]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/go/gofrontend/expressions.cc
Arm: Fix testism in pr88850 testcase.
[thirdparty/gcc.git] / gcc / go / gofrontend / expressions.cc
CommitLineData
e440a328 1// expressions.cc -- Go frontend expression handling.
2
3// Copyright 2009 The Go Authors. All rights reserved.
4// Use of this source code is governed by a BSD-style
5// license that can be found in the LICENSE file.
6
7#include "go-system.h"
8
ffe743ca 9#include <algorithm>
10
e440a328 11#include "go-c.h"
12#include "gogo.h"
631d5788 13#include "go-diagnostics.h"
438b4bec 14#include "go-encode-id.h"
e440a328 15#include "types.h"
16#include "export.h"
17#include "import.h"
18#include "statements.h"
19#include "lex.h"
a9182619 20#include "runtime.h"
6e193e6f 21#include "backend.h"
e440a328 22#include "expressions.h"
d751bb78 23#include "ast-dump.h"
e440a328 24
25// Class Expression.
26
27Expression::Expression(Expression_classification classification,
b13c66cd 28 Location location)
e440a328 29 : classification_(classification), location_(location)
30{
31}
32
33Expression::~Expression()
34{
35}
36
e440a328 37// Traverse the expressions.
38
39int
40Expression::traverse(Expression** pexpr, Traverse* traverse)
41{
42 Expression* expr = *pexpr;
43 if ((traverse->traverse_mask() & Traverse::traverse_expressions) != 0)
44 {
45 int t = traverse->expression(pexpr);
46 if (t == TRAVERSE_EXIT)
47 return TRAVERSE_EXIT;
48 else if (t == TRAVERSE_SKIP_COMPONENTS)
49 return TRAVERSE_CONTINUE;
50 }
51 return expr->do_traverse(traverse);
52}
53
54// Traverse subexpressions of this expression.
55
56int
57Expression::traverse_subexpressions(Traverse* traverse)
58{
59 return this->do_traverse(traverse);
60}
61
62// Default implementation for do_traverse for child classes.
63
64int
65Expression::do_traverse(Traverse*)
66{
67 return TRAVERSE_CONTINUE;
68}
69
70// This virtual function is called by the parser if the value of this
a7549a6a 71// expression is being discarded. By default, we give an error.
72// Expressions with side effects override.
e440a328 73
4f2138d7 74bool
e440a328 75Expression::do_discarding_value()
76{
a7549a6a 77 this->unused_value_error();
4f2138d7 78 return false;
e440a328 79}
80
81// This virtual function is called to export expressions. This will
82// only be used by expressions which may be constant.
83
84void
548be246 85Expression::do_export(Export_function_body*) const
e440a328 86{
c3e6f413 87 go_unreachable();
e440a328 88}
89
a7549a6a 90// Give an error saying that the value of the expression is not used.
e440a328 91
92void
a7549a6a 93Expression::unused_value_error()
e440a328 94{
4f2138d7 95 this->report_error(_("value computed is not used"));
e440a328 96}
97
98// Note that this expression is an error. This is called by children
99// when they discover an error.
100
101void
102Expression::set_is_error()
103{
104 this->classification_ = EXPRESSION_ERROR;
105}
106
107// For children to call to report an error conveniently.
108
109void
110Expression::report_error(const char* msg)
111{
631d5788 112 go_error_at(this->location_, "%s", msg);
e440a328 113 this->set_is_error();
114}
115
116// Set types of variables and constants. This is implemented by the
117// child class.
118
119void
120Expression::determine_type(const Type_context* context)
121{
122 this->do_determine_type(context);
123}
124
125// Set types when there is no context.
126
127void
128Expression::determine_type_no_context()
129{
130 Type_context context;
131 this->do_determine_type(&context);
132}
133
d3c55148 134// Return true if two expressions refer to the same variable or struct
135// field. This can only be true when there are no side effects.
136
137bool
138Expression::is_same_variable(Expression* a, Expression* b)
139{
140 if (a->classification() != b->classification())
141 return false;
142
143 Var_expression* av = a->var_expression();
144 if (av != NULL)
145 return av->named_object() == b->var_expression()->named_object();
146
147 Field_reference_expression* af = a->field_reference_expression();
148 if (af != NULL)
149 {
150 Field_reference_expression* bf = b->field_reference_expression();
151 return (af->field_index() == bf->field_index()
152 && Expression::is_same_variable(af->expr(), bf->expr()));
153 }
154
155 Unary_expression* au = a->unary_expression();
156 if (au != NULL)
157 {
158 Unary_expression* bu = b->unary_expression();
159 return (au->op() == OPERATOR_MULT
160 && bu->op() == OPERATOR_MULT
161 && Expression::is_same_variable(au->operand(),
162 bu->operand()));
163 }
164
165 return false;
166}
167
2c809f8f 168// Return an expression handling any conversions which must be done during
e440a328 169// assignment.
170
2c809f8f 171Expression*
b4a33049 172Expression::convert_for_assignment(Gogo*, Type* lhs_type,
2c809f8f 173 Expression* rhs, Location location)
e440a328 174{
2c809f8f 175 Type* rhs_type = rhs->type();
176 if (lhs_type->is_error()
177 || rhs_type->is_error()
178 || rhs->is_error_expression())
179 return Expression::make_error(location);
e440a328 180
3a522dcc 181 bool are_identical = Type::are_identical(lhs_type, rhs_type,
182 (Type::COMPARE_ERRORS
183 | Type::COMPARE_TAGS),
184 NULL);
22984631 185 if (!are_identical && lhs_type->interface_type() != NULL)
e440a328 186 {
187 if (rhs_type->interface_type() == NULL)
2c809f8f 188 return Expression::convert_type_to_interface(lhs_type, rhs, location);
e440a328 189 else
2c809f8f 190 return Expression::convert_interface_to_interface(lhs_type, rhs, false,
191 location);
e440a328 192 }
22984631 193 else if (!are_identical && rhs_type->interface_type() != NULL)
2c809f8f 194 return Expression::convert_interface_to_type(lhs_type, rhs, location);
411eb89e 195 else if (lhs_type->is_slice_type() && rhs_type->is_nil_type())
e440a328 196 {
2c809f8f 197 // Assigning nil to a slice.
2c809f8f 198 Expression* nil = Expression::make_nil(location);
e67508fa 199 Expression* zero = Expression::make_integer_ul(0, NULL, location);
2c809f8f 200 return Expression::make_slice_value(lhs_type, nil, zero, zero, location);
e440a328 201 }
202 else if (rhs_type->is_nil_type())
2c809f8f 203 return Expression::make_nil(location);
22984631 204 else if (are_identical)
e440a328 205 {
22984631 206 if (lhs_type->forwarded() != rhs_type->forwarded())
207 {
208 // Different but identical types require an explicit
209 // conversion. This happens with type aliases.
210 return Expression::make_cast(lhs_type, rhs, location);
211 }
212
e440a328 213 // No conversion is needed.
2c809f8f 214 return rhs;
215 }
216 else if (lhs_type->points_to() != NULL)
217 return Expression::make_unsafe_cast(lhs_type, rhs, location);
218 else if (lhs_type->is_numeric_type())
219 return Expression::make_cast(lhs_type, rhs, location);
220 else if ((lhs_type->struct_type() != NULL
221 && rhs_type->struct_type() != NULL)
222 || (lhs_type->array_type() != NULL
223 && rhs_type->array_type() != NULL))
e440a328 224 {
225 // This conversion must be permitted by Go, or we wouldn't have
226 // gotten here.
2c809f8f 227 return Expression::make_unsafe_cast(lhs_type, rhs, location);
e440a328 228 }
229 else
2c809f8f 230 return rhs;
e440a328 231}
232
2c809f8f 233// Return an expression for a conversion from a non-interface type to an
e440a328 234// interface type.
235
2c809f8f 236Expression*
237Expression::convert_type_to_interface(Type* lhs_type, Expression* rhs,
238 Location location)
e440a328 239{
e440a328 240 Interface_type* lhs_interface_type = lhs_type->interface_type();
241 bool lhs_is_empty = lhs_interface_type->is_empty();
242
243 // Since RHS_TYPE is a static type, we can create the interface
244 // method table at compile time.
245
246 // When setting an interface to nil, we just set both fields to
247 // NULL.
2c809f8f 248 Type* rhs_type = rhs->type();
e440a328 249 if (rhs_type->is_nil_type())
63697958 250 {
2c809f8f 251 Expression* nil = Expression::make_nil(location);
252 return Expression::make_interface_value(lhs_type, nil, nil, location);
63697958 253 }
e440a328 254
255 // This should have been checked already.
2b8629dd 256 if (!lhs_interface_type->implements_interface(rhs_type, NULL))
257 {
258 go_assert(saw_errors());
259 return Expression::make_error(location);
260 }
e440a328 261
e440a328 262 // An interface is a tuple. If LHS_TYPE is an empty interface type,
263 // then the first field is the type descriptor for RHS_TYPE.
264 // Otherwise it is the interface method table for RHS_TYPE.
2c809f8f 265 Expression* first_field;
e440a328 266 if (lhs_is_empty)
2c809f8f 267 first_field = Expression::make_type_descriptor(rhs_type, location);
e440a328 268 else
269 {
270 // Build the interface method table for this interface and this
271 // object type: a list of function pointers for each interface
272 // method.
273 Named_type* rhs_named_type = rhs_type->named_type();
c0cab2ec 274 Struct_type* rhs_struct_type = rhs_type->struct_type();
e440a328 275 bool is_pointer = false;
c0cab2ec 276 if (rhs_named_type == NULL && rhs_struct_type == NULL)
e440a328 277 {
278 rhs_named_type = rhs_type->deref()->named_type();
c0cab2ec 279 rhs_struct_type = rhs_type->deref()->struct_type();
e440a328 280 is_pointer = true;
281 }
c0cab2ec 282 if (rhs_named_type != NULL)
2c809f8f 283 first_field =
284 rhs_named_type->interface_method_table(lhs_interface_type,
285 is_pointer);
c0cab2ec 286 else if (rhs_struct_type != NULL)
2c809f8f 287 first_field =
288 rhs_struct_type->interface_method_table(lhs_interface_type,
289 is_pointer);
c0cab2ec 290 else
2c809f8f 291 first_field = Expression::make_nil(location);
e440a328 292 }
e440a328 293
2c809f8f 294 Expression* obj;
e440a328 295 if (rhs_type->points_to() != NULL)
296 {
2c809f8f 297 // We are assigning a pointer to the interface; the interface
e440a328 298 // holds the pointer itself.
2c809f8f 299 obj = rhs;
300 }
301 else
302 {
303 // We are assigning a non-pointer value to the interface; the
45ff893b 304 // interface gets a copy of the value in the heap if it escapes.
305 // TODO(cmang): Associate escape state state of RHS with newly
306 // created OBJ.
2c809f8f 307 obj = Expression::make_heap_expression(rhs, location);
e440a328 308 }
309
2c809f8f 310 return Expression::make_interface_value(lhs_type, first_field, obj, location);
311}
e440a328 312
2c809f8f 313// Return an expression for the type descriptor of RHS.
e440a328 314
2c809f8f 315Expression*
316Expression::get_interface_type_descriptor(Expression* rhs)
317{
318 go_assert(rhs->type()->interface_type() != NULL);
319 Location location = rhs->location();
e440a328 320
2c809f8f 321 // The type descriptor is the first field of an empty interface.
322 if (rhs->type()->interface_type()->is_empty())
323 return Expression::make_interface_info(rhs, INTERFACE_INFO_TYPE_DESCRIPTOR,
324 location);
325
326 Expression* mtable =
327 Expression::make_interface_info(rhs, INTERFACE_INFO_METHODS, location);
e440a328 328
2c809f8f 329 Expression* descriptor =
f614ea8b 330 Expression::make_dereference(mtable, NIL_CHECK_NOT_NEEDED, location);
2c809f8f 331 descriptor = Expression::make_field_reference(descriptor, 0, location);
332 Expression* nil = Expression::make_nil(location);
e440a328 333
2c809f8f 334 Expression* eq =
335 Expression::make_binary(OPERATOR_EQEQ, mtable, nil, location);
336 return Expression::make_conditional(eq, nil, descriptor, location);
e440a328 337}
338
2c809f8f 339// Return an expression for the conversion of an interface type to an
e440a328 340// interface type.
341
2c809f8f 342Expression*
343Expression::convert_interface_to_interface(Type *lhs_type, Expression* rhs,
344 bool for_type_guard,
345 Location location)
e440a328 346{
3a522dcc 347 if (Type::are_identical(lhs_type, rhs->type(),
348 Type::COMPARE_ERRORS | Type::COMPARE_TAGS,
349 NULL))
8ba8cc87 350 return rhs;
351
e440a328 352 Interface_type* lhs_interface_type = lhs_type->interface_type();
353 bool lhs_is_empty = lhs_interface_type->is_empty();
354
e440a328 355 // In the general case this requires runtime examination of the type
356 // method table to match it up with the interface methods.
357
358 // FIXME: If all of the methods in the right hand side interface
359 // also appear in the left hand side interface, then we don't need
360 // to do a runtime check, although we still need to build a new
361 // method table.
362
8ba8cc87 363 // We are going to evaluate RHS multiple times.
364 go_assert(rhs->is_variable());
365
e440a328 366 // Get the type descriptor for the right hand side. This will be
367 // NULL for a nil interface.
2c809f8f 368 Expression* rhs_type_expr = Expression::get_interface_type_descriptor(rhs);
369 Expression* lhs_type_expr =
370 Expression::make_type_descriptor(lhs_type, location);
e440a328 371
2c809f8f 372 Expression* first_field;
e440a328 373 if (for_type_guard)
374 {
375 // A type assertion fails when converting a nil interface.
6098d6cb 376 first_field = Runtime::make_call(Runtime::ASSERTITAB, location, 2,
377 lhs_type_expr, rhs_type_expr);
e440a328 378 }
379 else if (lhs_is_empty)
380 {
2c809f8f 381 // A conversion to an empty interface always succeeds, and the
e440a328 382 // first field is just the type descriptor of the object.
2c809f8f 383 first_field = rhs_type_expr;
e440a328 384 }
385 else
386 {
387 // A conversion to a non-empty interface may fail, but unlike a
388 // type assertion converting nil will always succeed.
6098d6cb 389 first_field = Runtime::make_call(Runtime::REQUIREITAB, location, 2,
390 lhs_type_expr, rhs_type_expr);
e440a328 391 }
392
393 // The second field is simply the object pointer.
2c809f8f 394 Expression* obj =
395 Expression::make_interface_info(rhs, INTERFACE_INFO_OBJECT, location);
396 return Expression::make_interface_value(lhs_type, first_field, obj, location);
e440a328 397}
398
2c809f8f 399// Return an expression for the conversion of an interface type to a
e440a328 400// non-interface type.
401
2c809f8f 402Expression*
403Expression::convert_interface_to_type(Type *lhs_type, Expression* rhs,
404 Location location)
e440a328 405{
8ba8cc87 406 // We are going to evaluate RHS multiple times.
407 go_assert(rhs->is_variable());
408
e440a328 409 // Call a function to check that the type is valid. The function
410 // will panic with an appropriate runtime type error if the type is
411 // not valid.
2c809f8f 412 Expression* lhs_type_expr = Expression::make_type_descriptor(lhs_type,
413 location);
414 Expression* rhs_descriptor =
415 Expression::get_interface_type_descriptor(rhs);
416
417 Type* rhs_type = rhs->type();
418 Expression* rhs_inter_expr = Expression::make_type_descriptor(rhs_type,
419 location);
420
6098d6cb 421 Expression* check_iface = Runtime::make_call(Runtime::ASSERTI2T,
2c809f8f 422 location, 3, lhs_type_expr,
423 rhs_descriptor, rhs_inter_expr);
e440a328 424
425 // If the call succeeds, pull out the value.
2c809f8f 426 Expression* obj = Expression::make_interface_info(rhs, INTERFACE_INFO_OBJECT,
427 location);
e440a328 428
429 // If the value is a pointer, then it is the value we want.
430 // Otherwise it points to the value.
431 if (lhs_type->points_to() == NULL)
432 {
2c809f8f 433 obj = Expression::make_unsafe_cast(Type::make_pointer_type(lhs_type), obj,
434 location);
f614ea8b 435 obj = Expression::make_dereference(obj, NIL_CHECK_NOT_NEEDED,
436 location);
e440a328 437 }
2c809f8f 438 return Expression::make_compound(check_iface, obj, location);
e440a328 439}
440
ea664253 441// Convert an expression to its backend representation. This is implemented by
442// the child class. Not that it is not in general safe to call this multiple
e440a328 443// times for a single expression, but that we don't catch such errors.
444
ea664253 445Bexpression*
446Expression::get_backend(Translate_context* context)
e440a328 447{
448 // The child may have marked this expression as having an error.
449 if (this->classification_ == EXPRESSION_ERROR)
ea664253 450 return context->backend()->error_expression();
e440a328 451
ea664253 452 return this->do_get_backend(context);
e440a328 453}
454
48c2a53a 455// Return a backend expression for VAL.
456Bexpression*
457Expression::backend_numeric_constant_expression(Translate_context* context,
458 Numeric_constant* val)
e440a328 459{
48c2a53a 460 Gogo* gogo = context->gogo();
461 Type* type = val->type();
462 if (type == NULL)
463 return gogo->backend()->error_expression();
e440a328 464
48c2a53a 465 Btype* btype = type->get_backend(gogo);
466 Bexpression* ret;
467 if (type->integer_type() != NULL)
e440a328 468 {
469 mpz_t ival;
48c2a53a 470 if (!val->to_int(&ival))
471 {
472 go_assert(saw_errors());
473 return gogo->backend()->error_expression();
474 }
475 ret = gogo->backend()->integer_constant_expression(btype, ival);
e440a328 476 mpz_clear(ival);
e440a328 477 }
48c2a53a 478 else if (type->float_type() != NULL)
e440a328 479 {
48c2a53a 480 mpfr_t fval;
481 if (!val->to_float(&fval))
482 {
483 go_assert(saw_errors());
484 return gogo->backend()->error_expression();
485 }
486 ret = gogo->backend()->float_constant_expression(btype, fval);
487 mpfr_clear(fval);
e440a328 488 }
48c2a53a 489 else if (type->complex_type() != NULL)
e440a328 490 {
fcbea5e4 491 mpc_t cval;
492 if (!val->to_complex(&cval))
48c2a53a 493 {
494 go_assert(saw_errors());
495 return gogo->backend()->error_expression();
496 }
fcbea5e4 497 ret = gogo->backend()->complex_constant_expression(btype, cval);
498 mpc_clear(cval);
e440a328 499 }
500 else
c3e6f413 501 go_unreachable();
e440a328 502
48c2a53a 503 return ret;
e440a328 504}
505
2c809f8f 506// Return an expression which evaluates to true if VAL, of arbitrary integer
507// type, is negative or is more than the maximum value of the Go type "int".
e440a328 508
2c809f8f 509Expression*
510Expression::check_bounds(Expression* val, Location loc)
e440a328 511{
2c809f8f 512 Type* val_type = val->type();
513 Type* bound_type = Type::lookup_integer_type("int");
514
515 int val_type_size;
516 bool val_is_unsigned = false;
517 if (val_type->integer_type() != NULL)
518 {
519 val_type_size = val_type->integer_type()->bits();
520 val_is_unsigned = val_type->integer_type()->is_unsigned();
521 }
522 else
523 {
524 if (!val_type->is_numeric_type()
525 || !Type::are_convertible(bound_type, val_type, NULL))
526 {
527 go_assert(saw_errors());
528 return Expression::make_boolean(true, loc);
529 }
e440a328 530
2c809f8f 531 if (val_type->complex_type() != NULL)
532 val_type_size = val_type->complex_type()->bits();
533 else
534 val_type_size = val_type->float_type()->bits();
535 }
536
537 Expression* negative_index = Expression::make_boolean(false, loc);
538 Expression* index_overflows = Expression::make_boolean(false, loc);
539 if (!val_is_unsigned)
e440a328 540 {
e67508fa 541 Expression* zero = Expression::make_integer_ul(0, val_type, loc);
2c809f8f 542 negative_index = Expression::make_binary(OPERATOR_LT, val, zero, loc);
e440a328 543 }
544
2c809f8f 545 int bound_type_size = bound_type->integer_type()->bits();
c3068ac0 546 if (val_type_size > bound_type_size
547 || (val_type_size == bound_type_size
2c809f8f 548 && val_is_unsigned))
549 {
550 mpz_t one;
551 mpz_init_set_ui(one, 1UL);
552
553 // maxval = 2^(bound_type_size - 1) - 1
554 mpz_t maxval;
555 mpz_init(maxval);
556 mpz_mul_2exp(maxval, one, bound_type_size - 1);
557 mpz_sub_ui(maxval, maxval, 1);
e67508fa 558 Expression* max = Expression::make_integer_z(&maxval, val_type, loc);
2c809f8f 559 mpz_clear(one);
560 mpz_clear(maxval);
561
562 index_overflows = Expression::make_binary(OPERATOR_GT, val, max, loc);
e440a328 563 }
564
2c809f8f 565 return Expression::make_binary(OPERATOR_OROR, negative_index, index_overflows,
566 loc);
e440a328 567}
568
d751bb78 569void
570Expression::dump_expression(Ast_dump_context* ast_dump_context) const
571{
572 this->do_dump_expression(ast_dump_context);
573}
574
e440a328 575// Error expressions. This are used to avoid cascading errors.
576
577class Error_expression : public Expression
578{
579 public:
b13c66cd 580 Error_expression(Location location)
e440a328 581 : Expression(EXPRESSION_ERROR, location)
582 { }
583
584 protected:
585 bool
586 do_is_constant() const
587 { return true; }
588
589 bool
0c77715b 590 do_numeric_constant_value(Numeric_constant* nc) const
e440a328 591 {
0c77715b 592 nc->set_unsigned_long(NULL, 0);
e440a328 593 return true;
594 }
595
4f2138d7 596 bool
e440a328 597 do_discarding_value()
4f2138d7 598 { return true; }
e440a328 599
600 Type*
601 do_type()
602 { return Type::make_error_type(); }
603
604 void
605 do_determine_type(const Type_context*)
606 { }
607
608 Expression*
609 do_copy()
610 { return this; }
611
612 bool
613 do_is_addressable() const
614 { return true; }
615
ea664253 616 Bexpression*
617 do_get_backend(Translate_context* context)
618 { return context->backend()->error_expression(); }
d751bb78 619
620 void
621 do_dump_expression(Ast_dump_context*) const;
e440a328 622};
623
d751bb78 624// Dump the ast representation for an error expression to a dump context.
625
626void
627Error_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
628{
629 ast_dump_context->ostream() << "_Error_" ;
630}
631
e440a328 632Expression*
b13c66cd 633Expression::make_error(Location location)
e440a328 634{
635 return new Error_expression(location);
636}
637
638// An expression which is really a type. This is used during parsing.
639// It is an error if these survive after lowering.
640
641class
642Type_expression : public Expression
643{
644 public:
b13c66cd 645 Type_expression(Type* type, Location location)
e440a328 646 : Expression(EXPRESSION_TYPE, location),
647 type_(type)
648 { }
649
650 protected:
651 int
652 do_traverse(Traverse* traverse)
653 { return Type::traverse(this->type_, traverse); }
654
655 Type*
656 do_type()
657 { return this->type_; }
658
659 void
660 do_determine_type(const Type_context*)
661 { }
662
663 void
664 do_check_types(Gogo*)
665 { this->report_error(_("invalid use of type")); }
666
667 Expression*
668 do_copy()
669 { return this; }
670
ea664253 671 Bexpression*
672 do_get_backend(Translate_context*)
c3e6f413 673 { go_unreachable(); }
e440a328 674
d751bb78 675 void do_dump_expression(Ast_dump_context*) const;
676
e440a328 677 private:
678 // The type which we are representing as an expression.
679 Type* type_;
680};
681
d751bb78 682void
683Type_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
684{
685 ast_dump_context->dump_type(this->type_);
686}
687
e440a328 688Expression*
b13c66cd 689Expression::make_type(Type* type, Location location)
e440a328 690{
691 return new Type_expression(type, location);
692}
693
e03bdf36 694// Class Parser_expression.
695
696Type*
697Parser_expression::do_type()
698{
699 // We should never really ask for the type of a Parser_expression.
700 // However, it can happen, at least when we have an invalid const
701 // whose initializer refers to the const itself. In that case we
702 // may ask for the type when lowering the const itself.
c484d925 703 go_assert(saw_errors());
e03bdf36 704 return Type::make_error_type();
705}
706
e440a328 707// Class Var_expression.
708
709// Lower a variable expression. Here we just make sure that the
710// initialization expression of the variable has been lowered. This
711// ensures that we will be able to determine the type of the variable
712// if necessary.
713
714Expression*
ceeb4318 715Var_expression::do_lower(Gogo* gogo, Named_object* function,
716 Statement_inserter* inserter, int)
e440a328 717{
718 if (this->variable_->is_variable())
719 {
720 Variable* var = this->variable_->var_value();
721 // This is either a local variable or a global variable. A
722 // reference to a variable which is local to an enclosing
723 // function will be a reference to a field in a closure.
724 if (var->is_global())
ceeb4318 725 {
726 function = NULL;
727 inserter = NULL;
728 }
729 var->lower_init_expression(gogo, function, inserter);
e440a328 730 }
731 return this;
732}
733
e440a328 734// Return the type of a reference to a variable.
735
736Type*
737Var_expression::do_type()
738{
739 if (this->variable_->is_variable())
740 return this->variable_->var_value()->type();
741 else if (this->variable_->is_result_variable())
742 return this->variable_->result_var_value()->type();
743 else
c3e6f413 744 go_unreachable();
e440a328 745}
746
0ab09e06 747// Determine the type of a reference to a variable.
748
749void
750Var_expression::do_determine_type(const Type_context*)
751{
752 if (this->variable_->is_variable())
753 this->variable_->var_value()->determine_type();
754}
755
e440a328 756// Something takes the address of this variable. This means that we
757// may want to move the variable onto the heap.
758
759void
760Var_expression::do_address_taken(bool escapes)
761{
762 if (!escapes)
f325319b 763 {
764 if (this->variable_->is_variable())
765 this->variable_->var_value()->set_non_escaping_address_taken();
766 else if (this->variable_->is_result_variable())
767 this->variable_->result_var_value()->set_non_escaping_address_taken();
768 else
769 go_unreachable();
770 }
e440a328 771 else
f325319b 772 {
773 if (this->variable_->is_variable())
774 this->variable_->var_value()->set_address_taken();
775 else if (this->variable_->is_result_variable())
776 this->variable_->result_var_value()->set_address_taken();
777 else
778 go_unreachable();
779 }
45ff893b 780
781 if (this->variable_->is_variable()
782 && this->variable_->var_value()->is_in_heap())
783 {
784 Node::make_node(this)->set_encoding(Node::ESCAPE_HEAP);
785 Node::make_node(this->variable_)->set_encoding(Node::ESCAPE_HEAP);
786 }
e440a328 787}
788
5f6f5357 789// The cost to inline a variable reference. We currently only support
790// references to parameters.
791
792int
793Var_expression::do_inlining_cost() const
794{
795 if (this->variable_->is_variable())
796 {
797 if (this->variable_->var_value()->is_parameter())
798 return 1;
799 }
800 else if (this->variable_->is_result_variable())
801 return 1;
802
803 return 0x100000;
804}
805
806// Export a reference to a variable.
807
808void
809Var_expression::do_export(Export_function_body* efb) const
810{
811 efb->write_string(Gogo::unpack_hidden_name(this->variable_->name()));
812}
813
ea664253 814// Get the backend representation for a reference to a variable.
e440a328 815
ea664253 816Bexpression*
817Var_expression::do_get_backend(Translate_context* context)
e440a328 818{
fe2f84cf 819 Bvariable* bvar = this->variable_->get_backend_variable(context->gogo(),
820 context->function());
fe2f84cf 821 bool is_in_heap;
c6777780 822 Location loc = this->location();
9b27b43c 823 Btype* btype;
824 Gogo* gogo = context->gogo();
fe2f84cf 825 if (this->variable_->is_variable())
9b27b43c 826 {
827 is_in_heap = this->variable_->var_value()->is_in_heap();
828 btype = this->variable_->var_value()->type()->get_backend(gogo);
829 }
fe2f84cf 830 else if (this->variable_->is_result_variable())
9b27b43c 831 {
832 is_in_heap = this->variable_->result_var_value()->is_in_heap();
833 btype = this->variable_->result_var_value()->type()->get_backend(gogo);
834 }
fe2f84cf 835 else
c3e6f413 836 go_unreachable();
c6777780 837
d4e6573e 838 Bexpression* ret =
7af8e400 839 context->backend()->var_expression(bvar, loc);
fe2f84cf 840 if (is_in_heap)
9b27b43c 841 ret = context->backend()->indirect_expression(btype, ret, true, loc);
ea664253 842 return ret;
e440a328 843}
844
d751bb78 845// Ast dump for variable expression.
846
847void
848Var_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
849{
cd5e24c1 850 ast_dump_context->ostream() << this->variable_->message_name() ;
d751bb78 851}
852
e440a328 853// Make a reference to a variable in an expression.
854
855Expression*
b13c66cd 856Expression::make_var_reference(Named_object* var, Location location)
e440a328 857{
858 if (var->is_sink())
859 return Expression::make_sink(location);
860
861 // FIXME: Creating a new object for each reference to a variable is
862 // wasteful.
863 return new Var_expression(var, location);
864}
865
b0c09712 866// Class Enclosed_var_expression.
867
868int
869Enclosed_var_expression::do_traverse(Traverse*)
870{
871 return TRAVERSE_CONTINUE;
872}
873
874// Lower the reference to the enclosed variable.
875
876Expression*
877Enclosed_var_expression::do_lower(Gogo* gogo, Named_object* function,
878 Statement_inserter* inserter, int)
879{
880 gogo->lower_expression(function, inserter, &this->reference_);
881 return this;
882}
883
884// Flatten the reference to the enclosed variable.
885
886Expression*
887Enclosed_var_expression::do_flatten(Gogo* gogo, Named_object* function,
888 Statement_inserter* inserter)
889{
890 gogo->flatten_expression(function, inserter, &this->reference_);
891 return this;
892}
893
894void
895Enclosed_var_expression::do_address_taken(bool escapes)
896{
897 if (!escapes)
898 {
899 if (this->variable_->is_variable())
900 this->variable_->var_value()->set_non_escaping_address_taken();
901 else if (this->variable_->is_result_variable())
902 this->variable_->result_var_value()->set_non_escaping_address_taken();
903 else
904 go_unreachable();
905 }
906 else
907 {
908 if (this->variable_->is_variable())
909 this->variable_->var_value()->set_address_taken();
910 else if (this->variable_->is_result_variable())
911 this->variable_->result_var_value()->set_address_taken();
912 else
913 go_unreachable();
914 }
45ff893b 915
916 if (this->variable_->is_variable()
917 && this->variable_->var_value()->is_in_heap())
918 Node::make_node(this->variable_)->set_encoding(Node::ESCAPE_HEAP);
b0c09712 919}
920
921// Ast dump for enclosed variable expression.
922
923void
924Enclosed_var_expression::do_dump_expression(Ast_dump_context* adc) const
925{
cd5e24c1 926 adc->ostream() << this->variable_->message_name();
b0c09712 927}
928
929// Make a reference to a variable within an enclosing function.
930
931Expression*
932Expression::make_enclosing_var_reference(Expression* reference,
933 Named_object* var, Location location)
934{
935 return new Enclosed_var_expression(reference, var, location);
936}
937
e440a328 938// Class Temporary_reference_expression.
939
940// The type.
941
942Type*
943Temporary_reference_expression::do_type()
944{
945 return this->statement_->type();
946}
947
948// Called if something takes the address of this temporary variable.
949// We never have to move temporary variables to the heap, but we do
950// need to know that they must live in the stack rather than in a
951// register.
952
953void
954Temporary_reference_expression::do_address_taken(bool)
955{
956 this->statement_->set_is_address_taken();
957}
958
ea664253 959// Get a backend expression referring to the variable.
e440a328 960
ea664253 961Bexpression*
962Temporary_reference_expression::do_get_backend(Translate_context* context)
e440a328 963{
cd440cff 964 Gogo* gogo = context->gogo();
eefc1ed3 965 Bvariable* bvar = this->statement_->get_backend_variable(context);
7af8e400 966 Bexpression* ret = gogo->backend()->var_expression(bvar, this->location());
eefc1ed3 967
cd440cff 968 // The backend can't always represent the same set of recursive types
eefc1ed3 969 // that the Go frontend can. In some cases this means that a
970 // temporary variable won't have the right backend type. Correct
971 // that here by adding a type cast. We need to use base() to push
972 // the circularity down one level.
cd440cff 973 Type* stype = this->statement_->type();
ceeb4318 974 if (!this->is_lvalue_
03118c21 975 && stype->points_to() != NULL
976 && stype->points_to()->is_void_type())
eefc1ed3 977 {
cd440cff 978 Btype* btype = this->type()->base()->get_backend(gogo);
979 ret = gogo->backend()->convert_expression(btype, ret, this->location());
eefc1ed3 980 }
ea664253 981 return ret;
e440a328 982}
983
d751bb78 984// Ast dump for temporary reference.
985
986void
987Temporary_reference_expression::do_dump_expression(
988 Ast_dump_context* ast_dump_context) const
989{
990 ast_dump_context->dump_temp_variable_name(this->statement_);
991}
992
e440a328 993// Make a reference to a temporary variable.
994
ceeb4318 995Temporary_reference_expression*
e440a328 996Expression::make_temporary_reference(Temporary_statement* statement,
b13c66cd 997 Location location)
e440a328 998{
999 return new Temporary_reference_expression(statement, location);
1000}
1001
e9d3367e 1002// Class Set_and_use_temporary_expression.
1003
1004// Return the type.
1005
1006Type*
1007Set_and_use_temporary_expression::do_type()
1008{
1009 return this->statement_->type();
1010}
1011
0afbb937 1012// Determine the type of the expression.
1013
1014void
1015Set_and_use_temporary_expression::do_determine_type(
1016 const Type_context* context)
1017{
1018 this->expr_->determine_type(context);
1019}
1020
e9d3367e 1021// Take the address.
1022
1023void
1024Set_and_use_temporary_expression::do_address_taken(bool)
1025{
1026 this->statement_->set_is_address_taken();
1027}
1028
1029// Return the backend representation.
1030
ea664253 1031Bexpression*
1032Set_and_use_temporary_expression::do_get_backend(Translate_context* context)
e9d3367e 1033{
e9d3367e 1034 Location loc = this->location();
a302c105 1035 Gogo* gogo = context->gogo();
1036 Bvariable* bvar = this->statement_->get_backend_variable(context);
7af8e400 1037 Bexpression* lvar_ref = gogo->backend()->var_expression(bvar, loc);
a302c105 1038
0ab48656 1039 Named_object* fn = context->function();
1040 go_assert(fn != NULL);
1041 Bfunction* bfn = fn->func_value()->get_or_make_decl(gogo, fn);
ea664253 1042 Bexpression* bexpr = this->expr_->get_backend(context);
0ab48656 1043 Bstatement* set = gogo->backend()->assignment_statement(bfn, lvar_ref,
1044 bexpr, loc);
7af8e400 1045 Bexpression* var_ref = gogo->backend()->var_expression(bvar, loc);
a302c105 1046 Bexpression* ret = gogo->backend()->compound_expression(set, var_ref, loc);
ea664253 1047 return ret;
e9d3367e 1048}
1049
1050// Dump.
1051
1052void
1053Set_and_use_temporary_expression::do_dump_expression(
1054 Ast_dump_context* ast_dump_context) const
1055{
1056 ast_dump_context->ostream() << '(';
1057 ast_dump_context->dump_temp_variable_name(this->statement_);
1058 ast_dump_context->ostream() << " = ";
1059 this->expr_->dump_expression(ast_dump_context);
1060 ast_dump_context->ostream() << ')';
1061}
1062
1063// Make a set-and-use temporary.
1064
1065Set_and_use_temporary_expression*
1066Expression::make_set_and_use_temporary(Temporary_statement* statement,
1067 Expression* expr, Location location)
1068{
1069 return new Set_and_use_temporary_expression(statement, expr, location);
1070}
1071
e440a328 1072// A sink expression--a use of the blank identifier _.
1073
1074class Sink_expression : public Expression
1075{
1076 public:
b13c66cd 1077 Sink_expression(Location location)
e440a328 1078 : Expression(EXPRESSION_SINK, location),
aa93217a 1079 type_(NULL), bvar_(NULL)
e440a328 1080 { }
1081
1082 protected:
4f2138d7 1083 bool
e440a328 1084 do_discarding_value()
4f2138d7 1085 { return true; }
e440a328 1086
1087 Type*
1088 do_type();
1089
1090 void
1091 do_determine_type(const Type_context*);
1092
1093 Expression*
1094 do_copy()
1095 { return new Sink_expression(this->location()); }
1096
ea664253 1097 Bexpression*
1098 do_get_backend(Translate_context*);
e440a328 1099
d751bb78 1100 void
1101 do_dump_expression(Ast_dump_context*) const;
1102
e440a328 1103 private:
1104 // The type of this sink variable.
1105 Type* type_;
1106 // The temporary variable we generate.
aa93217a 1107 Bvariable* bvar_;
e440a328 1108};
1109
1110// Return the type of a sink expression.
1111
1112Type*
1113Sink_expression::do_type()
1114{
1115 if (this->type_ == NULL)
1116 return Type::make_sink_type();
1117 return this->type_;
1118}
1119
1120// Determine the type of a sink expression.
1121
1122void
1123Sink_expression::do_determine_type(const Type_context* context)
1124{
1125 if (context->type != NULL)
1126 this->type_ = context->type;
1127}
1128
1129// Return a temporary variable for a sink expression. This will
1130// presumably be a write-only variable which the middle-end will drop.
1131
ea664253 1132Bexpression*
1133Sink_expression::do_get_backend(Translate_context* context)
e440a328 1134{
aa93217a 1135 Location loc = this->location();
1136 Gogo* gogo = context->gogo();
1137 if (this->bvar_ == NULL)
e440a328 1138 {
c484d925 1139 go_assert(this->type_ != NULL && !this->type_->is_sink_type());
aa93217a 1140 Named_object* fn = context->function();
1141 go_assert(fn != NULL);
1142 Bfunction* fn_ctx = fn->func_value()->get_or_make_decl(gogo, fn);
9f0e0513 1143 Btype* bt = this->type_->get_backend(context->gogo());
aa93217a 1144 Bstatement* decl;
1145 this->bvar_ =
1146 gogo->backend()->temporary_variable(fn_ctx, context->bblock(), bt, NULL,
1147 false, loc, &decl);
d4e6573e 1148 Bexpression* var_ref =
7af8e400 1149 gogo->backend()->var_expression(this->bvar_, loc);
aa93217a 1150 var_ref = gogo->backend()->compound_expression(decl, var_ref, loc);
ea664253 1151 return var_ref;
e440a328 1152 }
7af8e400 1153 return gogo->backend()->var_expression(this->bvar_, loc);
e440a328 1154}
1155
d751bb78 1156// Ast dump for sink expression.
1157
1158void
1159Sink_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
1160{
1161 ast_dump_context->ostream() << "_" ;
1162}
1163
e440a328 1164// Make a sink expression.
1165
1166Expression*
b13c66cd 1167Expression::make_sink(Location location)
e440a328 1168{
1169 return new Sink_expression(location);
1170}
1171
1172// Class Func_expression.
1173
1174// FIXME: Can a function expression appear in a constant expression?
1175// The value is unchanging. Initializing a constant to the address of
1176// a function seems like it could work, though there might be little
1177// point to it.
1178
e440a328 1179// Traversal.
1180
1181int
1182Func_expression::do_traverse(Traverse* traverse)
1183{
1184 return (this->closure_ == NULL
1185 ? TRAVERSE_CONTINUE
1186 : Expression::traverse(&this->closure_, traverse));
1187}
1188
1189// Return the type of a function expression.
1190
1191Type*
1192Func_expression::do_type()
1193{
1194 if (this->function_->is_function())
1195 return this->function_->func_value()->type();
1196 else if (this->function_->is_function_declaration())
1197 return this->function_->func_declaration_value()->type();
1198 else
c3e6f413 1199 go_unreachable();
e440a328 1200}
1201
ea664253 1202// Get the backend representation for the code of a function expression.
e440a328 1203
97267c39 1204Bexpression*
8381eda7 1205Func_expression::get_code_pointer(Gogo* gogo, Named_object* no, Location loc)
e440a328 1206{
1207 Function_type* fntype;
8381eda7 1208 if (no->is_function())
1209 fntype = no->func_value()->type();
1210 else if (no->is_function_declaration())
1211 fntype = no->func_declaration_value()->type();
e440a328 1212 else
c3e6f413 1213 go_unreachable();
e440a328 1214
1215 // Builtin functions are handled specially by Call_expression. We
1216 // can't take their address.
1217 if (fntype->is_builtin())
1218 {
631d5788 1219 go_error_at(loc,
1220 "invalid use of special builtin function %qs; must be called",
1221 no->message_name().c_str());
97267c39 1222 return gogo->backend()->error_expression();
e440a328 1223 }
1224
97267c39 1225 Bfunction* fndecl;
e440a328 1226 if (no->is_function())
cf3cae55 1227 fndecl = no->func_value()->get_or_make_decl(gogo, no);
e440a328 1228 else if (no->is_function_declaration())
cf3cae55 1229 fndecl = no->func_declaration_value()->get_or_make_decl(gogo, no);
e440a328 1230 else
c3e6f413 1231 go_unreachable();
e440a328 1232
97267c39 1233 return gogo->backend()->function_code_expression(fndecl, loc);
e440a328 1234}
1235
ea664253 1236// Get the backend representation for a function expression. This is used when
1237// we take the address of a function rather than simply calling it. A func
8381eda7 1238// value is represented as a pointer to a block of memory. The first
1239// word of that memory is a pointer to the function code. The
1240// remaining parts of that memory are the addresses of variables that
1241// the function closes over.
e440a328 1242
ea664253 1243Bexpression*
1244Func_expression::do_get_backend(Translate_context* context)
e440a328 1245{
8381eda7 1246 // If there is no closure, just use the function descriptor.
2010c17a 1247 if (this->closure_ == NULL)
8381eda7 1248 {
1249 Gogo* gogo = context->gogo();
1250 Named_object* no = this->function_;
1251 Expression* descriptor;
1252 if (no->is_function())
1253 descriptor = no->func_value()->descriptor(gogo, no);
1254 else if (no->is_function_declaration())
1255 {
1256 if (no->func_declaration_value()->type()->is_builtin())
1257 {
631d5788 1258 go_error_at(this->location(),
1259 ("invalid use of special builtin function %qs; "
1260 "must be called"),
1261 no->message_name().c_str());
ea664253 1262 return gogo->backend()->error_expression();
8381eda7 1263 }
1264 descriptor = no->func_declaration_value()->descriptor(gogo, no);
1265 }
1266 else
1267 go_unreachable();
2010c17a 1268
ea664253 1269 Bexpression* bdesc = descriptor->get_backend(context);
1270 return gogo->backend()->address_expression(bdesc, this->location());
8381eda7 1271 }
e440a328 1272
8381eda7 1273 go_assert(this->function_->func_value()->enclosing() != NULL);
e440a328 1274
8381eda7 1275 // If there is a closure, then the closure is itself the function
1276 // expression. It is a pointer to a struct whose first field points
1277 // to the function code and whose remaining fields are the addresses
1278 // of the closed-over variables.
76818e19 1279 Bexpression *bexpr = this->closure_->get_backend(context);
1280
1281 // Introduce a backend type conversion, to account for any differences
1282 // between the argument type (function descriptor, struct with a
1283 // single field) and the closure (struct with multiple fields).
1284 Gogo* gogo = context->gogo();
1285 Btype *btype = this->type()->get_backend(gogo);
1286 return gogo->backend()->convert_expression(btype, bexpr, this->location());
e440a328 1287}
1288
d751bb78 1289// Ast dump for function.
1290
1291void
1292Func_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
1293{
8b1c301d 1294 ast_dump_context->ostream() << this->function_->name();
1295 if (this->closure_ != NULL)
1296 {
1297 ast_dump_context->ostream() << " {closure = ";
1298 this->closure_->dump_expression(ast_dump_context);
1299 ast_dump_context->ostream() << "}";
1300 }
d751bb78 1301}
1302
e440a328 1303// Make a reference to a function in an expression.
1304
1305Expression*
1306Expression::make_func_reference(Named_object* function, Expression* closure,
b13c66cd 1307 Location location)
e440a328 1308{
b1d7ecfa 1309 Func_expression* fe = new Func_expression(function, closure, location);
1310
1311 // Detect references to builtin functions and set the runtime code if
1312 // appropriate.
1313 if (function->is_function_declaration())
1314 fe->set_runtime_code(Runtime::name_to_code(function->name()));
1315 return fe;
e440a328 1316}
1317
c6837989 1318// Class Func_descriptor_expression.
8381eda7 1319
c6837989 1320// Constructor.
8381eda7 1321
c6837989 1322Func_descriptor_expression::Func_descriptor_expression(Named_object* fn)
1323 : Expression(EXPRESSION_FUNC_DESCRIPTOR, fn->location()),
f8bdf81a 1324 fn_(fn), dvar_(NULL)
c6837989 1325{
1326 go_assert(!fn->is_function() || !fn->func_value()->needs_closure());
1327}
8381eda7 1328
c6837989 1329// Traversal.
8381eda7 1330
c6837989 1331int
1332Func_descriptor_expression::do_traverse(Traverse*)
1333{
1334 return TRAVERSE_CONTINUE;
1335}
8381eda7 1336
1337// All function descriptors have the same type.
1338
1339Type* Func_descriptor_expression::descriptor_type;
1340
1341void
1342Func_descriptor_expression::make_func_descriptor_type()
1343{
1344 if (Func_descriptor_expression::descriptor_type != NULL)
1345 return;
1346 Type* uintptr_type = Type::lookup_integer_type("uintptr");
1347 Type* struct_type = Type::make_builtin_struct_type(1, "code", uintptr_type);
1348 Func_descriptor_expression::descriptor_type =
1349 Type::make_builtin_named_type("functionDescriptor", struct_type);
1350}
1351
1352Type*
1353Func_descriptor_expression::do_type()
1354{
1355 Func_descriptor_expression::make_func_descriptor_type();
1356 return Func_descriptor_expression::descriptor_type;
1357}
1358
ea664253 1359// The backend representation for a function descriptor.
8381eda7 1360
ea664253 1361Bexpression*
1362Func_descriptor_expression::do_get_backend(Translate_context* context)
8381eda7 1363{
8381eda7 1364 Named_object* no = this->fn_;
1365 Location loc = no->location();
ea664253 1366 if (this->dvar_ != NULL)
7af8e400 1367 return context->backend()->var_expression(this->dvar_, loc);
8381eda7 1368
ea664253 1369 Gogo* gogo = context->gogo();
19272321 1370 std::string var_name(gogo->function_descriptor_name(no));
09e57698 1371 bool is_descriptor = false;
1372 if (no->is_function_declaration()
1373 && !no->func_declaration_value()->asm_name().empty()
1374 && Linemap::is_predeclared_location(no->location()))
19272321 1375 is_descriptor = true;
8381eda7 1376
13f2fdb8 1377 // The runtime package implements some functions defined in the
1378 // syscall package. Let the syscall package define the descriptor
1379 // in this case.
1380 if (gogo->compiling_runtime()
1381 && gogo->package_name() == "runtime"
1382 && no->is_function()
1383 && !no->func_value()->asm_name().empty()
1384 && no->func_value()->asm_name().compare(0, 8, "syscall.") == 0)
1385 is_descriptor = true;
1386
8381eda7 1387 Btype* btype = this->type()->get_backend(gogo);
1388
1389 Bvariable* bvar;
438b4bec 1390 std::string asm_name(go_selectively_encode_id(var_name));
09e57698 1391 if (no->package() != NULL || is_descriptor)
438b4bec 1392 bvar = context->backend()->immutable_struct_reference(var_name, asm_name,
1393 btype, loc);
8381eda7 1394 else
1395 {
1396 Location bloc = Linemap::predeclared_location();
80efb81d 1397
1398 // The runtime package has hash/equality functions that are
1399 // referenced by type descriptors outside of the runtime, so the
1400 // function descriptors must be visible even though they are not
1401 // exported.
1402 bool is_exported_runtime = false;
1403 if (gogo->compiling_runtime()
1404 && gogo->package_name() == "runtime"
1405 && (no->name().find("hash") != std::string::npos
1406 || no->name().find("equal") != std::string::npos))
1407 is_exported_runtime = true;
1408
8381eda7 1409 bool is_hidden = ((no->is_function()
1410 && no->func_value()->enclosing() != NULL)
80efb81d 1411 || (Gogo::is_hidden_name(no->name())
1412 && !is_exported_runtime)
8381eda7 1413 || Gogo::is_thunk(no));
80efb81d 1414
438b4bec 1415 bvar = context->backend()->immutable_struct(var_name, asm_name,
1416 is_hidden, false,
8381eda7 1417 btype, bloc);
1418 Expression_list* vals = new Expression_list();
f8bdf81a 1419 vals->push_back(Expression::make_func_code_reference(this->fn_, bloc));
8381eda7 1420 Expression* init =
1421 Expression::make_struct_composite_literal(this->type(), vals, bloc);
1422 Translate_context bcontext(gogo, NULL, NULL, NULL);
1423 bcontext.set_is_const();
ea664253 1424 Bexpression* binit = init->get_backend(&bcontext);
8381eda7 1425 context->backend()->immutable_struct_set_init(bvar, var_name, is_hidden,
1426 false, btype, bloc, binit);
1427 }
1428
1429 this->dvar_ = bvar;
7af8e400 1430 return gogo->backend()->var_expression(bvar, loc);
8381eda7 1431}
1432
c6837989 1433// Print a function descriptor expression.
1434
1435void
1436Func_descriptor_expression::do_dump_expression(Ast_dump_context* context) const
1437{
1438 context->ostream() << "[descriptor " << this->fn_->name() << "]";
1439}
1440
8381eda7 1441// Make a function descriptor expression.
1442
c6837989 1443Func_descriptor_expression*
1444Expression::make_func_descriptor(Named_object* fn)
8381eda7 1445{
c6837989 1446 return new Func_descriptor_expression(fn);
8381eda7 1447}
1448
1449// Make the function descriptor type, so that it can be converted.
1450
1451void
1452Expression::make_func_descriptor_type()
1453{
1454 Func_descriptor_expression::make_func_descriptor_type();
1455}
1456
1457// A reference to just the code of a function.
1458
1459class Func_code_reference_expression : public Expression
1460{
1461 public:
1462 Func_code_reference_expression(Named_object* function, Location location)
1463 : Expression(EXPRESSION_FUNC_CODE_REFERENCE, location),
1464 function_(function)
1465 { }
1466
1467 protected:
1468 int
1469 do_traverse(Traverse*)
1470 { return TRAVERSE_CONTINUE; }
1471
f9ca30f9 1472 bool
3ae06f68 1473 do_is_static_initializer() const
f9ca30f9 1474 { return true; }
1475
8381eda7 1476 Type*
1477 do_type()
1478 { return Type::make_pointer_type(Type::make_void_type()); }
1479
1480 void
1481 do_determine_type(const Type_context*)
1482 { }
1483
1484 Expression*
1485 do_copy()
1486 {
1487 return Expression::make_func_code_reference(this->function_,
1488 this->location());
1489 }
1490
ea664253 1491 Bexpression*
1492 do_get_backend(Translate_context*);
8381eda7 1493
1494 void
1495 do_dump_expression(Ast_dump_context* context) const
1496 { context->ostream() << "[raw " << this->function_->name() << "]" ; }
1497
1498 private:
1499 // The function.
1500 Named_object* function_;
1501};
1502
ea664253 1503// Get the backend representation for a reference to function code.
8381eda7 1504
ea664253 1505Bexpression*
1506Func_code_reference_expression::do_get_backend(Translate_context* context)
8381eda7 1507{
ea664253 1508 return Func_expression::get_code_pointer(context->gogo(), this->function_,
1509 this->location());
8381eda7 1510}
1511
1512// Make a reference to the code of a function.
1513
1514Expression*
1515Expression::make_func_code_reference(Named_object* function, Location location)
1516{
1517 return new Func_code_reference_expression(function, location);
1518}
1519
e440a328 1520// Class Unknown_expression.
1521
1522// Return the name of an unknown expression.
1523
1524const std::string&
1525Unknown_expression::name() const
1526{
1527 return this->named_object_->name();
1528}
1529
1530// Lower a reference to an unknown name.
1531
1532Expression*
ceeb4318 1533Unknown_expression::do_lower(Gogo*, Named_object*, Statement_inserter*, int)
e440a328 1534{
b13c66cd 1535 Location location = this->location();
e440a328 1536 Named_object* no = this->named_object_;
deded542 1537 Named_object* real;
1538 if (!no->is_unknown())
1539 real = no;
1540 else
e440a328 1541 {
deded542 1542 real = no->unknown_value()->real_named_object();
1543 if (real == NULL)
1544 {
1545 if (this->is_composite_literal_key_)
1546 return this;
acf8e158 1547 if (!this->no_error_message_)
631d5788 1548 go_error_at(location, "reference to undefined name %qs",
1549 this->named_object_->message_name().c_str());
deded542 1550 return Expression::make_error(location);
1551 }
e440a328 1552 }
1553 switch (real->classification())
1554 {
1555 case Named_object::NAMED_OBJECT_CONST:
1556 return Expression::make_const_reference(real, location);
1557 case Named_object::NAMED_OBJECT_TYPE:
1558 return Expression::make_type(real->type_value(), location);
1559 case Named_object::NAMED_OBJECT_TYPE_DECLARATION:
1560 if (this->is_composite_literal_key_)
1561 return this;
acf8e158 1562 if (!this->no_error_message_)
631d5788 1563 go_error_at(location, "reference to undefined type %qs",
1564 real->message_name().c_str());
e440a328 1565 return Expression::make_error(location);
1566 case Named_object::NAMED_OBJECT_VAR:
7d834090 1567 real->var_value()->set_is_used();
e440a328 1568 return Expression::make_var_reference(real, location);
1569 case Named_object::NAMED_OBJECT_FUNC:
1570 case Named_object::NAMED_OBJECT_FUNC_DECLARATION:
1571 return Expression::make_func_reference(real, NULL, location);
1572 case Named_object::NAMED_OBJECT_PACKAGE:
1573 if (this->is_composite_literal_key_)
1574 return this;
acf8e158 1575 if (!this->no_error_message_)
631d5788 1576 go_error_at(location, "unexpected reference to package");
e440a328 1577 return Expression::make_error(location);
1578 default:
c3e6f413 1579 go_unreachable();
e440a328 1580 }
1581}
1582
d751bb78 1583// Dump the ast representation for an unknown expression to a dump context.
1584
1585void
1586Unknown_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
1587{
1588 ast_dump_context->ostream() << "_Unknown_(" << this->named_object_->name()
1589 << ")";
d751bb78 1590}
1591
e440a328 1592// Make a reference to an unknown name.
1593
acf8e158 1594Unknown_expression*
b13c66cd 1595Expression::make_unknown_reference(Named_object* no, Location location)
e440a328 1596{
e440a328 1597 return new Unknown_expression(no, location);
1598}
1599
1600// A boolean expression.
1601
1602class Boolean_expression : public Expression
1603{
1604 public:
b13c66cd 1605 Boolean_expression(bool val, Location location)
e440a328 1606 : Expression(EXPRESSION_BOOLEAN, location),
1607 val_(val), type_(NULL)
1608 { }
1609
1610 static Expression*
bc8e2ef4 1611 do_import(Import_expression*, Location);
e440a328 1612
1613 protected:
1614 bool
1615 do_is_constant() const
1616 { return true; }
1617
0e168074 1618 bool
3ae06f68 1619 do_is_static_initializer() const
0e168074 1620 { return true; }
1621
e440a328 1622 Type*
1623 do_type();
1624
1625 void
1626 do_determine_type(const Type_context*);
1627
1628 Expression*
1629 do_copy()
1630 { return this; }
1631
ea664253 1632 Bexpression*
1633 do_get_backend(Translate_context* context)
1634 { return context->backend()->boolean_constant_expression(this->val_); }
e440a328 1635
5f6f5357 1636 int
1637 do_inlining_cost() const
1638 { return 1; }
1639
e440a328 1640 void
548be246 1641 do_export(Export_function_body* efb) const
204d4af4 1642 { efb->write_c_string(this->val_ ? "$true" : "$false"); }
e440a328 1643
d751bb78 1644 void
1645 do_dump_expression(Ast_dump_context* ast_dump_context) const
1646 { ast_dump_context->ostream() << (this->val_ ? "true" : "false"); }
1647
e440a328 1648 private:
1649 // The constant.
1650 bool val_;
1651 // The type as determined by context.
1652 Type* type_;
1653};
1654
1655// Get the type.
1656
1657Type*
1658Boolean_expression::do_type()
1659{
1660 if (this->type_ == NULL)
1661 this->type_ = Type::make_boolean_type();
1662 return this->type_;
1663}
1664
1665// Set the type from the context.
1666
1667void
1668Boolean_expression::do_determine_type(const Type_context* context)
1669{
1670 if (this->type_ != NULL && !this->type_->is_abstract())
1671 ;
1672 else if (context->type != NULL && context->type->is_boolean_type())
1673 this->type_ = context->type;
1674 else if (!context->may_be_abstract)
1675 this->type_ = Type::lookup_bool_type();
1676}
1677
1678// Import a boolean constant.
1679
1680Expression*
bc8e2ef4 1681Boolean_expression::do_import(Import_expression* imp, Location loc)
e440a328 1682{
204d4af4 1683 if (imp->version() >= EXPORT_FORMAT_V3)
1684 imp->require_c_string("$");
e440a328 1685 if (imp->peek_char() == 't')
1686 {
1687 imp->require_c_string("true");
9b92780c 1688 return Expression::make_boolean(true, loc);
e440a328 1689 }
1690 else
1691 {
1692 imp->require_c_string("false");
9b92780c 1693 return Expression::make_boolean(false, loc);
e440a328 1694 }
1695}
1696
1697// Make a boolean expression.
1698
1699Expression*
b13c66cd 1700Expression::make_boolean(bool val, Location location)
e440a328 1701{
1702 return new Boolean_expression(val, location);
1703}
1704
1705// Class String_expression.
1706
1707// Get the type.
1708
1709Type*
1710String_expression::do_type()
1711{
1712 if (this->type_ == NULL)
1713 this->type_ = Type::make_string_type();
1714 return this->type_;
1715}
1716
1717// Set the type from the context.
1718
1719void
1720String_expression::do_determine_type(const Type_context* context)
1721{
1722 if (this->type_ != NULL && !this->type_->is_abstract())
1723 ;
1724 else if (context->type != NULL && context->type->is_string_type())
1725 this->type_ = context->type;
1726 else if (!context->may_be_abstract)
1727 this->type_ = Type::lookup_string_type();
1728}
1729
1730// Build a string constant.
1731
ea664253 1732Bexpression*
1733String_expression::do_get_backend(Translate_context* context)
e440a328 1734{
2c809f8f 1735 Gogo* gogo = context->gogo();
1736 Btype* btype = Type::make_string_type()->get_backend(gogo);
1737
1738 Location loc = this->location();
1739 std::vector<Bexpression*> init(2);
1740 Bexpression* str_cst =
1741 gogo->backend()->string_constant_expression(this->val_);
1742 init[0] = gogo->backend()->address_expression(str_cst, loc);
1743
1744 Btype* int_btype = Type::lookup_integer_type("int")->get_backend(gogo);
1745 mpz_t lenval;
1746 mpz_init_set_ui(lenval, this->val_.length());
1747 init[1] = gogo->backend()->integer_constant_expression(int_btype, lenval);
1748 mpz_clear(lenval);
1749
ea664253 1750 return gogo->backend()->constructor_expression(btype, init, loc);
e440a328 1751}
1752
8b1c301d 1753 // Write string literal to string dump.
e440a328 1754
1755void
8b1c301d 1756String_expression::export_string(String_dump* exp,
1757 const String_expression* str)
e440a328 1758{
1759 std::string s;
8b1c301d 1760 s.reserve(str->val_.length() * 4 + 2);
e440a328 1761 s += '"';
8b1c301d 1762 for (std::string::const_iterator p = str->val_.begin();
1763 p != str->val_.end();
e440a328 1764 ++p)
1765 {
1766 if (*p == '\\' || *p == '"')
1767 {
1768 s += '\\';
1769 s += *p;
1770 }
1771 else if (*p >= 0x20 && *p < 0x7f)
1772 s += *p;
1773 else if (*p == '\n')
1774 s += "\\n";
1775 else if (*p == '\t')
1776 s += "\\t";
1777 else
1778 {
1779 s += "\\x";
1780 unsigned char c = *p;
1781 unsigned int dig = c >> 4;
1782 s += dig < 10 ? '0' + dig : 'A' + dig - 10;
1783 dig = c & 0xf;
1784 s += dig < 10 ? '0' + dig : 'A' + dig - 10;
1785 }
1786 }
1787 s += '"';
1788 exp->write_string(s);
1789}
1790
8b1c301d 1791// Export a string expression.
1792
1793void
548be246 1794String_expression::do_export(Export_function_body* efb) const
8b1c301d 1795{
548be246 1796 String_expression::export_string(efb, this);
8b1c301d 1797}
1798
e440a328 1799// Import a string expression.
1800
1801Expression*
bc8e2ef4 1802String_expression::do_import(Import_expression* imp, Location loc)
e440a328 1803{
1804 imp->require_c_string("\"");
1805 std::string val;
1806 while (true)
1807 {
1808 int c = imp->get_char();
1809 if (c == '"' || c == -1)
1810 break;
1811 if (c != '\\')
1812 val += static_cast<char>(c);
1813 else
1814 {
1815 c = imp->get_char();
1816 if (c == '\\' || c == '"')
1817 val += static_cast<char>(c);
1818 else if (c == 'n')
1819 val += '\n';
1820 else if (c == 't')
1821 val += '\t';
1822 else if (c == 'x')
1823 {
1824 c = imp->get_char();
1825 unsigned int vh = c >= '0' && c <= '9' ? c - '0' : c - 'A' + 10;
1826 c = imp->get_char();
1827 unsigned int vl = c >= '0' && c <= '9' ? c - '0' : c - 'A' + 10;
1828 char v = (vh << 4) | vl;
1829 val += v;
1830 }
1831 else
1832 {
631d5788 1833 go_error_at(imp->location(), "bad string constant");
9b92780c 1834 return Expression::make_error(loc);
e440a328 1835 }
1836 }
1837 }
9b92780c 1838 return Expression::make_string(val, loc);
e440a328 1839}
1840
d751bb78 1841// Ast dump for string expression.
1842
1843void
1844String_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
1845{
8b1c301d 1846 String_expression::export_string(ast_dump_context, this);
d751bb78 1847}
1848
e440a328 1849// Make a string expression.
1850
1851Expression*
b13c66cd 1852Expression::make_string(const std::string& val, Location location)
e440a328 1853{
1854 return new String_expression(val, location);
1855}
1856
2c809f8f 1857// An expression that evaluates to some characteristic of a string.
1858// This is used when indexing, bound-checking, or nil checking a string.
1859
1860class String_info_expression : public Expression
1861{
1862 public:
1863 String_info_expression(Expression* string, String_info string_info,
1864 Location location)
1865 : Expression(EXPRESSION_STRING_INFO, location),
1866 string_(string), string_info_(string_info)
1867 { }
1868
1869 protected:
1870 Type*
1871 do_type();
1872
1873 void
1874 do_determine_type(const Type_context*)
1875 { go_unreachable(); }
1876
1877 Expression*
1878 do_copy()
1879 {
1880 return new String_info_expression(this->string_->copy(), this->string_info_,
1881 this->location());
1882 }
1883
ea664253 1884 Bexpression*
1885 do_get_backend(Translate_context* context);
2c809f8f 1886
1887 void
1888 do_dump_expression(Ast_dump_context*) const;
1889
1890 void
1891 do_issue_nil_check()
1892 { this->string_->issue_nil_check(); }
1893
1894 private:
1895 // The string for which we are getting information.
1896 Expression* string_;
1897 // What information we want.
1898 String_info string_info_;
1899};
1900
1901// Return the type of the string info.
1902
1903Type*
1904String_info_expression::do_type()
1905{
1906 switch (this->string_info_)
1907 {
1908 case STRING_INFO_DATA:
1909 {
1910 Type* byte_type = Type::lookup_integer_type("uint8");
1911 return Type::make_pointer_type(byte_type);
1912 }
1913 case STRING_INFO_LENGTH:
1914 return Type::lookup_integer_type("int");
1915 default:
1916 go_unreachable();
1917 }
1918}
1919
1920// Return string information in GENERIC.
1921
ea664253 1922Bexpression*
1923String_info_expression::do_get_backend(Translate_context* context)
2c809f8f 1924{
1925 Gogo* gogo = context->gogo();
1926
ea664253 1927 Bexpression* bstring = this->string_->get_backend(context);
2c809f8f 1928 switch (this->string_info_)
1929 {
1930 case STRING_INFO_DATA:
1931 case STRING_INFO_LENGTH:
ea664253 1932 return gogo->backend()->struct_field_expression(bstring,
1933 this->string_info_,
1934 this->location());
2c809f8f 1935 break;
1936 default:
1937 go_unreachable();
1938 }
2c809f8f 1939}
1940
1941// Dump ast representation for a type info expression.
1942
1943void
1944String_info_expression::do_dump_expression(
1945 Ast_dump_context* ast_dump_context) const
1946{
1947 ast_dump_context->ostream() << "stringinfo(";
1948 this->string_->dump_expression(ast_dump_context);
1949 ast_dump_context->ostream() << ",";
1950 ast_dump_context->ostream() <<
1951 (this->string_info_ == STRING_INFO_DATA ? "data"
1952 : this->string_info_ == STRING_INFO_LENGTH ? "length"
1953 : "unknown");
1954 ast_dump_context->ostream() << ")";
1955}
1956
1957// Make a string info expression.
1958
1959Expression*
1960Expression::make_string_info(Expression* string, String_info string_info,
1961 Location location)
1962{
1963 return new String_info_expression(string, string_info, location);
1964}
1965
e440a328 1966// Make an integer expression.
1967
1968class Integer_expression : public Expression
1969{
1970 public:
5d4b8566 1971 Integer_expression(const mpz_t* val, Type* type, bool is_character_constant,
1972 Location location)
e440a328 1973 : Expression(EXPRESSION_INTEGER, location),
5d4b8566 1974 type_(type), is_character_constant_(is_character_constant)
e440a328 1975 { mpz_init_set(this->val_, *val); }
1976
1977 static Expression*
bc8e2ef4 1978 do_import(Import_expression*, Location);
e440a328 1979
8b1c301d 1980 // Write VAL to string dump.
e440a328 1981 static void
8b1c301d 1982 export_integer(String_dump* exp, const mpz_t val);
e440a328 1983
d751bb78 1984 // Write VAL to dump context.
1985 static void
1986 dump_integer(Ast_dump_context* ast_dump_context, const mpz_t val);
1987
e440a328 1988 protected:
1989 bool
1990 do_is_constant() const
1991 { return true; }
1992
0e168074 1993 bool
3ae06f68 1994 do_is_static_initializer() const
0e168074 1995 { return true; }
1996
e440a328 1997 bool
0c77715b 1998 do_numeric_constant_value(Numeric_constant* nc) const;
e440a328 1999
2000 Type*
2001 do_type();
2002
2003 void
2004 do_determine_type(const Type_context* context);
2005
2006 void
2007 do_check_types(Gogo*);
2008
ea664253 2009 Bexpression*
2010 do_get_backend(Translate_context*);
e440a328 2011
2012 Expression*
2013 do_copy()
5d4b8566 2014 {
2015 if (this->is_character_constant_)
de590a61 2016 return Expression::make_character(&this->val_,
2017 (this->type_ == NULL
2018 ? NULL
2019 : this->type_->copy_expressions()),
5d4b8566 2020 this->location());
2021 else
de590a61 2022 return Expression::make_integer_z(&this->val_,
2023 (this->type_ == NULL
2024 ? NULL
2025 : this->type_->copy_expressions()),
e67508fa 2026 this->location());
5d4b8566 2027 }
e440a328 2028
5f6f5357 2029 int
2030 do_inlining_cost() const
2031 { return 1; }
2032
e440a328 2033 void
548be246 2034 do_export(Export_function_body*) const;
e440a328 2035
d751bb78 2036 void
2037 do_dump_expression(Ast_dump_context*) const;
2038
e440a328 2039 private:
2040 // The integer value.
2041 mpz_t val_;
2042 // The type so far.
2043 Type* type_;
5d4b8566 2044 // Whether this is a character constant.
2045 bool is_character_constant_;
e440a328 2046};
2047
0c77715b 2048// Return a numeric constant for this expression. We have to mark
2049// this as a character when appropriate.
e440a328 2050
2051bool
0c77715b 2052Integer_expression::do_numeric_constant_value(Numeric_constant* nc) const
e440a328 2053{
0c77715b 2054 if (this->is_character_constant_)
2055 nc->set_rune(this->type_, this->val_);
2056 else
2057 nc->set_int(this->type_, this->val_);
e440a328 2058 return true;
2059}
2060
2061// Return the current type. If we haven't set the type yet, we return
2062// an abstract integer type.
2063
2064Type*
2065Integer_expression::do_type()
2066{
2067 if (this->type_ == NULL)
5d4b8566 2068 {
2069 if (this->is_character_constant_)
2070 this->type_ = Type::make_abstract_character_type();
2071 else
2072 this->type_ = Type::make_abstract_integer_type();
2073 }
e440a328 2074 return this->type_;
2075}
2076
2077// Set the type of the integer value. Here we may switch from an
2078// abstract type to a real type.
2079
2080void
2081Integer_expression::do_determine_type(const Type_context* context)
2082{
2083 if (this->type_ != NULL && !this->type_->is_abstract())
2084 ;
0c77715b 2085 else if (context->type != NULL && context->type->is_numeric_type())
e440a328 2086 this->type_ = context->type;
2087 else if (!context->may_be_abstract)
5d4b8566 2088 {
2089 if (this->is_character_constant_)
2090 this->type_ = Type::lookup_integer_type("int32");
2091 else
2092 this->type_ = Type::lookup_integer_type("int");
2093 }
e440a328 2094}
2095
e440a328 2096// Check the type of an integer constant.
2097
2098void
2099Integer_expression::do_check_types(Gogo*)
2100{
0c77715b 2101 Type* type = this->type_;
2102 if (type == NULL)
e440a328 2103 return;
0c77715b 2104 Numeric_constant nc;
2105 if (this->is_character_constant_)
2106 nc.set_rune(NULL, this->val_);
2107 else
2108 nc.set_int(NULL, this->val_);
2109 if (!nc.set_type(type, true, this->location()))
e440a328 2110 this->set_is_error();
2111}
2112
ea664253 2113// Get the backend representation for an integer constant.
e440a328 2114
ea664253 2115Bexpression*
2116Integer_expression::do_get_backend(Translate_context* context)
e440a328 2117{
12373dd5 2118 if (this->is_error_expression()
2119 || (this->type_ != NULL && this->type_->is_error_type()))
2120 {
2121 go_assert(saw_errors());
2122 return context->gogo()->backend()->error_expression();
2123 }
2124
48c2a53a 2125 Type* resolved_type = NULL;
e440a328 2126 if (this->type_ != NULL && !this->type_->is_abstract())
48c2a53a 2127 resolved_type = this->type_;
e440a328 2128 else if (this->type_ != NULL && this->type_->float_type() != NULL)
2129 {
2130 // We are converting to an abstract floating point type.
48c2a53a 2131 resolved_type = Type::lookup_float_type("float64");
e440a328 2132 }
2133 else if (this->type_ != NULL && this->type_->complex_type() != NULL)
2134 {
2135 // We are converting to an abstract complex type.
48c2a53a 2136 resolved_type = Type::lookup_complex_type("complex128");
e440a328 2137 }
2138 else
2139 {
2140 // If we still have an abstract type here, then this is being
2141 // used in a constant expression which didn't get reduced for
2142 // some reason. Use a type which will fit the value. We use <,
2143 // not <=, because we need an extra bit for the sign bit.
2144 int bits = mpz_sizeinbase(this->val_, 2);
1b1f2abf 2145 Type* int_type = Type::lookup_integer_type("int");
2146 if (bits < int_type->integer_type()->bits())
48c2a53a 2147 resolved_type = int_type;
e440a328 2148 else if (bits < 64)
48c2a53a 2149 resolved_type = Type::lookup_integer_type("int64");
e440a328 2150 else
48c2a53a 2151 {
2152 if (!saw_errors())
631d5788 2153 go_error_at(this->location(),
2154 "unknown type for large integer constant");
ea664253 2155 return context->gogo()->backend()->error_expression();
48c2a53a 2156 }
e440a328 2157 }
48c2a53a 2158 Numeric_constant nc;
2159 nc.set_int(resolved_type, this->val_);
ea664253 2160 return Expression::backend_numeric_constant_expression(context, &nc);
e440a328 2161}
2162
2163// Write VAL to export data.
2164
2165void
8b1c301d 2166Integer_expression::export_integer(String_dump* exp, const mpz_t val)
e440a328 2167{
2168 char* s = mpz_get_str(NULL, 10, val);
2169 exp->write_c_string(s);
2170 free(s);
2171}
2172
2173// Export an integer in a constant expression.
2174
2175void
548be246 2176Integer_expression::do_export(Export_function_body* efb) const
e440a328 2177{
69f634cc 2178 bool added_type = false;
2179 if (this->type_ != NULL
2180 && !this->type_->is_abstract()
2181 && this->type_ != efb->type_context())
2182 {
2183 efb->write_c_string("$convert(");
2184 efb->write_type(this->type_);
2185 efb->write_c_string(", ");
2186 added_type = true;
2187 }
2188
548be246 2189 Integer_expression::export_integer(efb, this->val_);
5d4b8566 2190 if (this->is_character_constant_)
548be246 2191 efb->write_c_string("'");
e440a328 2192 // A trailing space lets us reliably identify the end of the number.
548be246 2193 efb->write_c_string(" ");
69f634cc 2194
2195 if (added_type)
2196 efb->write_c_string(")");
e440a328 2197}
2198
2199// Import an integer, floating point, or complex value. This handles
2200// all these types because they all start with digits.
2201
2202Expression*
bc8e2ef4 2203Integer_expression::do_import(Import_expression* imp, Location loc)
e440a328 2204{
2205 std::string num = imp->read_identifier();
2206 imp->require_c_string(" ");
2207 if (!num.empty() && num[num.length() - 1] == 'i')
2208 {
2209 mpfr_t real;
2210 size_t plus_pos = num.find('+', 1);
2211 size_t minus_pos = num.find('-', 1);
2212 size_t pos;
2213 if (plus_pos == std::string::npos)
2214 pos = minus_pos;
2215 else if (minus_pos == std::string::npos)
2216 pos = plus_pos;
2217 else
2218 {
631d5788 2219 go_error_at(imp->location(), "bad number in import data: %qs",
2220 num.c_str());
9b92780c 2221 return Expression::make_error(loc);
e440a328 2222 }
2223 if (pos == std::string::npos)
2224 mpfr_set_ui(real, 0, GMP_RNDN);
2225 else
2226 {
2227 std::string real_str = num.substr(0, pos);
2228 if (mpfr_init_set_str(real, real_str.c_str(), 10, GMP_RNDN) != 0)
2229 {
631d5788 2230 go_error_at(imp->location(), "bad number in import data: %qs",
2231 real_str.c_str());
9b92780c 2232 return Expression::make_error(loc);
e440a328 2233 }
2234 }
2235
2236 std::string imag_str;
2237 if (pos == std::string::npos)
2238 imag_str = num;
2239 else
2240 imag_str = num.substr(pos);
2241 imag_str = imag_str.substr(0, imag_str.size() - 1);
2242 mpfr_t imag;
2243 if (mpfr_init_set_str(imag, imag_str.c_str(), 10, GMP_RNDN) != 0)
2244 {
631d5788 2245 go_error_at(imp->location(), "bad number in import data: %qs",
2246 imag_str.c_str());
9b92780c 2247 return Expression::make_error(loc);
e440a328 2248 }
fcbea5e4 2249 mpc_t cval;
2250 mpc_init2(cval, mpc_precision);
2251 mpc_set_fr_fr(cval, real, imag, MPC_RNDNN);
e440a328 2252 mpfr_clear(real);
2253 mpfr_clear(imag);
9b92780c 2254 Expression* ret = Expression::make_complex(&cval, NULL, loc);
fcbea5e4 2255 mpc_clear(cval);
e440a328 2256 return ret;
2257 }
2258 else if (num.find('.') == std::string::npos
2259 && num.find('E') == std::string::npos)
2260 {
5d4b8566 2261 bool is_character_constant = (!num.empty()
2262 && num[num.length() - 1] == '\'');
2263 if (is_character_constant)
2264 num = num.substr(0, num.length() - 1);
e440a328 2265 mpz_t val;
2266 if (mpz_init_set_str(val, num.c_str(), 10) != 0)
2267 {
631d5788 2268 go_error_at(imp->location(), "bad number in import data: %qs",
2269 num.c_str());
9b92780c 2270 return Expression::make_error(loc);
e440a328 2271 }
5d4b8566 2272 Expression* ret;
2273 if (is_character_constant)
9b92780c 2274 ret = Expression::make_character(&val, NULL, loc);
5d4b8566 2275 else
9b92780c 2276 ret = Expression::make_integer_z(&val, NULL, loc);
e440a328 2277 mpz_clear(val);
2278 return ret;
2279 }
2280 else
2281 {
2282 mpfr_t val;
2283 if (mpfr_init_set_str(val, num.c_str(), 10, GMP_RNDN) != 0)
2284 {
631d5788 2285 go_error_at(imp->location(), "bad number in import data: %qs",
2286 num.c_str());
9b92780c 2287 return Expression::make_error(loc);
e440a328 2288 }
9b92780c 2289 Expression* ret = Expression::make_float(&val, NULL, loc);
e440a328 2290 mpfr_clear(val);
2291 return ret;
2292 }
2293}
d751bb78 2294// Ast dump for integer expression.
2295
2296void
2297Integer_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
2298{
5d4b8566 2299 if (this->is_character_constant_)
2300 ast_dump_context->ostream() << '\'';
8b1c301d 2301 Integer_expression::export_integer(ast_dump_context, this->val_);
5d4b8566 2302 if (this->is_character_constant_)
2303 ast_dump_context->ostream() << '\'';
d751bb78 2304}
2305
e67508fa 2306// Build a new integer value from a multi-precision integer.
e440a328 2307
2308Expression*
e67508fa 2309Expression::make_integer_z(const mpz_t* val, Type* type, Location location)
5d4b8566 2310{
2311 return new Integer_expression(val, type, false, location);
2312}
2313
e67508fa 2314// Build a new integer value from an unsigned long.
2315
2316Expression*
2317Expression::make_integer_ul(unsigned long val, Type *type, Location location)
2318{
2319 mpz_t zval;
2320 mpz_init_set_ui(zval, val);
2321 Expression* ret = Expression::make_integer_z(&zval, type, location);
2322 mpz_clear(zval);
2323 return ret;
2324}
2325
2326// Build a new integer value from a signed long.
2327
2328Expression*
2329Expression::make_integer_sl(long val, Type *type, Location location)
2330{
2331 mpz_t zval;
2332 mpz_init_set_si(zval, val);
2333 Expression* ret = Expression::make_integer_z(&zval, type, location);
2334 mpz_clear(zval);
2335 return ret;
2336}
2337
3f378015 2338// Store an int64_t in an uninitialized mpz_t.
2339
2340static void
2341set_mpz_from_int64(mpz_t* zval, int64_t val)
2342{
2343 if (val >= 0)
2344 {
2345 unsigned long ul = static_cast<unsigned long>(val);
2346 if (static_cast<int64_t>(ul) == val)
2347 {
2348 mpz_init_set_ui(*zval, ul);
2349 return;
2350 }
2351 }
2352 uint64_t uv;
2353 if (val >= 0)
2354 uv = static_cast<uint64_t>(val);
2355 else
2356 uv = static_cast<uint64_t>(- val);
2357 unsigned long ul = uv & 0xffffffffUL;
2358 mpz_init_set_ui(*zval, ul);
2359 mpz_t hval;
2360 mpz_init_set_ui(hval, static_cast<unsigned long>(uv >> 32));
2361 mpz_mul_2exp(hval, hval, 32);
2362 mpz_add(*zval, *zval, hval);
2363 mpz_clear(hval);
2364 if (val < 0)
2365 mpz_neg(*zval, *zval);
2366}
2367
2368// Build a new integer value from an int64_t.
2369
2370Expression*
2371Expression::make_integer_int64(int64_t val, Type* type, Location location)
2372{
2373 mpz_t zval;
2374 set_mpz_from_int64(&zval, val);
2375 Expression* ret = Expression::make_integer_z(&zval, type, location);
2376 mpz_clear(zval);
2377 return ret;
2378}
2379
5d4b8566 2380// Build a new character constant value.
2381
2382Expression*
2383Expression::make_character(const mpz_t* val, Type* type, Location location)
e440a328 2384{
5d4b8566 2385 return new Integer_expression(val, type, true, location);
e440a328 2386}
2387
2388// Floats.
2389
2390class Float_expression : public Expression
2391{
2392 public:
b13c66cd 2393 Float_expression(const mpfr_t* val, Type* type, Location location)
e440a328 2394 : Expression(EXPRESSION_FLOAT, location),
2395 type_(type)
2396 {
2397 mpfr_init_set(this->val_, *val, GMP_RNDN);
2398 }
2399
e440a328 2400 // Write VAL to export data.
2401 static void
8b1c301d 2402 export_float(String_dump* exp, const mpfr_t val);
2403
d751bb78 2404 // Write VAL to dump file.
2405 static void
2406 dump_float(Ast_dump_context* ast_dump_context, const mpfr_t val);
e440a328 2407
2408 protected:
2409 bool
2410 do_is_constant() const
2411 { return true; }
2412
0e168074 2413 bool
3ae06f68 2414 do_is_static_initializer() const
0e168074 2415 { return true; }
2416
e440a328 2417 bool
0c77715b 2418 do_numeric_constant_value(Numeric_constant* nc) const
2419 {
2420 nc->set_float(this->type_, this->val_);
2421 return true;
2422 }
e440a328 2423
2424 Type*
2425 do_type();
2426
2427 void
2428 do_determine_type(const Type_context*);
2429
2430 void
2431 do_check_types(Gogo*);
2432
2433 Expression*
2434 do_copy()
de590a61 2435 { return Expression::make_float(&this->val_,
2436 (this->type_ == NULL
2437 ? NULL
2438 : this->type_->copy_expressions()),
e440a328 2439 this->location()); }
2440
ea664253 2441 Bexpression*
2442 do_get_backend(Translate_context*);
e440a328 2443
5f6f5357 2444 int
2445 do_inlining_cost() const
2446 { return 1; }
2447
e440a328 2448 void
548be246 2449 do_export(Export_function_body*) const;
e440a328 2450
d751bb78 2451 void
2452 do_dump_expression(Ast_dump_context*) const;
2453
e440a328 2454 private:
2455 // The floating point value.
2456 mpfr_t val_;
2457 // The type so far.
2458 Type* type_;
2459};
2460
e440a328 2461// Return the current type. If we haven't set the type yet, we return
2462// an abstract float type.
2463
2464Type*
2465Float_expression::do_type()
2466{
2467 if (this->type_ == NULL)
2468 this->type_ = Type::make_abstract_float_type();
2469 return this->type_;
2470}
2471
2472// Set the type of the float value. Here we may switch from an
2473// abstract type to a real type.
2474
2475void
2476Float_expression::do_determine_type(const Type_context* context)
2477{
2478 if (this->type_ != NULL && !this->type_->is_abstract())
2479 ;
2480 else if (context->type != NULL
2481 && (context->type->integer_type() != NULL
2482 || context->type->float_type() != NULL
2483 || context->type->complex_type() != NULL))
2484 this->type_ = context->type;
2485 else if (!context->may_be_abstract)
48080209 2486 this->type_ = Type::lookup_float_type("float64");
e440a328 2487}
2488
e440a328 2489// Check the type of a float value.
2490
2491void
2492Float_expression::do_check_types(Gogo*)
2493{
0c77715b 2494 Type* type = this->type_;
2495 if (type == NULL)
e440a328 2496 return;
0c77715b 2497 Numeric_constant nc;
2498 nc.set_float(NULL, this->val_);
2499 if (!nc.set_type(this->type_, true, this->location()))
e440a328 2500 this->set_is_error();
e440a328 2501}
2502
ea664253 2503// Get the backend representation for a float constant.
e440a328 2504
ea664253 2505Bexpression*
2506Float_expression::do_get_backend(Translate_context* context)
e440a328 2507{
12373dd5 2508 if (this->is_error_expression()
2509 || (this->type_ != NULL && this->type_->is_error_type()))
2510 {
2511 go_assert(saw_errors());
2512 return context->gogo()->backend()->error_expression();
2513 }
2514
48c2a53a 2515 Type* resolved_type;
e440a328 2516 if (this->type_ != NULL && !this->type_->is_abstract())
48c2a53a 2517 resolved_type = this->type_;
e440a328 2518 else if (this->type_ != NULL && this->type_->integer_type() != NULL)
2519 {
2520 // We have an abstract integer type. We just hope for the best.
48c2a53a 2521 resolved_type = Type::lookup_integer_type("int");
2522 }
2523 else if (this->type_ != NULL && this->type_->complex_type() != NULL)
2524 {
2525 // We are converting to an abstract complex type.
2526 resolved_type = Type::lookup_complex_type("complex128");
e440a328 2527 }
2528 else
2529 {
2530 // If we still have an abstract type here, then this is being
2531 // used in a constant expression which didn't get reduced. We
2532 // just use float64 and hope for the best.
48c2a53a 2533 resolved_type = Type::lookup_float_type("float64");
e440a328 2534 }
48c2a53a 2535
2536 Numeric_constant nc;
2537 nc.set_float(resolved_type, this->val_);
ea664253 2538 return Expression::backend_numeric_constant_expression(context, &nc);
e440a328 2539}
2540
8b1c301d 2541// Write a floating point number to a string dump.
e440a328 2542
2543void
8b1c301d 2544Float_expression::export_float(String_dump *exp, const mpfr_t val)
e440a328 2545{
2546 mp_exp_t exponent;
2547 char* s = mpfr_get_str(NULL, &exponent, 10, 0, val, GMP_RNDN);
2548 if (*s == '-')
2549 exp->write_c_string("-");
2550 exp->write_c_string("0.");
2551 exp->write_c_string(*s == '-' ? s + 1 : s);
2552 mpfr_free_str(s);
2553 char buf[30];
2554 snprintf(buf, sizeof buf, "E%ld", exponent);
2555 exp->write_c_string(buf);
2556}
2557
2558// Export a floating point number in a constant expression.
2559
2560void
548be246 2561Float_expression::do_export(Export_function_body* efb) const
e440a328 2562{
69f634cc 2563 bool added_type = false;
2564 if (this->type_ != NULL
2565 && !this->type_->is_abstract()
2566 && this->type_ != efb->type_context())
2567 {
2568 efb->write_c_string("$convert(");
2569 efb->write_type(this->type_);
2570 efb->write_c_string(", ");
2571 added_type = true;
2572 }
2573
548be246 2574 Float_expression::export_float(efb, this->val_);
e440a328 2575 // A trailing space lets us reliably identify the end of the number.
548be246 2576 efb->write_c_string(" ");
69f634cc 2577
2578 if (added_type)
2579 efb->write_c_string(")");
e440a328 2580}
2581
d751bb78 2582// Dump a floating point number to the dump file.
2583
2584void
2585Float_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
2586{
8b1c301d 2587 Float_expression::export_float(ast_dump_context, this->val_);
d751bb78 2588}
2589
e440a328 2590// Make a float expression.
2591
2592Expression*
b13c66cd 2593Expression::make_float(const mpfr_t* val, Type* type, Location location)
e440a328 2594{
2595 return new Float_expression(val, type, location);
2596}
2597
2598// Complex numbers.
2599
2600class Complex_expression : public Expression
2601{
2602 public:
fcbea5e4 2603 Complex_expression(const mpc_t* val, Type* type, Location location)
e440a328 2604 : Expression(EXPRESSION_COMPLEX, location),
2605 type_(type)
2606 {
fcbea5e4 2607 mpc_init2(this->val_, mpc_precision);
2608 mpc_set(this->val_, *val, MPC_RNDNN);
e440a328 2609 }
2610
fcbea5e4 2611 // Write VAL to string dump.
e440a328 2612 static void
fcbea5e4 2613 export_complex(String_dump* exp, const mpc_t val);
e440a328 2614
d751bb78 2615 // Write REAL/IMAG to dump context.
2616 static void
fcbea5e4 2617 dump_complex(Ast_dump_context* ast_dump_context, const mpc_t val);
d751bb78 2618
e440a328 2619 protected:
2620 bool
2621 do_is_constant() const
2622 { return true; }
2623
0e168074 2624 bool
3ae06f68 2625 do_is_static_initializer() const
0e168074 2626 { return true; }
2627
e440a328 2628 bool
0c77715b 2629 do_numeric_constant_value(Numeric_constant* nc) const
2630 {
fcbea5e4 2631 nc->set_complex(this->type_, this->val_);
0c77715b 2632 return true;
2633 }
e440a328 2634
2635 Type*
2636 do_type();
2637
2638 void
2639 do_determine_type(const Type_context*);
2640
2641 void
2642 do_check_types(Gogo*);
2643
2644 Expression*
2645 do_copy()
2646 {
de590a61 2647 return Expression::make_complex(&this->val_,
2648 (this->type_ == NULL
2649 ? NULL
2650 : this->type_->copy_expressions()),
e440a328 2651 this->location());
2652 }
2653
ea664253 2654 Bexpression*
2655 do_get_backend(Translate_context*);
e440a328 2656
5f6f5357 2657 int
2658 do_inlining_cost() const
2659 { return 2; }
2660
e440a328 2661 void
548be246 2662 do_export(Export_function_body*) const;
e440a328 2663
d751bb78 2664 void
2665 do_dump_expression(Ast_dump_context*) const;
abd26de0 2666
e440a328 2667 private:
fcbea5e4 2668 // The complex value.
2669 mpc_t val_;
e440a328 2670 // The type if known.
2671 Type* type_;
2672};
2673
e440a328 2674// Return the current type. If we haven't set the type yet, we return
2675// an abstract complex type.
2676
2677Type*
2678Complex_expression::do_type()
2679{
2680 if (this->type_ == NULL)
2681 this->type_ = Type::make_abstract_complex_type();
2682 return this->type_;
2683}
2684
2685// Set the type of the complex value. Here we may switch from an
2686// abstract type to a real type.
2687
2688void
2689Complex_expression::do_determine_type(const Type_context* context)
2690{
2691 if (this->type_ != NULL && !this->type_->is_abstract())
2692 ;
abd26de0 2693 else if (context->type != NULL && context->type->is_numeric_type())
e440a328 2694 this->type_ = context->type;
2695 else if (!context->may_be_abstract)
48080209 2696 this->type_ = Type::lookup_complex_type("complex128");
e440a328 2697}
2698
e440a328 2699// Check the type of a complex value.
2700
2701void
2702Complex_expression::do_check_types(Gogo*)
2703{
0c77715b 2704 Type* type = this->type_;
2705 if (type == NULL)
e440a328 2706 return;
0c77715b 2707 Numeric_constant nc;
fcbea5e4 2708 nc.set_complex(NULL, this->val_);
0c77715b 2709 if (!nc.set_type(this->type_, true, this->location()))
e440a328 2710 this->set_is_error();
2711}
2712
ea664253 2713// Get the backend representation for a complex constant.
e440a328 2714
ea664253 2715Bexpression*
2716Complex_expression::do_get_backend(Translate_context* context)
e440a328 2717{
12373dd5 2718 if (this->is_error_expression()
2719 || (this->type_ != NULL && this->type_->is_error_type()))
2720 {
2721 go_assert(saw_errors());
2722 return context->gogo()->backend()->error_expression();
2723 }
2724
48c2a53a 2725 Type* resolved_type;
e440a328 2726 if (this->type_ != NULL && !this->type_->is_abstract())
48c2a53a 2727 resolved_type = this->type_;
2728 else if (this->type_ != NULL && this->type_->integer_type() != NULL)
2729 {
2730 // We are converting to an abstract integer type.
2731 resolved_type = Type::lookup_integer_type("int");
2732 }
2733 else if (this->type_ != NULL && this->type_->float_type() != NULL)
2734 {
2735 // We are converting to an abstract float type.
2736 resolved_type = Type::lookup_float_type("float64");
2737 }
e440a328 2738 else
2739 {
47ae02b7 2740 // If we still have an abstract type here, this is being
e440a328 2741 // used in a constant expression which didn't get reduced. We
2742 // just use complex128 and hope for the best.
48c2a53a 2743 resolved_type = Type::lookup_complex_type("complex128");
e440a328 2744 }
48c2a53a 2745
2746 Numeric_constant nc;
fcbea5e4 2747 nc.set_complex(resolved_type, this->val_);
ea664253 2748 return Expression::backend_numeric_constant_expression(context, &nc);
e440a328 2749}
2750
2751// Write REAL/IMAG to export data.
2752
2753void
fcbea5e4 2754Complex_expression::export_complex(String_dump* exp, const mpc_t val)
e440a328 2755{
fcbea5e4 2756 if (!mpfr_zero_p(mpc_realref(val)))
e440a328 2757 {
fcbea5e4 2758 Float_expression::export_float(exp, mpc_realref(val));
d1db782d 2759 if (mpfr_sgn(mpc_imagref(val)) >= 0)
e440a328 2760 exp->write_c_string("+");
2761 }
fcbea5e4 2762 Float_expression::export_float(exp, mpc_imagref(val));
e440a328 2763 exp->write_c_string("i");
2764}
2765
2766// Export a complex number in a constant expression.
2767
2768void
548be246 2769Complex_expression::do_export(Export_function_body* efb) const
e440a328 2770{
69f634cc 2771 bool added_type = false;
2772 if (this->type_ != NULL
2773 && !this->type_->is_abstract()
2774 && this->type_ != efb->type_context())
2775 {
2776 efb->write_c_string("$convert(");
2777 efb->write_type(this->type_);
2778 efb->write_c_string(", ");
2779 added_type = true;
2780 }
2781
548be246 2782 Complex_expression::export_complex(efb, this->val_);
e440a328 2783 // A trailing space lets us reliably identify the end of the number.
548be246 2784 efb->write_c_string(" ");
69f634cc 2785
2786 if (added_type)
2787 efb->write_c_string(")");
e440a328 2788}
2789
d751bb78 2790// Dump a complex expression to the dump file.
2791
2792void
2793Complex_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
2794{
fcbea5e4 2795 Complex_expression::export_complex(ast_dump_context, this->val_);
d751bb78 2796}
2797
e440a328 2798// Make a complex expression.
2799
2800Expression*
fcbea5e4 2801Expression::make_complex(const mpc_t* val, Type* type, Location location)
e440a328 2802{
fcbea5e4 2803 return new Complex_expression(val, type, location);
e440a328 2804}
2805
d5b605df 2806// Find a named object in an expression.
2807
2808class Find_named_object : public Traverse
2809{
2810 public:
2811 Find_named_object(Named_object* no)
2812 : Traverse(traverse_expressions),
2813 no_(no), found_(false)
2814 { }
2815
2816 // Whether we found the object.
2817 bool
2818 found() const
2819 { return this->found_; }
2820
2821 protected:
2822 int
2823 expression(Expression**);
2824
2825 private:
2826 // The object we are looking for.
2827 Named_object* no_;
2828 // Whether we found it.
2829 bool found_;
2830};
2831
e440a328 2832// A reference to a const in an expression.
2833
2834class Const_expression : public Expression
2835{
2836 public:
b13c66cd 2837 Const_expression(Named_object* constant, Location location)
e440a328 2838 : Expression(EXPRESSION_CONST_REFERENCE, location),
13e818f5 2839 constant_(constant), type_(NULL), seen_(false)
e440a328 2840 { }
2841
d5b605df 2842 Named_object*
2843 named_object()
2844 { return this->constant_; }
2845
a7f064d5 2846 // Check that the initializer does not refer to the constant itself.
2847 void
2848 check_for_init_loop();
2849
e440a328 2850 protected:
ba4aedd4 2851 int
2852 do_traverse(Traverse*);
2853
e440a328 2854 Expression*
ceeb4318 2855 do_lower(Gogo*, Named_object*, Statement_inserter*, int);
e440a328 2856
2857 bool
2858 do_is_constant() const
2859 { return true; }
2860
0e168074 2861 bool
3ae06f68 2862 do_is_static_initializer() const
0e168074 2863 { return true; }
2864
e440a328 2865 bool
0c77715b 2866 do_numeric_constant_value(Numeric_constant* nc) const;
e440a328 2867
2868 bool
af6b489a 2869 do_string_constant_value(std::string* val) const;
e440a328 2870
2871 Type*
2872 do_type();
2873
2874 // The type of a const is set by the declaration, not the use.
2875 void
2876 do_determine_type(const Type_context*);
2877
2878 void
2879 do_check_types(Gogo*);
2880
2881 Expression*
2882 do_copy()
2883 { return this; }
2884
ea664253 2885 Bexpression*
2886 do_get_backend(Translate_context* context);
e440a328 2887
2888 // When exporting a reference to a const as part of a const
2889 // expression, we export the value. We ignore the fact that it has
2890 // a name.
2891 void
548be246 2892 do_export(Export_function_body* efb) const
2893 { this->constant_->const_value()->expr()->export_expression(efb); }
e440a328 2894
d751bb78 2895 void
2896 do_dump_expression(Ast_dump_context*) const;
2897
e440a328 2898 private:
2899 // The constant.
2900 Named_object* constant_;
2901 // The type of this reference. This is used if the constant has an
2902 // abstract type.
2903 Type* type_;
13e818f5 2904 // Used to prevent infinite recursion when a constant incorrectly
2905 // refers to itself.
2906 mutable bool seen_;
e440a328 2907};
2908
ba4aedd4 2909// Traversal.
2910
2911int
2912Const_expression::do_traverse(Traverse* traverse)
2913{
2914 if (this->type_ != NULL)
2915 return Type::traverse(this->type_, traverse);
2916 return TRAVERSE_CONTINUE;
2917}
2918
e440a328 2919// Lower a constant expression. This is where we convert the
2920// predeclared constant iota into an integer value.
2921
2922Expression*
ceeb4318 2923Const_expression::do_lower(Gogo* gogo, Named_object*,
2924 Statement_inserter*, int iota_value)
e440a328 2925{
2926 if (this->constant_->const_value()->expr()->classification()
2927 == EXPRESSION_IOTA)
2928 {
2929 if (iota_value == -1)
2930 {
631d5788 2931 go_error_at(this->location(),
2932 "iota is only defined in const declarations");
e440a328 2933 iota_value = 0;
2934 }
e67508fa 2935 return Expression::make_integer_ul(iota_value, NULL, this->location());
e440a328 2936 }
2937
2938 // Make sure that the constant itself has been lowered.
2939 gogo->lower_constant(this->constant_);
2940
2941 return this;
2942}
2943
0c77715b 2944// Return a numeric constant value.
e440a328 2945
2946bool
0c77715b 2947Const_expression::do_numeric_constant_value(Numeric_constant* nc) const
e440a328 2948{
13e818f5 2949 if (this->seen_)
2950 return false;
2951
e440a328 2952 Expression* e = this->constant_->const_value()->expr();
0c77715b 2953
13e818f5 2954 this->seen_ = true;
2955
0c77715b 2956 bool r = e->numeric_constant_value(nc);
e440a328 2957
13e818f5 2958 this->seen_ = false;
2959
e440a328 2960 Type* ctype;
2961 if (this->type_ != NULL)
2962 ctype = this->type_;
2963 else
2964 ctype = this->constant_->const_value()->type();
e440a328 2965 if (r && ctype != NULL)
2966 {
0c77715b 2967 if (!nc->set_type(ctype, false, this->location()))
e440a328 2968 return false;
e440a328 2969 }
e440a328 2970
e440a328 2971 return r;
2972}
2973
af6b489a 2974bool
2975Const_expression::do_string_constant_value(std::string* val) const
2976{
2977 if (this->seen_)
2978 return false;
2979
2980 Expression* e = this->constant_->const_value()->expr();
2981
2982 this->seen_ = true;
2983 bool ok = e->string_constant_value(val);
2984 this->seen_ = false;
2985
2986 return ok;
2987}
2988
e440a328 2989// Return the type of the const reference.
2990
2991Type*
2992Const_expression::do_type()
2993{
2994 if (this->type_ != NULL)
2995 return this->type_;
13e818f5 2996
2f78f012 2997 Named_constant* nc = this->constant_->const_value();
2998
2999 if (this->seen_ || nc->lowering())
13e818f5 3000 {
4b2ab536 3001 if (nc->type() == NULL || !nc->type()->is_error_type())
3002 {
3003 Location loc = this->location();
3004 if (!this->seen_)
3005 loc = nc->location();
3006 go_error_at(loc, "constant refers to itself");
3007 }
3008 this->set_is_error();
13e818f5 3009 this->type_ = Type::make_error_type();
4b2ab536 3010 nc->set_type(this->type_);
13e818f5 3011 return this->type_;
3012 }
3013
3014 this->seen_ = true;
3015
e440a328 3016 Type* ret = nc->type();
13e818f5 3017
e440a328 3018 if (ret != NULL)
13e818f5 3019 {
3020 this->seen_ = false;
3021 return ret;
3022 }
3023
e440a328 3024 // During parsing, a named constant may have a NULL type, but we
3025 // must not return a NULL type here.
13e818f5 3026 ret = nc->expr()->type();
3027
3028 this->seen_ = false;
3029
4b2ab536 3030 if (ret->is_error_type())
3031 nc->set_type(ret);
3032
13e818f5 3033 return ret;
e440a328 3034}
3035
3036// Set the type of the const reference.
3037
3038void
3039Const_expression::do_determine_type(const Type_context* context)
3040{
3041 Type* ctype = this->constant_->const_value()->type();
3042 Type* cetype = (ctype != NULL
3043 ? ctype
3044 : this->constant_->const_value()->expr()->type());
3045 if (ctype != NULL && !ctype->is_abstract())
3046 ;
3047 else if (context->type != NULL
0c77715b 3048 && context->type->is_numeric_type()
3049 && cetype->is_numeric_type())
e440a328 3050 this->type_ = context->type;
3051 else if (context->type != NULL
3052 && context->type->is_string_type()
3053 && cetype->is_string_type())
3054 this->type_ = context->type;
3055 else if (context->type != NULL
3056 && context->type->is_boolean_type()
3057 && cetype->is_boolean_type())
3058 this->type_ = context->type;
3059 else if (!context->may_be_abstract)
3060 {
3061 if (cetype->is_abstract())
3062 cetype = cetype->make_non_abstract_type();
3063 this->type_ = cetype;
3064 }
3065}
3066
a7f064d5 3067// Check for a loop in which the initializer of a constant refers to
3068// the constant itself.
e440a328 3069
3070void
a7f064d5 3071Const_expression::check_for_init_loop()
e440a328 3072{
5c13bd80 3073 if (this->type_ != NULL && this->type_->is_error())
d5b605df 3074 return;
3075
a7f064d5 3076 if (this->seen_)
3077 {
3078 this->report_error(_("constant refers to itself"));
3079 this->type_ = Type::make_error_type();
3080 return;
3081 }
3082
d5b605df 3083 Expression* init = this->constant_->const_value()->expr();
3084 Find_named_object find_named_object(this->constant_);
a7f064d5 3085
3086 this->seen_ = true;
d5b605df 3087 Expression::traverse(&init, &find_named_object);
a7f064d5 3088 this->seen_ = false;
3089
d5b605df 3090 if (find_named_object.found())
3091 {
5c13bd80 3092 if (this->type_ == NULL || !this->type_->is_error())
a7f064d5 3093 {
3094 this->report_error(_("constant refers to itself"));
3095 this->type_ = Type::make_error_type();
3096 }
d5b605df 3097 return;
3098 }
a7f064d5 3099}
3100
3101// Check types of a const reference.
3102
3103void
3104Const_expression::do_check_types(Gogo*)
3105{
5c13bd80 3106 if (this->type_ != NULL && this->type_->is_error())
a7f064d5 3107 return;
3108
3109 this->check_for_init_loop();
d5b605df 3110
0c77715b 3111 // Check that numeric constant fits in type.
3112 if (this->type_ != NULL && this->type_->is_numeric_type())
e440a328 3113 {
0c77715b 3114 Numeric_constant nc;
3115 if (this->constant_->const_value()->expr()->numeric_constant_value(&nc))
e440a328 3116 {
0c77715b 3117 if (!nc.set_type(this->type_, true, this->location()))
3118 this->set_is_error();
e440a328 3119 }
e440a328 3120 }
3121}
3122
ea664253 3123// Return the backend representation for a const reference.
e440a328 3124
ea664253 3125Bexpression*
3126Const_expression::do_get_backend(Translate_context* context)
e440a328 3127{
12373dd5 3128 if (this->is_error_expression()
3129 || (this->type_ != NULL && this->type_->is_error()))
3130 {
3131 go_assert(saw_errors());
3132 return context->backend()->error_expression();
3133 }
e440a328 3134
3135 // If the type has been set for this expression, but the underlying
3136 // object is an abstract int or float, we try to get the abstract
3137 // value. Otherwise we may lose something in the conversion.
f2de4532 3138 Expression* expr = this->constant_->const_value()->expr();
e440a328 3139 if (this->type_ != NULL
0c77715b 3140 && this->type_->is_numeric_type()
a68492b4 3141 && (this->constant_->const_value()->type() == NULL
3142 || this->constant_->const_value()->type()->is_abstract()))
e440a328 3143 {
0c77715b 3144 Numeric_constant nc;
3145 if (expr->numeric_constant_value(&nc)
3146 && nc.set_type(this->type_, false, this->location()))
e440a328 3147 {
0c77715b 3148 Expression* e = nc.expression(this->location());
ea664253 3149 return e->get_backend(context);
e440a328 3150 }
e440a328 3151 }
3152
2c809f8f 3153 if (this->type_ != NULL)
f2de4532 3154 expr = Expression::make_cast(this->type_, expr, this->location());
ea664253 3155 return expr->get_backend(context);
e440a328 3156}
3157
d751bb78 3158// Dump ast representation for constant expression.
3159
3160void
3161Const_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
3162{
3163 ast_dump_context->ostream() << this->constant_->name();
3164}
3165
e440a328 3166// Make a reference to a constant in an expression.
3167
3168Expression*
3169Expression::make_const_reference(Named_object* constant,
b13c66cd 3170 Location location)
e440a328 3171{
3172 return new Const_expression(constant, location);
3173}
3174
d5b605df 3175// Find a named object in an expression.
3176
3177int
3178Find_named_object::expression(Expression** pexpr)
3179{
3180 switch ((*pexpr)->classification())
3181 {
3182 case Expression::EXPRESSION_CONST_REFERENCE:
a7f064d5 3183 {
3184 Const_expression* ce = static_cast<Const_expression*>(*pexpr);
3185 if (ce->named_object() == this->no_)
3186 break;
3187
3188 // We need to check a constant initializer explicitly, as
3189 // loops here will not be caught by the loop checking for
3190 // variable initializers.
3191 ce->check_for_init_loop();
3192
3193 return TRAVERSE_CONTINUE;
3194 }
3195
d5b605df 3196 case Expression::EXPRESSION_VAR_REFERENCE:
3197 if ((*pexpr)->var_expression()->named_object() == this->no_)
3198 break;
3199 return TRAVERSE_CONTINUE;
3200 case Expression::EXPRESSION_FUNC_REFERENCE:
3201 if ((*pexpr)->func_expression()->named_object() == this->no_)
3202 break;
3203 return TRAVERSE_CONTINUE;
3204 default:
3205 return TRAVERSE_CONTINUE;
3206 }
3207 this->found_ = true;
3208 return TRAVERSE_EXIT;
3209}
3210
e440a328 3211// The nil value.
3212
3213class Nil_expression : public Expression
3214{
3215 public:
b13c66cd 3216 Nil_expression(Location location)
e440a328 3217 : Expression(EXPRESSION_NIL, location)
3218 { }
3219
3220 static Expression*
bc8e2ef4 3221 do_import(Import_expression*, Location);
e440a328 3222
3223 protected:
3224 bool
3225 do_is_constant() const
3226 { return true; }
3227
f9ca30f9 3228 bool
3ae06f68 3229 do_is_static_initializer() const
f9ca30f9 3230 { return true; }
3231
e440a328 3232 Type*
3233 do_type()
3234 { return Type::make_nil_type(); }
3235
3236 void
3237 do_determine_type(const Type_context*)
3238 { }
3239
3240 Expression*
3241 do_copy()
3242 { return this; }
3243
ea664253 3244 Bexpression*
3245 do_get_backend(Translate_context* context)
3246 { return context->backend()->nil_pointer_expression(); }
e440a328 3247
5f6f5357 3248 int
3249 do_inlining_cost() const
3250 { return 1; }
3251
e440a328 3252 void
548be246 3253 do_export(Export_function_body* efb) const
204d4af4 3254 { efb->write_c_string("$nil"); }
d751bb78 3255
3256 void
3257 do_dump_expression(Ast_dump_context* ast_dump_context) const
3258 { ast_dump_context->ostream() << "nil"; }
e440a328 3259};
3260
3261// Import a nil expression.
3262
3263Expression*
bc8e2ef4 3264Nil_expression::do_import(Import_expression* imp, Location loc)
e440a328 3265{
204d4af4 3266 if (imp->version() >= EXPORT_FORMAT_V3)
3267 imp->require_c_string("$");
e440a328 3268 imp->require_c_string("nil");
9b92780c 3269 return Expression::make_nil(loc);
e440a328 3270}
3271
3272// Make a nil expression.
3273
3274Expression*
b13c66cd 3275Expression::make_nil(Location location)
e440a328 3276{
3277 return new Nil_expression(location);
3278}
3279
3280// The value of the predeclared constant iota. This is little more
3281// than a marker. This will be lowered to an integer in
3282// Const_expression::do_lower, which is where we know the value that
3283// it should have.
3284
3285class Iota_expression : public Parser_expression
3286{
3287 public:
b13c66cd 3288 Iota_expression(Location location)
e440a328 3289 : Parser_expression(EXPRESSION_IOTA, location)
3290 { }
3291
3292 protected:
3293 Expression*
ceeb4318 3294 do_lower(Gogo*, Named_object*, Statement_inserter*, int)
c3e6f413 3295 { go_unreachable(); }
e440a328 3296
3297 // There should only ever be one of these.
3298 Expression*
3299 do_copy()
c3e6f413 3300 { go_unreachable(); }
d751bb78 3301
3302 void
3303 do_dump_expression(Ast_dump_context* ast_dump_context) const
3304 { ast_dump_context->ostream() << "iota"; }
e440a328 3305};
3306
3307// Make an iota expression. This is only called for one case: the
3308// value of the predeclared constant iota.
3309
3310Expression*
3311Expression::make_iota()
3312{
b13c66cd 3313 static Iota_expression iota_expression(Linemap::unknown_location());
e440a328 3314 return &iota_expression;
3315}
3316
da244e59 3317// Class Type_conversion_expression.
e440a328 3318
3319// Traversal.
3320
3321int
3322Type_conversion_expression::do_traverse(Traverse* traverse)
3323{
3324 if (Expression::traverse(&this->expr_, traverse) == TRAVERSE_EXIT
3325 || Type::traverse(this->type_, traverse) == TRAVERSE_EXIT)
3326 return TRAVERSE_EXIT;
3327 return TRAVERSE_CONTINUE;
3328}
3329
3330// Convert to a constant at lowering time.
3331
3332Expression*
ceeb4318 3333Type_conversion_expression::do_lower(Gogo*, Named_object*,
3334 Statement_inserter*, int)
e440a328 3335{
3336 Type* type = this->type_;
3337 Expression* val = this->expr_;
b13c66cd 3338 Location location = this->location();
e440a328 3339
0c77715b 3340 if (type->is_numeric_type())
e440a328 3341 {
0c77715b 3342 Numeric_constant nc;
3343 if (val->numeric_constant_value(&nc))
e440a328 3344 {
0c77715b 3345 if (!nc.set_type(type, true, location))
3346 return Expression::make_error(location);
3347 return nc.expression(location);
e440a328 3348 }
e440a328 3349 }
3350
d7739c9a 3351 // According to the language specification on string conversions
3352 // (http://golang.org/ref/spec#Conversions_to_and_from_a_string_type):
3353 // When converting an integer into a string, the string will be a UTF-8
3354 // representation of the integer and integers "outside the range of valid
3355 // Unicode code points are converted to '\uFFFD'."
3356 if (type->is_string_type())
3357 {
3358 Numeric_constant nc;
3359 if (val->numeric_constant_value(&nc) && nc.is_int())
3360 {
3361 // An integer value doesn't fit in the Unicode code point range if it
3362 // overflows the Go "int" type or is negative.
3363 unsigned long ul;
3364 if (!nc.set_type(Type::lookup_integer_type("int"), false, location)
3365 || nc.to_unsigned_long(&ul) == Numeric_constant::NC_UL_NEGATIVE)
3366 return Expression::make_string("\ufffd", location);
3367 }
3368 }
3369
55072f2b 3370 if (type->is_slice_type())
e440a328 3371 {
3372 Type* element_type = type->array_type()->element_type()->forwarded();
60963afd 3373 bool is_byte = (element_type->integer_type() != NULL
3374 && element_type->integer_type()->is_byte());
3375 bool is_rune = (element_type->integer_type() != NULL
3376 && element_type->integer_type()->is_rune());
3377 if (is_byte || is_rune)
e440a328 3378 {
3379 std::string s;
3380 if (val->string_constant_value(&s))
3381 {
3382 Expression_list* vals = new Expression_list();
3383 if (is_byte)
3384 {
3385 for (std::string::const_iterator p = s.begin();
3386 p != s.end();
3387 p++)
3388 {
e67508fa 3389 unsigned char c = static_cast<unsigned char>(*p);
3390 vals->push_back(Expression::make_integer_ul(c,
3391 element_type,
3392 location));
e440a328 3393 }
3394 }
3395 else
3396 {
3397 const char *p = s.data();
3398 const char *pend = s.data() + s.length();
3399 while (p < pend)
3400 {
3401 unsigned int c;
3402 int adv = Lex::fetch_char(p, &c);
3403 if (adv == 0)
3404 {
631d5788 3405 go_warning_at(this->location(), 0,
e440a328 3406 "invalid UTF-8 encoding");
3407 adv = 1;
3408 }
3409 p += adv;
e67508fa 3410 vals->push_back(Expression::make_integer_ul(c,
3411 element_type,
3412 location));
e440a328 3413 }
3414 }
3415
3416 return Expression::make_slice_composite_literal(type, vals,
3417 location);
3418 }
3419 }
3420 }
3421
3422 return this;
3423}
3424
35a54f17 3425// Flatten a type conversion by using a temporary variable for the slice
3426// in slice to string conversions.
3427
3428Expression*
3429Type_conversion_expression::do_flatten(Gogo*, Named_object*,
3430 Statement_inserter* inserter)
3431{
5bf8be8b 3432 if (this->type()->is_error_type() || this->expr_->is_error_expression())
3433 {
3434 go_assert(saw_errors());
3435 return Expression::make_error(this->location());
3436 }
3437
2c809f8f 3438 if (((this->type()->is_string_type()
3439 && this->expr_->type()->is_slice_type())
8ba8cc87 3440 || this->expr_->type()->interface_type() != NULL)
35a54f17 3441 && !this->expr_->is_variable())
3442 {
3443 Temporary_statement* temp =
3444 Statement::make_temporary(NULL, this->expr_, this->location());
3445 inserter->insert(temp);
3446 this->expr_ = Expression::make_temporary_reference(temp, this->location());
3447 }
3448 return this;
3449}
3450
1ca01a59 3451// Return whether a type conversion is a constant.
3452
3453bool
3454Type_conversion_expression::do_is_constant() const
3455{
3456 if (!this->expr_->is_constant())
3457 return false;
3458
3459 // A conversion to a type that may not be used as a constant is not
3460 // a constant. For example, []byte(nil).
3461 Type* type = this->type_;
3462 if (type->integer_type() == NULL
3463 && type->float_type() == NULL
3464 && type->complex_type() == NULL
3465 && !type->is_boolean_type()
3466 && !type->is_string_type())
3467 return false;
3468
3469 return true;
3470}
3471
3ae06f68 3472// Return whether a type conversion can be used in a constant
3473// initializer.
0e168074 3474
3475bool
3ae06f68 3476Type_conversion_expression::do_is_static_initializer() const
0e168074 3477{
3478 Type* type = this->type_;
3479 Type* expr_type = this->expr_->type();
3480
3481 if (type->interface_type() != NULL
3482 || expr_type->interface_type() != NULL)
3483 return false;
3484
3ae06f68 3485 if (!this->expr_->is_static_initializer())
0e168074 3486 return false;
3487
3a522dcc 3488 if (Type::are_identical(type, expr_type,
3489 Type::COMPARE_ERRORS | Type::COMPARE_TAGS,
3490 NULL))
0e168074 3491 return true;
3492
03118c21 3493 if (type->is_string_type() && expr_type->is_string_type())
3494 return true;
3495
3496 if ((type->is_numeric_type()
3497 || type->is_boolean_type()
3498 || type->points_to() != NULL)
3499 && (expr_type->is_numeric_type()
3500 || expr_type->is_boolean_type()
3501 || expr_type->points_to() != NULL))
3502 return true;
3503
3504 return false;
0e168074 3505}
3506
0c77715b 3507// Return the constant numeric value if there is one.
e440a328 3508
3509bool
0c77715b 3510Type_conversion_expression::do_numeric_constant_value(
3511 Numeric_constant* nc) const
e440a328 3512{
0c77715b 3513 if (!this->type_->is_numeric_type())
e440a328 3514 return false;
0c77715b 3515 if (!this->expr_->numeric_constant_value(nc))
e440a328 3516 return false;
0c77715b 3517 return nc->set_type(this->type_, false, this->location());
e440a328 3518}
3519
3520// Return the constant string value if there is one.
3521
3522bool
3523Type_conversion_expression::do_string_constant_value(std::string* val) const
3524{
3525 if (this->type_->is_string_type()
3526 && this->expr_->type()->integer_type() != NULL)
3527 {
0c77715b 3528 Numeric_constant nc;
3529 if (this->expr_->numeric_constant_value(&nc))
e440a328 3530 {
0c77715b 3531 unsigned long ival;
3532 if (nc.to_unsigned_long(&ival) == Numeric_constant::NC_UL_VALID)
e440a328 3533 {
0c77715b 3534 val->clear();
3535 Lex::append_char(ival, true, val, this->location());
e440a328 3536 return true;
3537 }
3538 }
e440a328 3539 }
3540
3541 // FIXME: Could handle conversion from const []int here.
3542
3543 return false;
3544}
3545
da244e59 3546// Determine the resulting type of the conversion.
3547
3548void
3549Type_conversion_expression::do_determine_type(const Type_context*)
3550{
3551 Type_context subcontext(this->type_, false);
3552 this->expr_->determine_type(&subcontext);
3553}
3554
e440a328 3555// Check that types are convertible.
3556
3557void
3558Type_conversion_expression::do_check_types(Gogo*)
3559{
3560 Type* type = this->type_;
3561 Type* expr_type = this->expr_->type();
3562 std::string reason;
3563
5c13bd80 3564 if (type->is_error() || expr_type->is_error())
842f6425 3565 {
842f6425 3566 this->set_is_error();
3567 return;
3568 }
3569
e440a328 3570 if (this->may_convert_function_types_
3571 && type->function_type() != NULL
3572 && expr_type->function_type() != NULL)
3573 return;
3574
3575 if (Type::are_convertible(type, expr_type, &reason))
3576 return;
3577
631d5788 3578 go_error_at(this->location(), "%s", reason.c_str());
e440a328 3579 this->set_is_error();
3580}
3581
de590a61 3582// Copy.
3583
3584Expression*
3585Type_conversion_expression::do_copy()
3586{
3587 return new Type_conversion_expression(this->type_->copy_expressions(),
3588 this->expr_->copy(),
3589 this->location());
3590}
3591
ea664253 3592// Get the backend representation for a type conversion.
e440a328 3593
ea664253 3594Bexpression*
3595Type_conversion_expression::do_get_backend(Translate_context* context)
e440a328 3596{
e440a328 3597 Type* type = this->type_;
3598 Type* expr_type = this->expr_->type();
2c809f8f 3599
3600 Gogo* gogo = context->gogo();
3601 Btype* btype = type->get_backend(gogo);
2c809f8f 3602 Location loc = this->location();
3603
3a522dcc 3604 if (Type::are_identical(type, expr_type,
3605 Type::COMPARE_ERRORS | Type::COMPARE_TAGS,
3606 NULL))
859cdc93 3607 {
3608 Bexpression* bexpr = this->expr_->get_backend(context);
3609 return gogo->backend()->convert_expression(btype, bexpr, loc);
3610 }
2c809f8f 3611 else if (type->interface_type() != NULL
3612 || expr_type->interface_type() != NULL)
e440a328 3613 {
2c809f8f 3614 Expression* conversion =
3615 Expression::convert_for_assignment(gogo, type, this->expr_,
3616 this->location());
ea664253 3617 return conversion->get_backend(context);
e440a328 3618 }
3619 else if (type->is_string_type()
3620 && expr_type->integer_type() != NULL)
3621 {
2c809f8f 3622 mpz_t intval;
3623 Numeric_constant nc;
3624 if (this->expr_->numeric_constant_value(&nc)
3625 && nc.to_int(&intval)
3626 && mpz_fits_ushort_p(intval))
e440a328 3627 {
e440a328 3628 std::string s;
2c809f8f 3629 Lex::append_char(mpz_get_ui(intval), true, &s, loc);
3630 mpz_clear(intval);
3631 Expression* se = Expression::make_string(s, loc);
ea664253 3632 return se->get_backend(context);
e440a328 3633 }
3634
f16ab008 3635 Expression* i2s_expr =
736a16ba 3636 Runtime::make_call(Runtime::INTSTRING, loc, 2,
3637 Expression::make_nil(loc), this->expr_);
ea664253 3638 return Expression::make_cast(type, i2s_expr, loc)->get_backend(context);
e440a328 3639 }
55072f2b 3640 else if (type->is_string_type() && expr_type->is_slice_type())
e440a328 3641 {
55072f2b 3642 Array_type* a = expr_type->array_type();
e440a328 3643 Type* e = a->element_type()->forwarded();
c484d925 3644 go_assert(e->integer_type() != NULL);
35a54f17 3645 go_assert(this->expr_->is_variable());
3646
3647 Runtime::Function code;
60963afd 3648 if (e->integer_type()->is_byte())
736a16ba 3649 code = Runtime::SLICEBYTETOSTRING;
e440a328 3650 else
35a54f17 3651 {
3652 go_assert(e->integer_type()->is_rune());
736a16ba 3653 code = Runtime::SLICERUNETOSTRING;
35a54f17 3654 }
736a16ba 3655 return Runtime::make_call(code, loc, 2, Expression::make_nil(loc),
3656 this->expr_)->get_backend(context);
e440a328 3657 }
411eb89e 3658 else if (type->is_slice_type() && expr_type->is_string_type())
e440a328 3659 {
3660 Type* e = type->array_type()->element_type()->forwarded();
c484d925 3661 go_assert(e->integer_type() != NULL);
6c252e42 3662
2c809f8f 3663 Runtime::Function code;
60963afd 3664 if (e->integer_type()->is_byte())
736a16ba 3665 code = Runtime::STRINGTOSLICEBYTE;
e440a328 3666 else
3667 {
60963afd 3668 go_assert(e->integer_type()->is_rune());
736a16ba 3669 code = Runtime::STRINGTOSLICERUNE;
e440a328 3670 }
736a16ba 3671 Expression* s2a = Runtime::make_call(code, loc, 2,
3672 Expression::make_nil(loc),
3673 this->expr_);
ea664253 3674 return Expression::make_unsafe_cast(type, s2a, loc)->get_backend(context);
2c809f8f 3675 }
3676 else if (type->is_numeric_type())
3677 {
3678 go_assert(Type::are_convertible(type, expr_type, NULL));
859cdc93 3679 Bexpression* bexpr = this->expr_->get_backend(context);
ea664253 3680 return gogo->backend()->convert_expression(btype, bexpr, loc);
e440a328 3681 }
3682 else if ((type->is_unsafe_pointer_type()
2c809f8f 3683 && (expr_type->points_to() != NULL
3684 || expr_type->integer_type()))
3685 || (expr_type->is_unsafe_pointer_type()
3686 && type->points_to() != NULL)
3687 || (this->may_convert_function_types_
3688 && type->function_type() != NULL
3689 && expr_type->function_type() != NULL))
859cdc93 3690 {
3691 Bexpression* bexpr = this->expr_->get_backend(context);
3692 return gogo->backend()->convert_expression(btype, bexpr, loc);
3693 }
e440a328 3694 else
2c809f8f 3695 {
3696 Expression* conversion =
3697 Expression::convert_for_assignment(gogo, type, this->expr_, loc);
ea664253 3698 return conversion->get_backend(context);
2c809f8f 3699 }
e440a328 3700}
3701
5f6f5357 3702// Cost of inlining a type conversion.
3703
3704int
3705Type_conversion_expression::do_inlining_cost() const
3706{
3707 Type* type = this->type_;
3708 Type* expr_type = this->expr_->type();
3709 if (type->interface_type() != NULL || expr_type->interface_type() != NULL)
3710 return 10;
3711 else if (type->is_string_type() && expr_type->integer_type() != NULL)
3712 return 10;
3713 else if (type->is_string_type() && expr_type->is_slice_type())
3714 return 10;
3715 else if (type->is_slice_type() && expr_type->is_string_type())
3716 return 10;
3717 else
3718 return 1;
3719}
3720
e440a328 3721// Output a type conversion in a constant expression.
3722
3723void
548be246 3724Type_conversion_expression::do_export(Export_function_body* efb) const
e440a328 3725{
204d4af4 3726 efb->write_c_string("$convert(");
548be246 3727 efb->write_type(this->type_);
3728 efb->write_c_string(", ");
69f634cc 3729
3730 Type* old_context = efb->type_context();
3731 efb->set_type_context(this->type_);
3732
548be246 3733 this->expr_->export_expression(efb);
69f634cc 3734
3735 efb->set_type_context(old_context);
3736
548be246 3737 efb->write_c_string(")");
e440a328 3738}
3739
3740// Import a type conversion or a struct construction.
3741
3742Expression*
bc8e2ef4 3743Type_conversion_expression::do_import(Import_expression* imp, Location loc)
e440a328 3744{
204d4af4 3745 imp->require_c_string("$convert(");
e440a328 3746 Type* type = imp->read_type();
3747 imp->require_c_string(", ");
9b92780c 3748 Expression* val = Expression::import_expression(imp, loc);
e440a328 3749 imp->require_c_string(")");
9b92780c 3750 return Expression::make_cast(type, val, loc);
e440a328 3751}
3752
d751bb78 3753// Dump ast representation for a type conversion expression.
3754
3755void
3756Type_conversion_expression::do_dump_expression(
3757 Ast_dump_context* ast_dump_context) const
3758{
3759 ast_dump_context->dump_type(this->type_);
3760 ast_dump_context->ostream() << "(";
3761 ast_dump_context->dump_expression(this->expr_);
3762 ast_dump_context->ostream() << ") ";
3763}
3764
e440a328 3765// Make a type cast expression.
3766
3767Expression*
b13c66cd 3768Expression::make_cast(Type* type, Expression* val, Location location)
e440a328 3769{
3770 if (type->is_error_type() || val->is_error_expression())
3771 return Expression::make_error(location);
3772 return new Type_conversion_expression(type, val, location);
3773}
3774
98f62f7a 3775// Class Unsafe_type_conversion_expression.
9581e91d 3776
3777// Traversal.
3778
3779int
3780Unsafe_type_conversion_expression::do_traverse(Traverse* traverse)
3781{
3782 if (Expression::traverse(&this->expr_, traverse) == TRAVERSE_EXIT
3783 || Type::traverse(this->type_, traverse) == TRAVERSE_EXIT)
3784 return TRAVERSE_EXIT;
3785 return TRAVERSE_CONTINUE;
3786}
3787
3ae06f68 3788// Return whether an unsafe type conversion can be used as a constant
3789// initializer.
aa5ae575 3790
3791bool
3ae06f68 3792Unsafe_type_conversion_expression::do_is_static_initializer() const
aa5ae575 3793{
3794 Type* type = this->type_;
3795 Type* expr_type = this->expr_->type();
3796
3797 if (type->interface_type() != NULL
3798 || expr_type->interface_type() != NULL)
3799 return false;
3800
3ae06f68 3801 if (!this->expr_->is_static_initializer())
aa5ae575 3802 return false;
3803
3804 if (Type::are_convertible(type, expr_type, NULL))
3805 return true;
3806
03118c21 3807 if (type->is_string_type() && expr_type->is_string_type())
3808 return true;
3809
3810 if ((type->is_numeric_type()
3811 || type->is_boolean_type()
3812 || type->points_to() != NULL)
3813 && (expr_type->is_numeric_type()
3814 || expr_type->is_boolean_type()
3815 || expr_type->points_to() != NULL))
3816 return true;
3817
3818 return false;
aa5ae575 3819}
3820
de590a61 3821// Copy.
3822
3823Expression*
3824Unsafe_type_conversion_expression::do_copy()
3825{
3826 return new Unsafe_type_conversion_expression(this->type_->copy_expressions(),
3827 this->expr_->copy(),
3828 this->location());
3829}
3830
9581e91d 3831// Convert to backend representation.
3832
ea664253 3833Bexpression*
3834Unsafe_type_conversion_expression::do_get_backend(Translate_context* context)
9581e91d 3835{
3836 // We are only called for a limited number of cases.
3837
3838 Type* t = this->type_;
3839 Type* et = this->expr_->type();
5c4802f1 3840
3841 if (t->is_error_type()
3842 || this->expr_->is_error_expression()
3843 || et->is_error_type())
3844 {
3845 go_assert(saw_errors());
3846 return context->backend()->error_expression();
3847 }
3848
2c809f8f 3849 if (t->array_type() != NULL)
3850 go_assert(et->array_type() != NULL
3851 && t->is_slice_type() == et->is_slice_type());
3852 else if (t->struct_type() != NULL)
9581e91d 3853 {
2c809f8f 3854 if (t->named_type() != NULL
3855 && et->named_type() != NULL
3856 && !Type::are_convertible(t, et, NULL))
3857 {
3858 go_assert(saw_errors());
ea664253 3859 return context->backend()->error_expression();
2c809f8f 3860 }
3861
3862 go_assert(et->struct_type() != NULL
3863 && Type::are_convertible(t, et, NULL));
3864 }
3865 else if (t->map_type() != NULL)
c484d925 3866 go_assert(et->map_type() != NULL);
9581e91d 3867 else if (t->channel_type() != NULL)
c484d925 3868 go_assert(et->channel_type() != NULL);
09ea332d 3869 else if (t->points_to() != NULL)
2c809f8f 3870 go_assert(et->points_to() != NULL
3871 || et->channel_type() != NULL
3872 || et->map_type() != NULL
3873 || et->function_type() != NULL
132ed071 3874 || et->integer_type() != NULL
2c809f8f 3875 || et->is_nil_type());
9581e91d 3876 else if (et->is_unsafe_pointer_type())
c484d925 3877 go_assert(t->points_to() != NULL);
2c809f8f 3878 else if (t->interface_type() != NULL)
9581e91d 3879 {
2c809f8f 3880 bool empty_iface = t->interface_type()->is_empty();
c484d925 3881 go_assert(et->interface_type() != NULL
2c809f8f 3882 && et->interface_type()->is_empty() == empty_iface);
9581e91d 3883 }
588e3cf9 3884 else if (t->integer_type() != NULL)
2c809f8f 3885 go_assert(et->is_boolean_type()
3886 || et->integer_type() != NULL
3887 || et->function_type() != NULL
3888 || et->points_to() != NULL
3889 || et->map_type() != NULL
8ba8cc87 3890 || et->channel_type() != NULL
3891 || et->is_nil_type());
cd39797e 3892 else if (t->function_type() != NULL)
3893 go_assert(et->points_to() != NULL);
9581e91d 3894 else
c3e6f413 3895 go_unreachable();
9581e91d 3896
2c809f8f 3897 Gogo* gogo = context->gogo();
3898 Btype* btype = t->get_backend(gogo);
ea664253 3899 Bexpression* bexpr = this->expr_->get_backend(context);
2c809f8f 3900 Location loc = this->location();
ea664253 3901 return gogo->backend()->convert_expression(btype, bexpr, loc);
9581e91d 3902}
3903
d751bb78 3904// Dump ast representation for an unsafe type conversion expression.
3905
3906void
3907Unsafe_type_conversion_expression::do_dump_expression(
3908 Ast_dump_context* ast_dump_context) const
3909{
3910 ast_dump_context->dump_type(this->type_);
3911 ast_dump_context->ostream() << "(";
3912 ast_dump_context->dump_expression(this->expr_);
3913 ast_dump_context->ostream() << ") ";
3914}
3915
9581e91d 3916// Make an unsafe type conversion expression.
3917
3918Expression*
3919Expression::make_unsafe_cast(Type* type, Expression* expr,
b13c66cd 3920 Location location)
9581e91d 3921{
3922 return new Unsafe_type_conversion_expression(type, expr, location);
3923}
3924
76f85fd6 3925// Class Unary_expression.
e440a328 3926
03118c21 3927// Call the address_taken method of the operand if needed. This is
3928// called after escape analysis but before inserting write barriers.
3929
3930void
c1177ba4 3931Unary_expression::check_operand_address_taken(Gogo*)
03118c21 3932{
3933 if (this->op_ != OPERATOR_AND)
3934 return;
3935
3936 // If this->escapes_ is false at this point, then it was set to
3937 // false by an explicit call to set_does_not_escape, and the value
3938 // does not escape. If this->escapes_ is true, we may be able to
2f86af0a 3939 // set it to false based on the escape analysis pass.
3940 if (this->escapes_)
3941 {
3942 Node* n = Node::make_node(this);
3943 if ((n->encoding() & ESCAPE_MASK) == int(Node::ESCAPE_NONE))
3944 this->escapes_ = false;
03118c21 3945 }
3946
3947 this->expr_->address_taken(this->escapes_);
3948}
3949
e440a328 3950// If we are taking the address of a composite literal, and the
2c809f8f 3951// contents are not constant, then we want to make a heap expression
e440a328 3952// instead.
3953
3954Expression*
ceeb4318 3955Unary_expression::do_lower(Gogo*, Named_object*, Statement_inserter*, int)
e440a328 3956{
b13c66cd 3957 Location loc = this->location();
e440a328 3958 Operator op = this->op_;
3959 Expression* expr = this->expr_;
3960
3961 if (op == OPERATOR_MULT && expr->is_type_expression())
3962 return Expression::make_type(Type::make_pointer_type(expr->type()), loc);
3963
3964 // *&x simplifies to x. *(*T)(unsafe.Pointer)(&x) does not require
3965 // moving x to the heap. FIXME: Is it worth doing a real escape
3966 // analysis here? This case is found in math/unsafe.go and is
3967 // therefore worth special casing.
3968 if (op == OPERATOR_MULT)
3969 {
3970 Expression* e = expr;
3971 while (e->classification() == EXPRESSION_CONVERSION)
3972 {
3973 Type_conversion_expression* te
3974 = static_cast<Type_conversion_expression*>(e);
3975 e = te->expr();
3976 }
3977
3978 if (e->classification() == EXPRESSION_UNARY)
3979 {
3980 Unary_expression* ue = static_cast<Unary_expression*>(e);
3981 if (ue->op_ == OPERATOR_AND)
3982 {
3983 if (e == expr)
3984 {
3985 // *&x == x.
f4dea966 3986 if (!ue->expr_->is_addressable() && !ue->create_temp_)
3987 {
631d5788 3988 go_error_at(ue->location(),
3989 "invalid operand for unary %<&%>");
f4dea966 3990 this->set_is_error();
3991 }
e440a328 3992 return ue->expr_;
3993 }
3994 ue->set_does_not_escape();
3995 }
3996 }
3997 }
3998
55661ce9 3999 // Catching an invalid indirection of unsafe.Pointer here avoid
4000 // having to deal with TYPE_VOID in other places.
4001 if (op == OPERATOR_MULT && expr->type()->is_unsafe_pointer_type())
4002 {
631d5788 4003 go_error_at(this->location(), "invalid indirect of %<unsafe.Pointer%>");
55661ce9 4004 return Expression::make_error(this->location());
4005 }
4006
d9f3743a 4007 // Check for an invalid pointer dereference. We need to do this
4008 // here because Unary_expression::do_type will return an error type
4009 // in this case. That can cause code to appear erroneous, and
4010 // therefore disappear at lowering time, without any error message.
4011 if (op == OPERATOR_MULT && expr->type()->points_to() == NULL)
4012 {
4013 this->report_error(_("expected pointer"));
4014 return Expression::make_error(this->location());
4015 }
4016
59a401fe 4017 if (op == OPERATOR_PLUS || op == OPERATOR_MINUS || op == OPERATOR_XOR)
e440a328 4018 {
0c77715b 4019 Numeric_constant nc;
4020 if (expr->numeric_constant_value(&nc))
e440a328 4021 {
0c77715b 4022 Numeric_constant result;
af7a5274 4023 bool issued_error;
4024 if (Unary_expression::eval_constant(op, &nc, loc, &result,
4025 &issued_error))
0c77715b 4026 return result.expression(loc);
af7a5274 4027 else if (issued_error)
4028 return Expression::make_error(this->location());
e440a328 4029 }
4030 }
4031
4032 return this;
4033}
4034
f9ca30f9 4035// Flatten expression if a nil check must be performed and create temporary
4036// variables if necessary.
4037
4038Expression*
4039Unary_expression::do_flatten(Gogo* gogo, Named_object*,
4040 Statement_inserter* inserter)
4041{
5bf8be8b 4042 if (this->is_error_expression()
4043 || this->expr_->is_error_expression()
4044 || this->expr_->type()->is_error_type())
4045 {
4046 go_assert(saw_errors());
4047 return Expression::make_error(this->location());
4048 }
f4dea966 4049
f9ca30f9 4050 Location location = this->location();
4051 if (this->op_ == OPERATOR_MULT
4052 && !this->expr_->is_variable())
4053 {
4054 go_assert(this->expr_->type()->points_to() != NULL);
f614ea8b 4055 switch (this->requires_nil_check(gogo))
f9ca30f9 4056 {
f614ea8b 4057 case NIL_CHECK_ERROR_ENCOUNTERED:
2a305b85 4058 {
4059 go_assert(saw_errors());
4060 return Expression::make_error(this->location());
4061 }
f614ea8b 4062 case NIL_CHECK_NOT_NEEDED:
4063 break;
4064 case NIL_CHECK_NEEDED:
4065 this->create_temp_ = true;
4066 break;
4067 case NIL_CHECK_DEFAULT:
4068 go_unreachable();
f9ca30f9 4069 }
4070 }
4071
4072 if (this->create_temp_ && !this->expr_->is_variable())
4073 {
4074 Temporary_statement* temp =
4075 Statement::make_temporary(NULL, this->expr_, location);
4076 inserter->insert(temp);
4077 this->expr_ = Expression::make_temporary_reference(temp, location);
4078 }
4079
4080 return this;
4081}
4082
e440a328 4083// Return whether a unary expression is a constant.
4084
4085bool
4086Unary_expression::do_is_constant() const
4087{
4088 if (this->op_ == OPERATOR_MULT)
4089 {
4090 // Indirecting through a pointer is only constant if the object
4091 // to which the expression points is constant, but we currently
4092 // have no way to determine that.
4093 return false;
4094 }
4095 else if (this->op_ == OPERATOR_AND)
4096 {
4097 // Taking the address of a variable is constant if it is a
f9ca30f9 4098 // global variable, not constant otherwise. In other cases taking the
4099 // address is probably not a constant.
e440a328 4100 Var_expression* ve = this->expr_->var_expression();
4101 if (ve != NULL)
4102 {
4103 Named_object* no = ve->named_object();
4104 return no->is_variable() && no->var_value()->is_global();
4105 }
4106 return false;
4107 }
4108 else
4109 return this->expr_->is_constant();
4110}
4111
3ae06f68 4112// Return whether a unary expression can be used as a constant
4113// initializer.
4114
4115bool
4116Unary_expression::do_is_static_initializer() const
4117{
4118 if (this->op_ == OPERATOR_MULT)
4119 return false;
4120 else if (this->op_ == OPERATOR_AND)
de048538 4121 return Unary_expression::base_is_static_initializer(this->expr_);
4122 else
4123 return this->expr_->is_static_initializer();
4124}
3ae06f68 4125
de048538 4126// Return whether the address of EXPR can be used as a static
4127// initializer.
3ae06f68 4128
de048538 4129bool
4130Unary_expression::base_is_static_initializer(Expression* expr)
4131{
4132 // The address of a field reference can be a static initializer if
4133 // the base can be a static initializer.
4134 Field_reference_expression* fre = expr->field_reference_expression();
4135 if (fre != NULL)
4136 return Unary_expression::base_is_static_initializer(fre->expr());
4137
4138 // The address of an index expression can be a static initializer if
4139 // the base can be a static initializer and the index is constant.
4140 Array_index_expression* aind = expr->array_index_expression();
4141 if (aind != NULL)
4142 return (aind->end() == NULL
4143 && aind->start()->is_constant()
4144 && Unary_expression::base_is_static_initializer(aind->array()));
4145
4146 // The address of a global variable can be a static initializer.
4147 Var_expression* ve = expr->var_expression();
4148 if (ve != NULL)
4149 {
4150 Named_object* no = ve->named_object();
4151 return no->is_variable() && no->var_value()->is_global();
4152 }
4153
4154 // The address of a composite literal can be used as a static
4155 // initializer if the composite literal is itself usable as a
4156 // static initializer.
4157 if (expr->is_composite_literal() && expr->is_static_initializer())
4158 return true;
3ae06f68 4159
de048538 4160 // The address of a string constant can be used as a static
4161 // initializer. This can not be written in Go itself but this is
4162 // used when building a type descriptor.
4163 if (expr->string_expression() != NULL)
4164 return true;
4165
4166 return false;
3ae06f68 4167}
4168
f614ea8b 4169// Return whether this dereference expression requires an explicit nil
4170// check. If we are dereferencing the pointer to a large struct
4171// (greater than the specified size threshold), we need to check for
4172// nil. We don't bother to check for small structs because we expect
4173// the system to crash on a nil pointer dereference. However, if we
4174// know the address of this expression is being taken, we must always
4175// check for nil.
4176Unary_expression::Nil_check_classification
4177Unary_expression::requires_nil_check(Gogo* gogo)
4178{
4179 go_assert(this->op_ == OPERATOR_MULT);
4180 go_assert(this->expr_->type()->points_to() != NULL);
4181
4182 if (this->issue_nil_check_ == NIL_CHECK_NEEDED)
4183 return NIL_CHECK_NEEDED;
4184 else if (this->issue_nil_check_ == NIL_CHECK_NOT_NEEDED)
4185 return NIL_CHECK_NOT_NEEDED;
4186
4187 Type* ptype = this->expr_->type()->points_to();
4188 int64_t type_size = -1;
4189 if (!ptype->is_void_type())
4190 {
4191 bool ok = ptype->backend_type_size(gogo, &type_size);
4192 if (!ok)
4193 return NIL_CHECK_ERROR_ENCOUNTERED;
4194 }
4195
4196 int64_t size_cutoff = gogo->nil_check_size_threshold();
4197 if (size_cutoff == -1 || (type_size != -1 && type_size >= size_cutoff))
4198 this->issue_nil_check_ = NIL_CHECK_NEEDED;
4199 else
4200 this->issue_nil_check_ = NIL_CHECK_NOT_NEEDED;
4201 return this->issue_nil_check_;
4202}
4203
0c77715b 4204// Apply unary opcode OP to UNC, setting NC. Return true if this
af7a5274 4205// could be done, false if not. On overflow, issues an error and sets
4206// *ISSUED_ERROR.
e440a328 4207
4208bool
0c77715b 4209Unary_expression::eval_constant(Operator op, const Numeric_constant* unc,
af7a5274 4210 Location location, Numeric_constant* nc,
4211 bool* issued_error)
e440a328 4212{
af7a5274 4213 *issued_error = false;
e440a328 4214 switch (op)
4215 {
4216 case OPERATOR_PLUS:
0c77715b 4217 *nc = *unc;
e440a328 4218 return true;
0c77715b 4219
e440a328 4220 case OPERATOR_MINUS:
0c77715b 4221 if (unc->is_int() || unc->is_rune())
4222 break;
4223 else if (unc->is_float())
4224 {
4225 mpfr_t uval;
4226 unc->get_float(&uval);
4227 mpfr_t val;
4228 mpfr_init(val);
4229 mpfr_neg(val, uval, GMP_RNDN);
4230 nc->set_float(unc->type(), val);
4231 mpfr_clear(uval);
4232 mpfr_clear(val);
4233 return true;
4234 }
4235 else if (unc->is_complex())
4236 {
fcbea5e4 4237 mpc_t uval;
4238 unc->get_complex(&uval);
4239 mpc_t val;
4240 mpc_init2(val, mpc_precision);
4241 mpc_neg(val, uval, MPC_RNDNN);
4242 nc->set_complex(unc->type(), val);
4243 mpc_clear(uval);
4244 mpc_clear(val);
0c77715b 4245 return true;
4246 }
e440a328 4247 else
0c77715b 4248 go_unreachable();
e440a328 4249
0c77715b 4250 case OPERATOR_XOR:
4251 break;
68448d53 4252
59a401fe 4253 case OPERATOR_NOT:
e440a328 4254 case OPERATOR_AND:
4255 case OPERATOR_MULT:
4256 return false;
0c77715b 4257
e440a328 4258 default:
c3e6f413 4259 go_unreachable();
e440a328 4260 }
e440a328 4261
0c77715b 4262 if (!unc->is_int() && !unc->is_rune())
4263 return false;
4264
4265 mpz_t uval;
8387e1df 4266 if (unc->is_rune())
4267 unc->get_rune(&uval);
4268 else
4269 unc->get_int(&uval);
0c77715b 4270 mpz_t val;
4271 mpz_init(val);
e440a328 4272
e440a328 4273 switch (op)
4274 {
e440a328 4275 case OPERATOR_MINUS:
0c77715b 4276 mpz_neg(val, uval);
4277 break;
4278
e440a328 4279 case OPERATOR_NOT:
0c77715b 4280 mpz_set_ui(val, mpz_cmp_si(uval, 0) == 0 ? 1 : 0);
4281 break;
4282
e440a328 4283 case OPERATOR_XOR:
0c77715b 4284 {
4285 Type* utype = unc->type();
4286 if (utype->integer_type() == NULL
4287 || utype->integer_type()->is_abstract())
4288 mpz_com(val, uval);
4289 else
4290 {
4291 // The number of HOST_WIDE_INTs that it takes to represent
4292 // UVAL.
4293 size_t count = ((mpz_sizeinbase(uval, 2)
4294 + HOST_BITS_PER_WIDE_INT
4295 - 1)
4296 / HOST_BITS_PER_WIDE_INT);
e440a328 4297
0c77715b 4298 unsigned HOST_WIDE_INT* phwi = new unsigned HOST_WIDE_INT[count];
4299 memset(phwi, 0, count * sizeof(HOST_WIDE_INT));
4300
4301 size_t obits = utype->integer_type()->bits();
4302
4303 if (!utype->integer_type()->is_unsigned() && mpz_sgn(uval) < 0)
4304 {
4305 mpz_t adj;
4306 mpz_init_set_ui(adj, 1);
4307 mpz_mul_2exp(adj, adj, obits);
4308 mpz_add(uval, uval, adj);
4309 mpz_clear(adj);
4310 }
4311
4312 size_t ecount;
4313 mpz_export(phwi, &ecount, -1, sizeof(HOST_WIDE_INT), 0, 0, uval);
4314 go_assert(ecount <= count);
4315
4316 // Trim down to the number of words required by the type.
4317 size_t ocount = ((obits + HOST_BITS_PER_WIDE_INT - 1)
4318 / HOST_BITS_PER_WIDE_INT);
4319 go_assert(ocount <= count);
4320
4321 for (size_t i = 0; i < ocount; ++i)
4322 phwi[i] = ~phwi[i];
4323
4324 size_t clearbits = ocount * HOST_BITS_PER_WIDE_INT - obits;
4325 if (clearbits != 0)
4326 phwi[ocount - 1] &= (((unsigned HOST_WIDE_INT) (HOST_WIDE_INT) -1)
4327 >> clearbits);
4328
4329 mpz_import(val, ocount, -1, sizeof(HOST_WIDE_INT), 0, 0, phwi);
4330
4331 if (!utype->integer_type()->is_unsigned()
4332 && mpz_tstbit(val, obits - 1))
4333 {
4334 mpz_t adj;
4335 mpz_init_set_ui(adj, 1);
4336 mpz_mul_2exp(adj, adj, obits);
4337 mpz_sub(val, val, adj);
4338 mpz_clear(adj);
4339 }
4340
4341 delete[] phwi;
4342 }
4343 }
4344 break;
e440a328 4345
e440a328 4346 default:
c3e6f413 4347 go_unreachable();
e440a328 4348 }
e440a328 4349
0c77715b 4350 if (unc->is_rune())
4351 nc->set_rune(NULL, val);
e440a328 4352 else
0c77715b 4353 nc->set_int(NULL, val);
e440a328 4354
0c77715b 4355 mpz_clear(uval);
4356 mpz_clear(val);
e440a328 4357
af7a5274 4358 if (!nc->set_type(unc->type(), true, location))
4359 {
4360 *issued_error = true;
4361 return false;
4362 }
4363 return true;
e440a328 4364}
4365
0c77715b 4366// Return the integral constant value of a unary expression, if it has one.
e440a328 4367
4368bool
0c77715b 4369Unary_expression::do_numeric_constant_value(Numeric_constant* nc) const
e440a328 4370{
0c77715b 4371 Numeric_constant unc;
4372 if (!this->expr_->numeric_constant_value(&unc))
4373 return false;
af7a5274 4374 bool issued_error;
0c77715b 4375 return Unary_expression::eval_constant(this->op_, &unc, this->location(),
af7a5274 4376 nc, &issued_error);
e440a328 4377}
4378
4379// Return the type of a unary expression.
4380
4381Type*
4382Unary_expression::do_type()
4383{
4384 switch (this->op_)
4385 {
4386 case OPERATOR_PLUS:
4387 case OPERATOR_MINUS:
4388 case OPERATOR_NOT:
4389 case OPERATOR_XOR:
4390 return this->expr_->type();
4391
4392 case OPERATOR_AND:
4393 return Type::make_pointer_type(this->expr_->type());
4394
4395 case OPERATOR_MULT:
4396 {
4397 Type* subtype = this->expr_->type();
4398 Type* points_to = subtype->points_to();
4399 if (points_to == NULL)
4400 return Type::make_error_type();
4401 return points_to;
4402 }
4403
4404 default:
c3e6f413 4405 go_unreachable();
e440a328 4406 }
4407}
4408
4409// Determine abstract types for a unary expression.
4410
4411void
4412Unary_expression::do_determine_type(const Type_context* context)
4413{
4414 switch (this->op_)
4415 {
4416 case OPERATOR_PLUS:
4417 case OPERATOR_MINUS:
4418 case OPERATOR_NOT:
4419 case OPERATOR_XOR:
4420 this->expr_->determine_type(context);
4421 break;
4422
4423 case OPERATOR_AND:
4424 // Taking the address of something.
4425 {
4426 Type* subtype = (context->type == NULL
4427 ? NULL
4428 : context->type->points_to());
4429 Type_context subcontext(subtype, false);
4430 this->expr_->determine_type(&subcontext);
4431 }
4432 break;
4433
4434 case OPERATOR_MULT:
4435 // Indirecting through a pointer.
4436 {
4437 Type* subtype = (context->type == NULL
4438 ? NULL
4439 : Type::make_pointer_type(context->type));
4440 Type_context subcontext(subtype, false);
4441 this->expr_->determine_type(&subcontext);
4442 }
4443 break;
4444
4445 default:
c3e6f413 4446 go_unreachable();
e440a328 4447 }
4448}
4449
4450// Check types for a unary expression.
4451
4452void
4453Unary_expression::do_check_types(Gogo*)
4454{
9fe897ef 4455 Type* type = this->expr_->type();
5c13bd80 4456 if (type->is_error())
9fe897ef 4457 {
4458 this->set_is_error();
4459 return;
4460 }
4461
e440a328 4462 switch (this->op_)
4463 {
4464 case OPERATOR_PLUS:
4465 case OPERATOR_MINUS:
9fe897ef 4466 if (type->integer_type() == NULL
4467 && type->float_type() == NULL
4468 && type->complex_type() == NULL)
4469 this->report_error(_("expected numeric type"));
e440a328 4470 break;
4471
4472 case OPERATOR_NOT:
59a401fe 4473 if (!type->is_boolean_type())
4474 this->report_error(_("expected boolean type"));
4475 break;
4476
e440a328 4477 case OPERATOR_XOR:
b3b1474e 4478 if (type->integer_type() == NULL)
4479 this->report_error(_("expected integer"));
e440a328 4480 break;
4481
4482 case OPERATOR_AND:
4483 if (!this->expr_->is_addressable())
09ea332d 4484 {
4485 if (!this->create_temp_)
f4dea966 4486 {
631d5788 4487 go_error_at(this->location(), "invalid operand for unary %<&%>");
f4dea966 4488 this->set_is_error();
4489 }
09ea332d 4490 }
e440a328 4491 else
da244e59 4492 this->expr_->issue_nil_check();
e440a328 4493 break;
4494
4495 case OPERATOR_MULT:
4496 // Indirecting through a pointer.
9fe897ef 4497 if (type->points_to() == NULL)
4498 this->report_error(_("expected pointer"));
7661d702 4499 if (type->points_to()->is_error())
4500 this->set_is_error();
e440a328 4501 break;
4502
4503 default:
c3e6f413 4504 go_unreachable();
e440a328 4505 }
4506}
4507
ea664253 4508// Get the backend representation for a unary expression.
e440a328 4509
ea664253 4510Bexpression*
4511Unary_expression::do_get_backend(Translate_context* context)
e440a328 4512{
1b1f2abf 4513 Gogo* gogo = context->gogo();
e9d3367e 4514 Location loc = this->location();
4515
4516 // Taking the address of a set-and-use-temporary expression requires
4517 // setting the temporary and then taking the address.
4518 if (this->op_ == OPERATOR_AND)
4519 {
4520 Set_and_use_temporary_expression* sut =
4521 this->expr_->set_and_use_temporary_expression();
4522 if (sut != NULL)
4523 {
4524 Temporary_statement* temp = sut->temporary();
4525 Bvariable* bvar = temp->get_backend_variable(context);
d4e6573e 4526 Bexpression* bvar_expr =
7af8e400 4527 gogo->backend()->var_expression(bvar, loc);
ea664253 4528 Bexpression* bval = sut->expression()->get_backend(context);
f9ca30f9 4529
0ab48656 4530 Named_object* fn = context->function();
4531 go_assert(fn != NULL);
4532 Bfunction* bfn =
4533 fn->func_value()->get_or_make_decl(gogo, fn);
f9ca30f9 4534 Bstatement* bassign =
0ab48656 4535 gogo->backend()->assignment_statement(bfn, bvar_expr, bval, loc);
f9ca30f9 4536 Bexpression* bvar_addr =
4537 gogo->backend()->address_expression(bvar_expr, loc);
ea664253 4538 return gogo->backend()->compound_expression(bassign, bvar_addr, loc);
e9d3367e 4539 }
4540 }
4541
f9ca30f9 4542 Bexpression* ret;
ea664253 4543 Bexpression* bexpr = this->expr_->get_backend(context);
f9ca30f9 4544 Btype* btype = this->expr_->type()->get_backend(gogo);
e440a328 4545 switch (this->op_)
4546 {
4547 case OPERATOR_PLUS:
f9ca30f9 4548 ret = bexpr;
4549 break;
e440a328 4550
4551 case OPERATOR_MINUS:
f9ca30f9 4552 ret = gogo->backend()->unary_expression(this->op_, bexpr, loc);
4553 ret = gogo->backend()->convert_expression(btype, ret, loc);
4554 break;
e440a328 4555
4556 case OPERATOR_NOT:
e440a328 4557 case OPERATOR_XOR:
f9ca30f9 4558 ret = gogo->backend()->unary_expression(this->op_, bexpr, loc);
4559 break;
e440a328 4560
4561 case OPERATOR_AND:
09ea332d 4562 if (!this->create_temp_)
4563 {
4564 // We should not see a non-constant constructor here; cases
4565 // where we would see one should have been moved onto the
4566 // heap at parse time. Taking the address of a nonconstant
4567 // constructor will not do what the programmer expects.
f9ca30f9 4568
4569 go_assert(!this->expr_->is_composite_literal()
3ae06f68 4570 || this->expr_->is_static_initializer());
24060bf9 4571 if (this->expr_->classification() == EXPRESSION_UNARY)
4572 {
4573 Unary_expression* ue =
4574 static_cast<Unary_expression*>(this->expr_);
4575 go_assert(ue->op() != OPERATOR_AND);
4576 }
09ea332d 4577 }
e440a328 4578
f23d7786 4579 if (this->is_gc_root_ || this->is_slice_init_)
76f85fd6 4580 {
19272321 4581 std::string var_name;
f23d7786 4582 bool copy_to_heap = false;
4583 if (this->is_gc_root_)
4584 {
4585 // Build a decl for a GC root variable. GC roots are mutable, so
4586 // they cannot be represented as an immutable_struct in the
4587 // backend.
19272321 4588 var_name = gogo->gc_root_name();
f23d7786 4589 }
4590 else
4591 {
4592 // Build a decl for a slice value initializer. An immutable slice
4593 // value initializer may have to be copied to the heap if it
4594 // contains pointers in a non-constant context.
19272321 4595 var_name = gogo->initializer_name();
f23d7786 4596
4597 Array_type* at = this->expr_->type()->array_type();
4598 go_assert(at != NULL);
4599
4600 // If we are not copying the value to the heap, we will only
4601 // initialize the value once, so we can use this directly
4602 // rather than copying it. In that case we can't make it
4603 // read-only, because the program is permitted to change it.
ee200713 4604 copy_to_heap = (context->function() != NULL
4605 || context->is_const());
f23d7786 4606 }
19272321 4607 std::string asm_name(go_selectively_encode_id(var_name));
f23d7786 4608 Bvariable* implicit =
19272321 4609 gogo->backend()->implicit_variable(var_name, asm_name,
438b4bec 4610 btype, true, copy_to_heap,
4611 false, 0);
19272321 4612 gogo->backend()->implicit_variable_set_init(implicit, var_name, btype,
aa5ae575 4613 true, copy_to_heap, false,
4614 bexpr);
7af8e400 4615 bexpr = gogo->backend()->var_expression(implicit, loc);
1b4fb1e0 4616
4617 // If we are not copying a slice initializer to the heap,
4618 // then it can be changed by the program, so if it can
4619 // contain pointers we must register it as a GC root.
4620 if (this->is_slice_init_
4621 && !copy_to_heap
4622 && this->expr_->type()->has_pointer())
4623 {
4624 Bexpression* root =
7af8e400 4625 gogo->backend()->var_expression(implicit, loc);
1b4fb1e0 4626 root = gogo->backend()->address_expression(root, loc);
4627 Type* type = Type::make_pointer_type(this->expr_->type());
4628 gogo->add_gc_root(Expression::make_backend(root, type, loc));
4629 }
76f85fd6 4630 }
4631 else if ((this->expr_->is_composite_literal()
3ae06f68 4632 || this->expr_->string_expression() != NULL)
4633 && this->expr_->is_static_initializer())
f9ca30f9 4634 {
19272321 4635 std::string var_name(gogo->initializer_name());
4636 std::string asm_name(go_selectively_encode_id(var_name));
f9ca30f9 4637 Bvariable* decl =
19272321 4638 gogo->backend()->immutable_struct(var_name, asm_name,
438b4bec 4639 true, false, btype, loc);
19272321 4640 gogo->backend()->immutable_struct_set_init(decl, var_name, true,
4641 false, btype, loc, bexpr);
7af8e400 4642 bexpr = gogo->backend()->var_expression(decl, loc);
f9ca30f9 4643 }
09ea332d 4644
f9ca30f9 4645 go_assert(!this->create_temp_ || this->expr_->is_variable());
4646 ret = gogo->backend()->address_expression(bexpr, loc);
4647 break;
e440a328 4648
4649 case OPERATOR_MULT:
4650 {
f9ca30f9 4651 go_assert(this->expr_->type()->points_to() != NULL);
e440a328 4652
f614ea8b 4653 bool known_valid = false;
f9ca30f9 4654 Type* ptype = this->expr_->type()->points_to();
4655 Btype* pbtype = ptype->get_backend(gogo);
f614ea8b 4656 switch (this->requires_nil_check(gogo))
4657 {
4658 case NIL_CHECK_NOT_NEEDED:
4659 break;
4660 case NIL_CHECK_ERROR_ENCOUNTERED:
2a305b85 4661 {
4662 go_assert(saw_errors());
4663 return gogo->backend()->error_expression();
4664 }
f614ea8b 4665 case NIL_CHECK_NEEDED:
4666 {
f9ca30f9 4667 go_assert(this->expr_->is_variable());
2dd89704 4668
4669 // If we're nil-checking the result of a set-and-use-temporary
4670 // expression, then pick out the target temp and use that
4671 // for the final result of the conditional.
4672 Bexpression* tbexpr = bexpr;
4673 Bexpression* ubexpr = bexpr;
4674 Set_and_use_temporary_expression* sut =
4675 this->expr_->set_and_use_temporary_expression();
4676 if (sut != NULL) {
4677 Temporary_statement* temp = sut->temporary();
4678 Bvariable* bvar = temp->get_backend_variable(context);
4679 ubexpr = gogo->backend()->var_expression(bvar, loc);
4680 }
ea664253 4681 Bexpression* nil =
f614ea8b 4682 Expression::make_nil(loc)->get_backend(context);
f9ca30f9 4683 Bexpression* compare =
2dd89704 4684 gogo->backend()->binary_expression(OPERATOR_EQEQ, tbexpr,
f9ca30f9 4685 nil, loc);
f9ca30f9 4686 Bexpression* crash =
f614ea8b 4687 gogo->runtime_error(RUNTIME_ERROR_NIL_DEREFERENCE,
4688 loc)->get_backend(context);
93715b75 4689 Bfunction* bfn = context->function()->func_value()->get_decl();
4690 bexpr = gogo->backend()->conditional_expression(bfn, btype,
4691 compare,
2dd89704 4692 crash, ubexpr,
f9ca30f9 4693 loc);
f614ea8b 4694 known_valid = true;
4695 break;
4696 }
4697 case NIL_CHECK_DEFAULT:
4698 go_unreachable();
4699 }
4700 ret = gogo->backend()->indirect_expression(pbtype, bexpr,
4701 known_valid, loc);
e440a328 4702 }
f9ca30f9 4703 break;
e440a328 4704
4705 default:
c3e6f413 4706 go_unreachable();
e440a328 4707 }
f9ca30f9 4708
ea664253 4709 return ret;
e440a328 4710}
4711
4712// Export a unary expression.
4713
4714void
548be246 4715Unary_expression::do_export(Export_function_body* efb) const
e440a328 4716{
4717 switch (this->op_)
4718 {
4719 case OPERATOR_PLUS:
204d4af4 4720 efb->write_c_string("+");
e440a328 4721 break;
4722 case OPERATOR_MINUS:
204d4af4 4723 efb->write_c_string("-");
e440a328 4724 break;
4725 case OPERATOR_NOT:
204d4af4 4726 efb->write_c_string("!");
e440a328 4727 break;
4728 case OPERATOR_XOR:
204d4af4 4729 efb->write_c_string("^");
e440a328 4730 break;
4731 case OPERATOR_AND:
5f6f5357 4732 efb->write_c_string("&");
4733 break;
e440a328 4734 case OPERATOR_MULT:
5f6f5357 4735 efb->write_c_string("*");
4736 break;
e440a328 4737 default:
c3e6f413 4738 go_unreachable();
e440a328 4739 }
548be246 4740 this->expr_->export_expression(efb);
e440a328 4741}
4742
4743// Import a unary expression.
4744
4745Expression*
bc8e2ef4 4746Unary_expression::do_import(Import_expression* imp, Location loc)
e440a328 4747{
4748 Operator op;
4749 switch (imp->get_char())
4750 {
4751 case '+':
4752 op = OPERATOR_PLUS;
4753 break;
4754 case '-':
4755 op = OPERATOR_MINUS;
4756 break;
4757 case '!':
4758 op = OPERATOR_NOT;
4759 break;
4760 case '^':
4761 op = OPERATOR_XOR;
4762 break;
5f6f5357 4763 case '&':
4764 op = OPERATOR_AND;
4765 break;
4766 case '*':
4767 op = OPERATOR_MULT;
4768 break;
e440a328 4769 default:
c3e6f413 4770 go_unreachable();
e440a328 4771 }
204d4af4 4772 if (imp->version() < EXPORT_FORMAT_V3)
4773 imp->require_c_string(" ");
9b92780c 4774 Expression* expr = Expression::import_expression(imp, loc);
4775 return Expression::make_unary(op, expr, loc);
e440a328 4776}
4777
d751bb78 4778// Dump ast representation of an unary expression.
4779
4780void
4781Unary_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
4782{
4783 ast_dump_context->dump_operator(this->op_);
4784 ast_dump_context->ostream() << "(";
4785 ast_dump_context->dump_expression(this->expr_);
4786 ast_dump_context->ostream() << ") ";
4787}
4788
e440a328 4789// Make a unary expression.
4790
4791Expression*
b13c66cd 4792Expression::make_unary(Operator op, Expression* expr, Location location)
e440a328 4793{
4794 return new Unary_expression(op, expr, location);
4795}
4796
f614ea8b 4797Expression*
4798Expression::make_dereference(Expression* ptr,
4799 Nil_check_classification docheck,
4800 Location location)
4801{
4802 Expression* deref = Expression::make_unary(OPERATOR_MULT, ptr, location);
4803 if (docheck == NIL_CHECK_NEEDED)
4804 deref->unary_expression()->set_requires_nil_check(true);
4805 else if (docheck == NIL_CHECK_NOT_NEEDED)
4806 deref->unary_expression()->set_requires_nil_check(false);
4807 return deref;
4808}
4809
e440a328 4810// If this is an indirection through a pointer, return the expression
4811// being pointed through. Otherwise return this.
4812
4813Expression*
4814Expression::deref()
4815{
4816 if (this->classification_ == EXPRESSION_UNARY)
4817 {
4818 Unary_expression* ue = static_cast<Unary_expression*>(this);
4819 if (ue->op() == OPERATOR_MULT)
4820 return ue->operand();
4821 }
4822 return this;
4823}
4824
4825// Class Binary_expression.
4826
4827// Traversal.
4828
4829int
4830Binary_expression::do_traverse(Traverse* traverse)
4831{
4832 int t = Expression::traverse(&this->left_, traverse);
4833 if (t == TRAVERSE_EXIT)
4834 return TRAVERSE_EXIT;
4835 return Expression::traverse(&this->right_, traverse);
4836}
4837
3ae06f68 4838// Return whether this expression may be used as a static initializer.
4839
4840bool
4841Binary_expression::do_is_static_initializer() const
4842{
4843 if (!this->left_->is_static_initializer()
4844 || !this->right_->is_static_initializer())
4845 return false;
4846
4847 // Addresses can be static initializers, but we can't implement
4848 // arbitray binary expressions of them.
4849 Unary_expression* lu = this->left_->unary_expression();
4850 Unary_expression* ru = this->right_->unary_expression();
4851 if (lu != NULL && lu->op() == OPERATOR_AND)
4852 {
4853 if (ru != NULL && ru->op() == OPERATOR_AND)
4854 return this->op_ == OPERATOR_MINUS;
4855 else
4856 return this->op_ == OPERATOR_PLUS || this->op_ == OPERATOR_MINUS;
4857 }
4858 else if (ru != NULL && ru->op() == OPERATOR_AND)
4859 return this->op_ == OPERATOR_PLUS || this->op_ == OPERATOR_MINUS;
4860
4861 // Other cases should resolve in the backend.
4862 return true;
4863}
4864
0c77715b 4865// Return the type to use for a binary operation on operands of
4866// LEFT_TYPE and RIGHT_TYPE. These are the types of constants and as
4867// such may be NULL or abstract.
4868
4869bool
4870Binary_expression::operation_type(Operator op, Type* left_type,
4871 Type* right_type, Type** result_type)
4872{
4873 if (left_type != right_type
4874 && !left_type->is_abstract()
4875 && !right_type->is_abstract()
4876 && left_type->base() != right_type->base()
4877 && op != OPERATOR_LSHIFT
4878 && op != OPERATOR_RSHIFT)
4879 {
4880 // May be a type error--let it be diagnosed elsewhere.
4881 return false;
4882 }
4883
4884 if (op == OPERATOR_LSHIFT || op == OPERATOR_RSHIFT)
4885 {
4886 if (left_type->integer_type() != NULL)
4887 *result_type = left_type;
4888 else
4889 *result_type = Type::make_abstract_integer_type();
4890 }
4891 else if (!left_type->is_abstract() && left_type->named_type() != NULL)
4892 *result_type = left_type;
4893 else if (!right_type->is_abstract() && right_type->named_type() != NULL)
4894 *result_type = right_type;
4895 else if (!left_type->is_abstract())
4896 *result_type = left_type;
4897 else if (!right_type->is_abstract())
4898 *result_type = right_type;
4899 else if (left_type->complex_type() != NULL)
4900 *result_type = left_type;
4901 else if (right_type->complex_type() != NULL)
4902 *result_type = right_type;
4903 else if (left_type->float_type() != NULL)
4904 *result_type = left_type;
4905 else if (right_type->float_type() != NULL)
4906 *result_type = right_type;
4907 else if (left_type->integer_type() != NULL
4908 && left_type->integer_type()->is_rune())
4909 *result_type = left_type;
4910 else if (right_type->integer_type() != NULL
4911 && right_type->integer_type()->is_rune())
4912 *result_type = right_type;
4913 else
4914 *result_type = left_type;
4915
4916 return true;
4917}
4918
4919// Convert an integer comparison code and an operator to a boolean
4920// value.
e440a328 4921
4922bool
0c77715b 4923Binary_expression::cmp_to_bool(Operator op, int cmp)
e440a328 4924{
e440a328 4925 switch (op)
4926 {
4927 case OPERATOR_EQEQ:
0c77715b 4928 return cmp == 0;
4929 break;
e440a328 4930 case OPERATOR_NOTEQ:
0c77715b 4931 return cmp != 0;
4932 break;
e440a328 4933 case OPERATOR_LT:
0c77715b 4934 return cmp < 0;
4935 break;
e440a328 4936 case OPERATOR_LE:
0c77715b 4937 return cmp <= 0;
e440a328 4938 case OPERATOR_GT:
0c77715b 4939 return cmp > 0;
e440a328 4940 case OPERATOR_GE:
0c77715b 4941 return cmp >= 0;
e440a328 4942 default:
c3e6f413 4943 go_unreachable();
e440a328 4944 }
4945}
4946
0c77715b 4947// Compare constants according to OP.
e440a328 4948
4949bool
0c77715b 4950Binary_expression::compare_constant(Operator op, Numeric_constant* left_nc,
4951 Numeric_constant* right_nc,
4952 Location location, bool* result)
e440a328 4953{
0c77715b 4954 Type* left_type = left_nc->type();
4955 Type* right_type = right_nc->type();
4956
4957 Type* type;
4958 if (!Binary_expression::operation_type(op, left_type, right_type, &type))
4959 return false;
4960
4961 // When comparing an untyped operand to a typed operand, we are
4962 // effectively coercing the untyped operand to the other operand's
4963 // type, so make sure that is valid.
4964 if (!left_nc->set_type(type, true, location)
4965 || !right_nc->set_type(type, true, location))
4966 return false;
4967
4968 bool ret;
4969 int cmp;
4970 if (type->complex_type() != NULL)
4971 {
4972 if (op != OPERATOR_EQEQ && op != OPERATOR_NOTEQ)
4973 return false;
4974 ret = Binary_expression::compare_complex(left_nc, right_nc, &cmp);
4975 }
4976 else if (type->float_type() != NULL)
4977 ret = Binary_expression::compare_float(left_nc, right_nc, &cmp);
e440a328 4978 else
0c77715b 4979 ret = Binary_expression::compare_integer(left_nc, right_nc, &cmp);
4980
4981 if (ret)
4982 *result = Binary_expression::cmp_to_bool(op, cmp);
4983
4984 return ret;
4985}
4986
4987// Compare integer constants.
4988
4989bool
4990Binary_expression::compare_integer(const Numeric_constant* left_nc,
4991 const Numeric_constant* right_nc,
4992 int* cmp)
4993{
4994 mpz_t left_val;
4995 if (!left_nc->to_int(&left_val))
4996 return false;
4997 mpz_t right_val;
4998 if (!right_nc->to_int(&right_val))
e440a328 4999 {
0c77715b 5000 mpz_clear(left_val);
5001 return false;
e440a328 5002 }
0c77715b 5003
5004 *cmp = mpz_cmp(left_val, right_val);
5005
5006 mpz_clear(left_val);
5007 mpz_clear(right_val);
5008
5009 return true;
5010}
5011
5012// Compare floating point constants.
5013
5014bool
5015Binary_expression::compare_float(const Numeric_constant* left_nc,
5016 const Numeric_constant* right_nc,
5017 int* cmp)
5018{
5019 mpfr_t left_val;
5020 if (!left_nc->to_float(&left_val))
5021 return false;
5022 mpfr_t right_val;
5023 if (!right_nc->to_float(&right_val))
e440a328 5024 {
0c77715b 5025 mpfr_clear(left_val);
5026 return false;
5027 }
5028
5029 // We already coerced both operands to the same type. If that type
5030 // is not an abstract type, we need to round the values accordingly.
5031 Type* type = left_nc->type();
5032 if (!type->is_abstract() && type->float_type() != NULL)
5033 {
5034 int bits = type->float_type()->bits();
5035 mpfr_prec_round(left_val, bits, GMP_RNDN);
5036 mpfr_prec_round(right_val, bits, GMP_RNDN);
e440a328 5037 }
0c77715b 5038
5039 *cmp = mpfr_cmp(left_val, right_val);
5040
5041 mpfr_clear(left_val);
5042 mpfr_clear(right_val);
5043
5044 return true;
e440a328 5045}
5046
0c77715b 5047// Compare complex constants. Complex numbers may only be compared
5048// for equality.
e440a328 5049
5050bool
0c77715b 5051Binary_expression::compare_complex(const Numeric_constant* left_nc,
5052 const Numeric_constant* right_nc,
5053 int* cmp)
e440a328 5054{
fcbea5e4 5055 mpc_t left_val;
5056 if (!left_nc->to_complex(&left_val))
0c77715b 5057 return false;
fcbea5e4 5058 mpc_t right_val;
5059 if (!right_nc->to_complex(&right_val))
e440a328 5060 {
fcbea5e4 5061 mpc_clear(left_val);
0c77715b 5062 return false;
e440a328 5063 }
0c77715b 5064
5065 // We already coerced both operands to the same type. If that type
5066 // is not an abstract type, we need to round the values accordingly.
5067 Type* type = left_nc->type();
5068 if (!type->is_abstract() && type->complex_type() != NULL)
e440a328 5069 {
0c77715b 5070 int bits = type->complex_type()->bits();
fcbea5e4 5071 mpfr_prec_round(mpc_realref(left_val), bits / 2, GMP_RNDN);
5072 mpfr_prec_round(mpc_imagref(left_val), bits / 2, GMP_RNDN);
5073 mpfr_prec_round(mpc_realref(right_val), bits / 2, GMP_RNDN);
5074 mpfr_prec_round(mpc_imagref(right_val), bits / 2, GMP_RNDN);
e440a328 5075 }
0c77715b 5076
fcbea5e4 5077 *cmp = mpc_cmp(left_val, right_val) != 0;
0c77715b 5078
fcbea5e4 5079 mpc_clear(left_val);
5080 mpc_clear(right_val);
0c77715b 5081
5082 return true;
e440a328 5083}
5084
0c77715b 5085// Apply binary opcode OP to LEFT_NC and RIGHT_NC, setting NC. Return
5086// true if this could be done, false if not. Issue errors at LOCATION
af7a5274 5087// as appropriate, and sets *ISSUED_ERROR if it did.
e440a328 5088
5089bool
0c77715b 5090Binary_expression::eval_constant(Operator op, Numeric_constant* left_nc,
5091 Numeric_constant* right_nc,
af7a5274 5092 Location location, Numeric_constant* nc,
5093 bool* issued_error)
e440a328 5094{
af7a5274 5095 *issued_error = false;
e440a328 5096 switch (op)
5097 {
5098 case OPERATOR_OROR:
5099 case OPERATOR_ANDAND:
5100 case OPERATOR_EQEQ:
5101 case OPERATOR_NOTEQ:
5102 case OPERATOR_LT:
5103 case OPERATOR_LE:
5104 case OPERATOR_GT:
5105 case OPERATOR_GE:
9767e2d3 5106 // These return boolean values, not numeric.
5107 return false;
0c77715b 5108 default:
5109 break;
5110 }
5111
5112 Type* left_type = left_nc->type();
5113 Type* right_type = right_nc->type();
5114
5115 Type* type;
5116 if (!Binary_expression::operation_type(op, left_type, right_type, &type))
5117 return false;
5118
5119 bool is_shift = op == OPERATOR_LSHIFT || op == OPERATOR_RSHIFT;
5120
5121 // When combining an untyped operand with a typed operand, we are
5122 // effectively coercing the untyped operand to the other operand's
5123 // type, so make sure that is valid.
5124 if (!left_nc->set_type(type, true, location))
5125 return false;
5126 if (!is_shift && !right_nc->set_type(type, true, location))
5127 return false;
85334a21 5128 if (is_shift
5129 && ((left_type->integer_type() == NULL
5130 && !left_type->is_abstract())
5131 || (right_type->integer_type() == NULL
5132 && !right_type->is_abstract())))
5133 return false;
0c77715b 5134
5135 bool r;
5136 if (type->complex_type() != NULL)
5137 r = Binary_expression::eval_complex(op, left_nc, right_nc, location, nc);
5138 else if (type->float_type() != NULL)
5139 r = Binary_expression::eval_float(op, left_nc, right_nc, location, nc);
5140 else
5141 r = Binary_expression::eval_integer(op, left_nc, right_nc, location, nc);
5142
5143 if (r)
af7a5274 5144 {
5145 r = nc->set_type(type, true, location);
5146 if (!r)
5147 *issued_error = true;
5148 }
0c77715b 5149
5150 return r;
5151}
5152
5153// Apply binary opcode OP to LEFT_NC and RIGHT_NC, setting NC, using
5154// integer operations. Return true if this could be done, false if
5155// not.
5156
5157bool
5158Binary_expression::eval_integer(Operator op, const Numeric_constant* left_nc,
5159 const Numeric_constant* right_nc,
5160 Location location, Numeric_constant* nc)
5161{
5162 mpz_t left_val;
5163 if (!left_nc->to_int(&left_val))
5164 return false;
5165 mpz_t right_val;
5166 if (!right_nc->to_int(&right_val))
5167 {
5168 mpz_clear(left_val);
e440a328 5169 return false;
0c77715b 5170 }
5171
5172 mpz_t val;
5173 mpz_init(val);
5174
5175 switch (op)
5176 {
e440a328 5177 case OPERATOR_PLUS:
5178 mpz_add(val, left_val, right_val);
2c809f8f 5179 if (mpz_sizeinbase(val, 2) > 0x100000)
5180 {
631d5788 5181 go_error_at(location, "constant addition overflow");
71a45216 5182 nc->set_invalid();
2c809f8f 5183 mpz_set_ui(val, 1);
5184 }
e440a328 5185 break;
5186 case OPERATOR_MINUS:
5187 mpz_sub(val, left_val, right_val);
2c809f8f 5188 if (mpz_sizeinbase(val, 2) > 0x100000)
5189 {
631d5788 5190 go_error_at(location, "constant subtraction overflow");
71a45216 5191 nc->set_invalid();
2c809f8f 5192 mpz_set_ui(val, 1);
5193 }
e440a328 5194 break;
5195 case OPERATOR_OR:
5196 mpz_ior(val, left_val, right_val);
5197 break;
5198 case OPERATOR_XOR:
5199 mpz_xor(val, left_val, right_val);
5200 break;
5201 case OPERATOR_MULT:
5202 mpz_mul(val, left_val, right_val);
2c809f8f 5203 if (mpz_sizeinbase(val, 2) > 0x100000)
5204 {
631d5788 5205 go_error_at(location, "constant multiplication overflow");
71a45216 5206 nc->set_invalid();
2c809f8f 5207 mpz_set_ui(val, 1);
5208 }
e440a328 5209 break;
5210 case OPERATOR_DIV:
5211 if (mpz_sgn(right_val) != 0)
5212 mpz_tdiv_q(val, left_val, right_val);
5213 else
5214 {
631d5788 5215 go_error_at(location, "division by zero");
71a45216 5216 nc->set_invalid();
e440a328 5217 mpz_set_ui(val, 0);
e440a328 5218 }
5219 break;
5220 case OPERATOR_MOD:
5221 if (mpz_sgn(right_val) != 0)
5222 mpz_tdiv_r(val, left_val, right_val);
5223 else
5224 {
631d5788 5225 go_error_at(location, "division by zero");
71a45216 5226 nc->set_invalid();
e440a328 5227 mpz_set_ui(val, 0);
e440a328 5228 }
5229 break;
5230 case OPERATOR_LSHIFT:
5231 {
5232 unsigned long shift = mpz_get_ui(right_val);
0c77715b 5233 if (mpz_cmp_ui(right_val, shift) == 0 && shift <= 0x100000)
5234 mpz_mul_2exp(val, left_val, shift);
5235 else
e440a328 5236 {
631d5788 5237 go_error_at(location, "shift count overflow");
71a45216 5238 nc->set_invalid();
2c809f8f 5239 mpz_set_ui(val, 1);
e440a328 5240 }
e440a328 5241 break;
5242 }
5243 break;
5244 case OPERATOR_RSHIFT:
5245 {
5246 unsigned long shift = mpz_get_ui(right_val);
5247 if (mpz_cmp_ui(right_val, shift) != 0)
5248 {
631d5788 5249 go_error_at(location, "shift count overflow");
71a45216 5250 nc->set_invalid();
2c809f8f 5251 mpz_set_ui(val, 1);
e440a328 5252 }
e440a328 5253 else
0c77715b 5254 {
5255 if (mpz_cmp_ui(left_val, 0) >= 0)
5256 mpz_tdiv_q_2exp(val, left_val, shift);
5257 else
5258 mpz_fdiv_q_2exp(val, left_val, shift);
5259 }
e440a328 5260 break;
5261 }
5262 break;
5263 case OPERATOR_AND:
5264 mpz_and(val, left_val, right_val);
5265 break;
5266 case OPERATOR_BITCLEAR:
5267 {
5268 mpz_t tval;
5269 mpz_init(tval);
5270 mpz_com(tval, right_val);
5271 mpz_and(val, left_val, tval);
5272 mpz_clear(tval);
5273 }
5274 break;
5275 default:
c3e6f413 5276 go_unreachable();
e440a328 5277 }
5278
0c77715b 5279 mpz_clear(left_val);
5280 mpz_clear(right_val);
e440a328 5281
0c77715b 5282 if (left_nc->is_rune()
5283 || (op != OPERATOR_LSHIFT
5284 && op != OPERATOR_RSHIFT
5285 && right_nc->is_rune()))
5286 nc->set_rune(NULL, val);
5287 else
5288 nc->set_int(NULL, val);
5289
5290 mpz_clear(val);
e440a328 5291
5292 return true;
5293}
5294
0c77715b 5295// Apply binary opcode OP to LEFT_NC and RIGHT_NC, setting NC, using
5296// floating point operations. Return true if this could be done,
5297// false if not.
e440a328 5298
5299bool
0c77715b 5300Binary_expression::eval_float(Operator op, const Numeric_constant* left_nc,
5301 const Numeric_constant* right_nc,
5302 Location location, Numeric_constant* nc)
e440a328 5303{
0c77715b 5304 mpfr_t left_val;
5305 if (!left_nc->to_float(&left_val))
5306 return false;
5307 mpfr_t right_val;
5308 if (!right_nc->to_float(&right_val))
e440a328 5309 {
0c77715b 5310 mpfr_clear(left_val);
e440a328 5311 return false;
0c77715b 5312 }
5313
5314 mpfr_t val;
5315 mpfr_init(val);
5316
5317 bool ret = true;
5318 switch (op)
5319 {
e440a328 5320 case OPERATOR_PLUS:
5321 mpfr_add(val, left_val, right_val, GMP_RNDN);
5322 break;
5323 case OPERATOR_MINUS:
5324 mpfr_sub(val, left_val, right_val, GMP_RNDN);
5325 break;
5326 case OPERATOR_OR:
5327 case OPERATOR_XOR:
5328 case OPERATOR_AND:
5329 case OPERATOR_BITCLEAR:
0c77715b 5330 case OPERATOR_MOD:
5331 case OPERATOR_LSHIFT:
5332 case OPERATOR_RSHIFT:
5333 mpfr_set_ui(val, 0, GMP_RNDN);
5334 ret = false;
5335 break;
e440a328 5336 case OPERATOR_MULT:
5337 mpfr_mul(val, left_val, right_val, GMP_RNDN);
5338 break;
5339 case OPERATOR_DIV:
0c77715b 5340 if (!mpfr_zero_p(right_val))
5341 mpfr_div(val, left_val, right_val, GMP_RNDN);
5342 else
5343 {
631d5788 5344 go_error_at(location, "division by zero");
71a45216 5345 nc->set_invalid();
0c77715b 5346 mpfr_set_ui(val, 0, GMP_RNDN);
5347 }
e440a328 5348 break;
e440a328 5349 default:
c3e6f413 5350 go_unreachable();
e440a328 5351 }
5352
0c77715b 5353 mpfr_clear(left_val);
5354 mpfr_clear(right_val);
e440a328 5355
0c77715b 5356 nc->set_float(NULL, val);
5357 mpfr_clear(val);
e440a328 5358
0c77715b 5359 return ret;
e440a328 5360}
5361
0c77715b 5362// Apply binary opcode OP to LEFT_NC and RIGHT_NC, setting NC, using
5363// complex operations. Return true if this could be done, false if
5364// not.
e440a328 5365
5366bool
0c77715b 5367Binary_expression::eval_complex(Operator op, const Numeric_constant* left_nc,
5368 const Numeric_constant* right_nc,
5369 Location location, Numeric_constant* nc)
e440a328 5370{
fcbea5e4 5371 mpc_t left_val;
5372 if (!left_nc->to_complex(&left_val))
0c77715b 5373 return false;
fcbea5e4 5374 mpc_t right_val;
5375 if (!right_nc->to_complex(&right_val))
e440a328 5376 {
fcbea5e4 5377 mpc_clear(left_val);
e440a328 5378 return false;
0c77715b 5379 }
5380
fcbea5e4 5381 mpc_t val;
5382 mpc_init2(val, mpc_precision);
0c77715b 5383
5384 bool ret = true;
5385 switch (op)
5386 {
e440a328 5387 case OPERATOR_PLUS:
fcbea5e4 5388 mpc_add(val, left_val, right_val, MPC_RNDNN);
e440a328 5389 break;
5390 case OPERATOR_MINUS:
fcbea5e4 5391 mpc_sub(val, left_val, right_val, MPC_RNDNN);
e440a328 5392 break;
5393 case OPERATOR_OR:
5394 case OPERATOR_XOR:
5395 case OPERATOR_AND:
5396 case OPERATOR_BITCLEAR:
0c77715b 5397 case OPERATOR_MOD:
5398 case OPERATOR_LSHIFT:
5399 case OPERATOR_RSHIFT:
fcbea5e4 5400 mpc_set_ui(val, 0, MPC_RNDNN);
0c77715b 5401 ret = false;
5402 break;
e440a328 5403 case OPERATOR_MULT:
fcbea5e4 5404 mpc_mul(val, left_val, right_val, MPC_RNDNN);
e440a328 5405 break;
5406 case OPERATOR_DIV:
fcbea5e4 5407 if (mpc_cmp_si(right_val, 0) == 0)
5408 {
631d5788 5409 go_error_at(location, "division by zero");
71a45216 5410 nc->set_invalid();
fcbea5e4 5411 mpc_set_ui(val, 0, MPC_RNDNN);
5412 break;
5413 }
5414 mpc_div(val, left_val, right_val, MPC_RNDNN);
e440a328 5415 break;
e440a328 5416 default:
c3e6f413 5417 go_unreachable();
e440a328 5418 }
5419
fcbea5e4 5420 mpc_clear(left_val);
5421 mpc_clear(right_val);
e440a328 5422
fcbea5e4 5423 nc->set_complex(NULL, val);
5424 mpc_clear(val);
e440a328 5425
0c77715b 5426 return ret;
e440a328 5427}
5428
5429// Lower a binary expression. We have to evaluate constant
5430// expressions now, in order to implement Go's unlimited precision
5431// constants.
5432
5433Expression*
e9d3367e 5434Binary_expression::do_lower(Gogo* gogo, Named_object*,
5435 Statement_inserter* inserter, int)
e440a328 5436{
b13c66cd 5437 Location location = this->location();
e440a328 5438 Operator op = this->op_;
5439 Expression* left = this->left_;
5440 Expression* right = this->right_;
5441
5442 const bool is_comparison = (op == OPERATOR_EQEQ
5443 || op == OPERATOR_NOTEQ
5444 || op == OPERATOR_LT
5445 || op == OPERATOR_LE
5446 || op == OPERATOR_GT
5447 || op == OPERATOR_GE);
5448
0c77715b 5449 // Numeric constant expressions.
e440a328 5450 {
0c77715b 5451 Numeric_constant left_nc;
5452 Numeric_constant right_nc;
5453 if (left->numeric_constant_value(&left_nc)
5454 && right->numeric_constant_value(&right_nc))
e440a328 5455 {
0c77715b 5456 if (is_comparison)
e440a328 5457 {
0c77715b 5458 bool result;
5459 if (!Binary_expression::compare_constant(op, &left_nc,
5460 &right_nc, location,
5461 &result))
5462 return this;
e90c9dfc 5463 return Expression::make_cast(Type::make_boolean_type(),
0c77715b 5464 Expression::make_boolean(result,
5465 location),
5466 location);
e440a328 5467 }
5468 else
5469 {
0c77715b 5470 Numeric_constant nc;
af7a5274 5471 bool issued_error;
0c77715b 5472 if (!Binary_expression::eval_constant(op, &left_nc, &right_nc,
af7a5274 5473 location, &nc,
5474 &issued_error))
5475 {
5476 if (issued_error)
5477 return Expression::make_error(location);
71a45216 5478 return this;
af7a5274 5479 }
0c77715b 5480 return nc.expression(location);
e440a328 5481 }
5482 }
e440a328 5483 }
5484
5485 // String constant expressions.
315fa98d 5486 if (left->type()->is_string_type() && right->type()->is_string_type())
e440a328 5487 {
5488 std::string left_string;
5489 std::string right_string;
5490 if (left->string_constant_value(&left_string)
5491 && right->string_constant_value(&right_string))
315fa98d 5492 {
5493 if (op == OPERATOR_PLUS)
5494 return Expression::make_string(left_string + right_string,
5495 location);
5496 else if (is_comparison)
5497 {
5498 int cmp = left_string.compare(right_string);
0c77715b 5499 bool r = Binary_expression::cmp_to_bool(op, cmp);
e90c9dfc 5500 return Expression::make_boolean(r, location);
b40dc774 5501 }
5502 }
b40dc774 5503 }
5504
ceeb12d7 5505 // Lower struct, array, and some interface comparisons.
e9d3367e 5506 if (op == OPERATOR_EQEQ || op == OPERATOR_NOTEQ)
5507 {
b79832ca 5508 if (left->type()->struct_type() != NULL
5509 && right->type()->struct_type() != NULL)
e9d3367e 5510 return this->lower_struct_comparison(gogo, inserter);
5511 else if (left->type()->array_type() != NULL
b79832ca 5512 && !left->type()->is_slice_type()
5513 && right->type()->array_type() != NULL
5514 && !right->type()->is_slice_type())
e9d3367e 5515 return this->lower_array_comparison(gogo, inserter);
ceeb12d7 5516 else if ((left->type()->interface_type() != NULL
5517 && right->type()->interface_type() == NULL)
5518 || (left->type()->interface_type() == NULL
5519 && right->type()->interface_type() != NULL))
5520 return this->lower_interface_value_comparison(gogo, inserter);
e9d3367e 5521 }
5522
736a16ba 5523 // Lower string concatenation to String_concat_expression, so that
5524 // we can group sequences of string additions.
5525 if (this->left_->type()->is_string_type() && this->op_ == OPERATOR_PLUS)
5526 {
5527 Expression_list* exprs;
5528 String_concat_expression* left_sce =
5529 this->left_->string_concat_expression();
5530 if (left_sce != NULL)
5531 exprs = left_sce->exprs();
5532 else
5533 {
5534 exprs = new Expression_list();
5535 exprs->push_back(this->left_);
5536 }
5537
5538 String_concat_expression* right_sce =
5539 this->right_->string_concat_expression();
5540 if (right_sce != NULL)
5541 exprs->append(right_sce->exprs());
5542 else
5543 exprs->push_back(this->right_);
5544
5545 return Expression::make_string_concat(exprs);
5546 }
5547
e440a328 5548 return this;
5549}
5550
e9d3367e 5551// Lower a struct comparison.
5552
5553Expression*
5554Binary_expression::lower_struct_comparison(Gogo* gogo,
5555 Statement_inserter* inserter)
5556{
5557 Struct_type* st = this->left_->type()->struct_type();
5558 Struct_type* st2 = this->right_->type()->struct_type();
5559 if (st2 == NULL)
5560 return this;
3a522dcc 5561 if (st != st2
5562 && !Type::are_identical(st, st2,
5563 Type::COMPARE_ERRORS | Type::COMPARE_TAGS,
5564 NULL))
e9d3367e 5565 return this;
5566 if (!Type::are_compatible_for_comparison(true, this->left_->type(),
5567 this->right_->type(), NULL))
5568 return this;
5569
5570 // See if we can compare using memcmp. As a heuristic, we use
5571 // memcmp rather than field references and comparisons if there are
5572 // more than two fields.
113ef6a5 5573 if (st->compare_is_identity(gogo) && st->total_field_count() > 2)
e9d3367e 5574 return this->lower_compare_to_memcmp(gogo, inserter);
5575
5576 Location loc = this->location();
5577
5578 Expression* left = this->left_;
5579 Temporary_statement* left_temp = NULL;
5580 if (left->var_expression() == NULL
5581 && left->temporary_reference_expression() == NULL)
5582 {
5583 left_temp = Statement::make_temporary(left->type(), NULL, loc);
5584 inserter->insert(left_temp);
5585 left = Expression::make_set_and_use_temporary(left_temp, left, loc);
5586 }
5587
5588 Expression* right = this->right_;
5589 Temporary_statement* right_temp = NULL;
5590 if (right->var_expression() == NULL
5591 && right->temporary_reference_expression() == NULL)
5592 {
5593 right_temp = Statement::make_temporary(right->type(), NULL, loc);
5594 inserter->insert(right_temp);
5595 right = Expression::make_set_and_use_temporary(right_temp, right, loc);
5596 }
5597
5598 Expression* ret = Expression::make_boolean(true, loc);
5599 const Struct_field_list* fields = st->fields();
5600 unsigned int field_index = 0;
5601 for (Struct_field_list::const_iterator pf = fields->begin();
5602 pf != fields->end();
5603 ++pf, ++field_index)
5604 {
f5165c05 5605 if (Gogo::is_sink_name(pf->field_name()))
5606 continue;
5607
e9d3367e 5608 if (field_index > 0)
5609 {
5610 if (left_temp == NULL)
5611 left = left->copy();
5612 else
5613 left = Expression::make_temporary_reference(left_temp, loc);
5614 if (right_temp == NULL)
5615 right = right->copy();
5616 else
5617 right = Expression::make_temporary_reference(right_temp, loc);
5618 }
5619 Expression* f1 = Expression::make_field_reference(left, field_index,
5620 loc);
5621 Expression* f2 = Expression::make_field_reference(right, field_index,
5622 loc);
5623 Expression* cond = Expression::make_binary(OPERATOR_EQEQ, f1, f2, loc);
5624 ret = Expression::make_binary(OPERATOR_ANDAND, ret, cond, loc);
5625 }
5626
5627 if (this->op_ == OPERATOR_NOTEQ)
5628 ret = Expression::make_unary(OPERATOR_NOT, ret, loc);
5629
5630 return ret;
5631}
5632
5633// Lower an array comparison.
5634
5635Expression*
5636Binary_expression::lower_array_comparison(Gogo* gogo,
5637 Statement_inserter* inserter)
5638{
5639 Array_type* at = this->left_->type()->array_type();
5640 Array_type* at2 = this->right_->type()->array_type();
5641 if (at2 == NULL)
5642 return this;
3a522dcc 5643 if (at != at2
5644 && !Type::are_identical(at, at2,
5645 Type::COMPARE_ERRORS | Type::COMPARE_TAGS,
5646 NULL))
e9d3367e 5647 return this;
5648 if (!Type::are_compatible_for_comparison(true, this->left_->type(),
5649 this->right_->type(), NULL))
5650 return this;
5651
5652 // Call memcmp directly if possible. This may let the middle-end
5653 // optimize the call.
113ef6a5 5654 if (at->compare_is_identity(gogo))
e9d3367e 5655 return this->lower_compare_to_memcmp(gogo, inserter);
5656
5657 // Call the array comparison function.
5658 Named_object* hash_fn;
5659 Named_object* equal_fn;
5660 at->type_functions(gogo, this->left_->type()->named_type(), NULL, NULL,
5661 &hash_fn, &equal_fn);
5662
5663 Location loc = this->location();
5664
5665 Expression* func = Expression::make_func_reference(equal_fn, NULL, loc);
5666
5667 Expression_list* args = new Expression_list();
5668 args->push_back(this->operand_address(inserter, this->left_));
5669 args->push_back(this->operand_address(inserter, this->right_));
e9d3367e 5670
5671 Expression* ret = Expression::make_call(func, args, false, loc);
5672
5673 if (this->op_ == OPERATOR_NOTEQ)
5674 ret = Expression::make_unary(OPERATOR_NOT, ret, loc);
5675
5676 return ret;
5677}
5678
ceeb12d7 5679// Lower an interface to value comparison.
5680
5681Expression*
5682Binary_expression::lower_interface_value_comparison(Gogo*,
5683 Statement_inserter* inserter)
5684{
5685 Type* left_type = this->left_->type();
5686 Type* right_type = this->right_->type();
5687 Interface_type* ift;
5688 if (left_type->interface_type() != NULL)
5689 {
5690 ift = left_type->interface_type();
5691 if (!ift->implements_interface(right_type, NULL))
5692 return this;
5693 }
5694 else
5695 {
5696 ift = right_type->interface_type();
5697 if (!ift->implements_interface(left_type, NULL))
5698 return this;
5699 }
5700 if (!Type::are_compatible_for_comparison(true, left_type, right_type, NULL))
5701 return this;
5702
5703 Location loc = this->location();
5704
5705 if (left_type->interface_type() == NULL
5706 && left_type->points_to() == NULL
5707 && !this->left_->is_addressable())
5708 {
5709 Temporary_statement* temp =
5710 Statement::make_temporary(left_type, NULL, loc);
5711 inserter->insert(temp);
5712 this->left_ =
5713 Expression::make_set_and_use_temporary(temp, this->left_, loc);
5714 }
5715
5716 if (right_type->interface_type() == NULL
5717 && right_type->points_to() == NULL
5718 && !this->right_->is_addressable())
5719 {
5720 Temporary_statement* temp =
5721 Statement::make_temporary(right_type, NULL, loc);
5722 inserter->insert(temp);
5723 this->right_ =
5724 Expression::make_set_and_use_temporary(temp, this->right_, loc);
5725 }
5726
5727 return this;
5728}
5729
e9d3367e 5730// Lower a struct or array comparison to a call to memcmp.
5731
5732Expression*
5733Binary_expression::lower_compare_to_memcmp(Gogo*, Statement_inserter* inserter)
5734{
5735 Location loc = this->location();
5736
5737 Expression* a1 = this->operand_address(inserter, this->left_);
5738 Expression* a2 = this->operand_address(inserter, this->right_);
5739 Expression* len = Expression::make_type_info(this->left_->type(),
5740 TYPE_INFO_SIZE);
5741
5742 Expression* call = Runtime::make_call(Runtime::MEMCMP, loc, 3, a1, a2, len);
e67508fa 5743 Expression* zero = Expression::make_integer_ul(0, NULL, loc);
e9d3367e 5744 return Expression::make_binary(this->op_, call, zero, loc);
5745}
5746
a32698ee 5747Expression*
5c3f3470 5748Binary_expression::do_flatten(Gogo* gogo, Named_object*,
a32698ee 5749 Statement_inserter* inserter)
5750{
5751 Location loc = this->location();
5bf8be8b 5752 if (this->left_->type()->is_error_type()
5753 || this->right_->type()->is_error_type()
5754 || this->left_->is_error_expression()
5755 || this->right_->is_error_expression())
5756 {
5757 go_assert(saw_errors());
5758 return Expression::make_error(loc);
5759 }
5760
a32698ee 5761 Temporary_statement* temp;
a32698ee 5762
5763 Type* left_type = this->left_->type();
5764 bool is_shift_op = (this->op_ == OPERATOR_LSHIFT
5765 || this->op_ == OPERATOR_RSHIFT);
5766 bool is_idiv_op = ((this->op_ == OPERATOR_DIV &&
5767 left_type->integer_type() != NULL)
5768 || this->op_ == OPERATOR_MOD);
5769
a32698ee 5770 if (is_shift_op
5c3f3470 5771 || (is_idiv_op
5772 && (gogo->check_divide_by_zero() || gogo->check_divide_overflow())))
a32698ee 5773 {
545ab43b 5774 if (!this->left_->is_variable() && !this->left_->is_constant())
a32698ee 5775 {
5776 temp = Statement::make_temporary(NULL, this->left_, loc);
5777 inserter->insert(temp);
5778 this->left_ = Expression::make_temporary_reference(temp, loc);
5779 }
545ab43b 5780 if (!this->right_->is_variable() && !this->right_->is_constant())
a32698ee 5781 {
5782 temp =
5783 Statement::make_temporary(NULL, this->right_, loc);
5784 this->right_ = Expression::make_temporary_reference(temp, loc);
5785 inserter->insert(temp);
5786 }
5787 }
5788 return this;
5789}
5790
5791
e9d3367e 5792// Return the address of EXPR, cast to unsafe.Pointer.
5793
5794Expression*
5795Binary_expression::operand_address(Statement_inserter* inserter,
5796 Expression* expr)
5797{
5798 Location loc = this->location();
5799
5800 if (!expr->is_addressable())
5801 {
5802 Temporary_statement* temp = Statement::make_temporary(expr->type(), NULL,
5803 loc);
5804 inserter->insert(temp);
5805 expr = Expression::make_set_and_use_temporary(temp, expr, loc);
5806 }
5807 expr = Expression::make_unary(OPERATOR_AND, expr, loc);
5808 static_cast<Unary_expression*>(expr)->set_does_not_escape();
5809 Type* void_type = Type::make_void_type();
5810 Type* unsafe_pointer_type = Type::make_pointer_type(void_type);
5811 return Expression::make_cast(unsafe_pointer_type, expr, loc);
5812}
5813
0c77715b 5814// Return the numeric constant value, if it has one.
e440a328 5815
5816bool
0c77715b 5817Binary_expression::do_numeric_constant_value(Numeric_constant* nc) const
e440a328 5818{
0c77715b 5819 Numeric_constant left_nc;
5820 if (!this->left_->numeric_constant_value(&left_nc))
5821 return false;
5822 Numeric_constant right_nc;
5823 if (!this->right_->numeric_constant_value(&right_nc))
5824 return false;
af7a5274 5825 bool issued_error;
9767e2d3 5826 return Binary_expression::eval_constant(this->op_, &left_nc, &right_nc,
af7a5274 5827 this->location(), nc, &issued_error);
e440a328 5828}
5829
5830// Note that the value is being discarded.
5831
4f2138d7 5832bool
e440a328 5833Binary_expression::do_discarding_value()
5834{
5835 if (this->op_ == OPERATOR_OROR || this->op_ == OPERATOR_ANDAND)
4f2138d7 5836 return this->right_->discarding_value();
e440a328 5837 else
4f2138d7 5838 {
5839 this->unused_value_error();
5840 return false;
5841 }
e440a328 5842}
5843
5844// Get type.
5845
5846Type*
5847Binary_expression::do_type()
5848{
5f5fea79 5849 if (this->classification() == EXPRESSION_ERROR)
5850 return Type::make_error_type();
5851
e440a328 5852 switch (this->op_)
5853 {
e440a328 5854 case OPERATOR_EQEQ:
5855 case OPERATOR_NOTEQ:
5856 case OPERATOR_LT:
5857 case OPERATOR_LE:
5858 case OPERATOR_GT:
5859 case OPERATOR_GE:
e90c9dfc 5860 if (this->type_ == NULL)
5861 this->type_ = Type::make_boolean_type();
5862 return this->type_;
e440a328 5863
5864 case OPERATOR_PLUS:
5865 case OPERATOR_MINUS:
5866 case OPERATOR_OR:
5867 case OPERATOR_XOR:
5868 case OPERATOR_MULT:
5869 case OPERATOR_DIV:
5870 case OPERATOR_MOD:
5871 case OPERATOR_AND:
5872 case OPERATOR_BITCLEAR:
e90c9dfc 5873 case OPERATOR_OROR:
5874 case OPERATOR_ANDAND:
e440a328 5875 {
0c77715b 5876 Type* type;
5877 if (!Binary_expression::operation_type(this->op_,
5878 this->left_->type(),
5879 this->right_->type(),
5880 &type))
5881 return Type::make_error_type();
5882 return type;
e440a328 5883 }
5884
5885 case OPERATOR_LSHIFT:
5886 case OPERATOR_RSHIFT:
5887 return this->left_->type();
5888
5889 default:
c3e6f413 5890 go_unreachable();
e440a328 5891 }
5892}
5893
5894// Set type for a binary expression.
5895
5896void
5897Binary_expression::do_determine_type(const Type_context* context)
5898{
5899 Type* tleft = this->left_->type();
5900 Type* tright = this->right_->type();
5901
5902 // Both sides should have the same type, except for the shift
5903 // operations. For a comparison, we should ignore the incoming
5904 // type.
5905
5906 bool is_shift_op = (this->op_ == OPERATOR_LSHIFT
5907 || this->op_ == OPERATOR_RSHIFT);
5908
5909 bool is_comparison = (this->op_ == OPERATOR_EQEQ
5910 || this->op_ == OPERATOR_NOTEQ
5911 || this->op_ == OPERATOR_LT
5912 || this->op_ == OPERATOR_LE
5913 || this->op_ == OPERATOR_GT
5914 || this->op_ == OPERATOR_GE);
5915
c999c2a7 5916 // For constant expressions, the context of the result is not useful in
5917 // determining the types of the operands. It is only legal to use abstract
5918 // boolean, numeric, and string constants as operands where it is legal to
5919 // use non-abstract boolean, numeric, and string constants, respectively.
5920 // Any issues with the operation will be resolved in the check_types pass.
5921 bool is_constant_expr = (this->left_->is_constant()
5922 && this->right_->is_constant());
5923
e440a328 5924 Type_context subcontext(*context);
5925
9c4ff2ce 5926 if (is_constant_expr && !is_shift_op)
af7a5274 5927 {
5928 subcontext.type = NULL;
5929 subcontext.may_be_abstract = true;
5930 }
5931 else if (is_comparison)
e440a328 5932 {
5933 // In a comparison, the context does not determine the types of
5934 // the operands.
5935 subcontext.type = NULL;
5936 }
5937
5938 // Set the context for the left hand operand.
5939 if (is_shift_op)
5940 {
b40dc774 5941 // The right hand operand of a shift plays no role in
5942 // determining the type of the left hand operand.
e440a328 5943 }
5944 else if (!tleft->is_abstract())
5945 subcontext.type = tleft;
5946 else if (!tright->is_abstract())
5947 subcontext.type = tright;
5948 else if (subcontext.type == NULL)
5949 {
5950 if ((tleft->integer_type() != NULL && tright->integer_type() != NULL)
5951 || (tleft->float_type() != NULL && tright->float_type() != NULL)
5952 || (tleft->complex_type() != NULL && tright->complex_type() != NULL))
5953 {
5954 // Both sides have an abstract integer, abstract float, or
5955 // abstract complex type. Just let CONTEXT determine
5956 // whether they may remain abstract or not.
5957 }
5958 else if (tleft->complex_type() != NULL)
5959 subcontext.type = tleft;
5960 else if (tright->complex_type() != NULL)
5961 subcontext.type = tright;
5962 else if (tleft->float_type() != NULL)
5963 subcontext.type = tleft;
5964 else if (tright->float_type() != NULL)
5965 subcontext.type = tright;
5966 else
5967 subcontext.type = tleft;
f58a23ae 5968
5969 if (subcontext.type != NULL && !context->may_be_abstract)
5970 subcontext.type = subcontext.type->make_non_abstract_type();
e440a328 5971 }
5972
af7a5274 5973 this->left_->determine_type(&subcontext);
e440a328 5974
e440a328 5975 if (is_shift_op)
5976 {
b40dc774 5977 // We may have inherited an unusable type for the shift operand.
5978 // Give a useful error if that happened.
5979 if (tleft->is_abstract()
5980 && subcontext.type != NULL
8ab6effb 5981 && !subcontext.may_be_abstract
f6bc81e6 5982 && subcontext.type->interface_type() == NULL
8ab6effb 5983 && subcontext.type->integer_type() == NULL)
b40dc774 5984 this->report_error(("invalid context-determined non-integer type "
8ab6effb 5985 "for left operand of shift"));
b40dc774 5986
5987 // The context for the right hand operand is the same as for the
5988 // left hand operand, except for a shift operator.
e440a328 5989 subcontext.type = Type::lookup_integer_type("uint");
5990 subcontext.may_be_abstract = false;
5991 }
5992
af7a5274 5993 this->right_->determine_type(&subcontext);
e90c9dfc 5994
5995 if (is_comparison)
5996 {
5997 if (this->type_ != NULL && !this->type_->is_abstract())
5998 ;
5999 else if (context->type != NULL && context->type->is_boolean_type())
6000 this->type_ = context->type;
6001 else if (!context->may_be_abstract)
6002 this->type_ = Type::lookup_bool_type();
6003 }
e440a328 6004}
6005
6006// Report an error if the binary operator OP does not support TYPE.
be8b5eee 6007// OTYPE is the type of the other operand. Return whether the
6008// operation is OK. This should not be used for shift.
e440a328 6009
6010bool
be8b5eee 6011Binary_expression::check_operator_type(Operator op, Type* type, Type* otype,
b13c66cd 6012 Location location)
e440a328 6013{
6014 switch (op)
6015 {
6016 case OPERATOR_OROR:
6017 case OPERATOR_ANDAND:
c999c2a7 6018 if (!type->is_boolean_type()
6019 || !otype->is_boolean_type())
e440a328 6020 {
631d5788 6021 go_error_at(location, "expected boolean type");
e440a328 6022 return false;
6023 }
6024 break;
6025
6026 case OPERATOR_EQEQ:
6027 case OPERATOR_NOTEQ:
e9d3367e 6028 {
6029 std::string reason;
6030 if (!Type::are_compatible_for_comparison(true, type, otype, &reason))
6031 {
631d5788 6032 go_error_at(location, "%s", reason.c_str());
e9d3367e 6033 return false;
6034 }
6035 }
e440a328 6036 break;
6037
6038 case OPERATOR_LT:
6039 case OPERATOR_LE:
6040 case OPERATOR_GT:
6041 case OPERATOR_GE:
e9d3367e 6042 {
6043 std::string reason;
6044 if (!Type::are_compatible_for_comparison(false, type, otype, &reason))
6045 {
631d5788 6046 go_error_at(location, "%s", reason.c_str());
e9d3367e 6047 return false;
6048 }
6049 }
e440a328 6050 break;
6051
6052 case OPERATOR_PLUS:
6053 case OPERATOR_PLUSEQ:
c999c2a7 6054 if ((!type->is_numeric_type() && !type->is_string_type())
6055 || (!otype->is_numeric_type() && !otype->is_string_type()))
e440a328 6056 {
631d5788 6057 go_error_at(location,
e440a328 6058 "expected integer, floating, complex, or string type");
6059 return false;
6060 }
6061 break;
6062
6063 case OPERATOR_MINUS:
6064 case OPERATOR_MINUSEQ:
6065 case OPERATOR_MULT:
6066 case OPERATOR_MULTEQ:
6067 case OPERATOR_DIV:
6068 case OPERATOR_DIVEQ:
c999c2a7 6069 if (!type->is_numeric_type() || !otype->is_numeric_type())
e440a328 6070 {
631d5788 6071 go_error_at(location, "expected integer, floating, or complex type");
e440a328 6072 return false;
6073 }
6074 break;
6075
6076 case OPERATOR_MOD:
6077 case OPERATOR_MODEQ:
6078 case OPERATOR_OR:
6079 case OPERATOR_OREQ:
6080 case OPERATOR_AND:
6081 case OPERATOR_ANDEQ:
6082 case OPERATOR_XOR:
6083 case OPERATOR_XOREQ:
6084 case OPERATOR_BITCLEAR:
6085 case OPERATOR_BITCLEAREQ:
c999c2a7 6086 if (type->integer_type() == NULL || otype->integer_type() == NULL)
e440a328 6087 {
631d5788 6088 go_error_at(location, "expected integer type");
e440a328 6089 return false;
6090 }
6091 break;
6092
6093 default:
c3e6f413 6094 go_unreachable();
e440a328 6095 }
6096
6097 return true;
6098}
6099
6100// Check types.
6101
6102void
6103Binary_expression::do_check_types(Gogo*)
6104{
5f5fea79 6105 if (this->classification() == EXPRESSION_ERROR)
6106 return;
6107
e440a328 6108 Type* left_type = this->left_->type();
6109 Type* right_type = this->right_->type();
5c13bd80 6110 if (left_type->is_error() || right_type->is_error())
9fe897ef 6111 {
6112 this->set_is_error();
6113 return;
6114 }
e440a328 6115
6116 if (this->op_ == OPERATOR_EQEQ
6117 || this->op_ == OPERATOR_NOTEQ
6118 || this->op_ == OPERATOR_LT
6119 || this->op_ == OPERATOR_LE
6120 || this->op_ == OPERATOR_GT
6121 || this->op_ == OPERATOR_GE)
6122 {
907c5ecd 6123 if (left_type->is_nil_type() && right_type->is_nil_type())
6124 {
6125 this->report_error(_("invalid comparison of nil with nil"));
6126 return;
6127 }
e440a328 6128 if (!Type::are_assignable(left_type, right_type, NULL)
6129 && !Type::are_assignable(right_type, left_type, NULL))
6130 {
6131 this->report_error(_("incompatible types in binary expression"));
6132 return;
6133 }
6134 if (!Binary_expression::check_operator_type(this->op_, left_type,
be8b5eee 6135 right_type,
e440a328 6136 this->location())
6137 || !Binary_expression::check_operator_type(this->op_, right_type,
be8b5eee 6138 left_type,
e440a328 6139 this->location()))
6140 {
6141 this->set_is_error();
6142 return;
6143 }
6144 }
6145 else if (this->op_ != OPERATOR_LSHIFT && this->op_ != OPERATOR_RSHIFT)
6146 {
6147 if (!Type::are_compatible_for_binop(left_type, right_type))
6148 {
6149 this->report_error(_("incompatible types in binary expression"));
6150 return;
6151 }
6152 if (!Binary_expression::check_operator_type(this->op_, left_type,
be8b5eee 6153 right_type,
e440a328 6154 this->location()))
6155 {
6156 this->set_is_error();
6157 return;
6158 }
5c65b19d 6159 if (this->op_ == OPERATOR_DIV || this->op_ == OPERATOR_MOD)
6160 {
6161 // Division by a zero integer constant is an error.
6162 Numeric_constant rconst;
6163 unsigned long rval;
6164 if (left_type->integer_type() != NULL
6165 && this->right_->numeric_constant_value(&rconst)
6166 && rconst.to_unsigned_long(&rval) == Numeric_constant::NC_UL_VALID
6167 && rval == 0)
6168 {
6169 this->report_error(_("integer division by zero"));
6170 return;
6171 }
6172 }
e440a328 6173 }
6174 else
6175 {
6176 if (left_type->integer_type() == NULL)
6177 this->report_error(_("shift of non-integer operand"));
6178
6b5e0fac 6179 if (right_type->is_string_type())
6180 this->report_error(_("shift count not unsigned integer"));
6181 else if (!right_type->is_abstract()
e440a328 6182 && (right_type->integer_type() == NULL
6183 || !right_type->integer_type()->is_unsigned()))
6184 this->report_error(_("shift count not unsigned integer"));
6185 else
6186 {
0c77715b 6187 Numeric_constant nc;
6188 if (this->right_->numeric_constant_value(&nc))
e440a328 6189 {
0c77715b 6190 mpz_t val;
6191 if (!nc.to_int(&val))
6192 this->report_error(_("shift count not unsigned integer"));
6193 else
a4eba91b 6194 {
0c77715b 6195 if (mpz_sgn(val) < 0)
6196 {
6197 this->report_error(_("negative shift count"));
0c77715b 6198 Location rloc = this->right_->location();
e67508fa 6199 this->right_ = Expression::make_integer_ul(0, right_type,
6200 rloc);
0c77715b 6201 }
6202 mpz_clear(val);
a4eba91b 6203 }
e440a328 6204 }
e440a328 6205 }
6206 }
6207}
6208
ea664253 6209// Get the backend representation for a binary expression.
e440a328 6210
ea664253 6211Bexpression*
6212Binary_expression::do_get_backend(Translate_context* context)
e440a328 6213{
1b1f2abf 6214 Gogo* gogo = context->gogo();
a32698ee 6215 Location loc = this->location();
6216 Type* left_type = this->left_->type();
6217 Type* right_type = this->right_->type();
1b1f2abf 6218
e440a328 6219 bool use_left_type = true;
6220 bool is_shift_op = false;
29a2d1d8 6221 bool is_idiv_op = false;
e440a328 6222 switch (this->op_)
6223 {
6224 case OPERATOR_EQEQ:
6225 case OPERATOR_NOTEQ:
6226 case OPERATOR_LT:
6227 case OPERATOR_LE:
6228 case OPERATOR_GT:
6229 case OPERATOR_GE:
ea664253 6230 return Expression::comparison(context, this->type_, this->op_,
6231 this->left_, this->right_, loc);
e440a328 6232
6233 case OPERATOR_OROR:
e440a328 6234 case OPERATOR_ANDAND:
e440a328 6235 use_left_type = false;
6236 break;
6237 case OPERATOR_PLUS:
e440a328 6238 case OPERATOR_MINUS:
e440a328 6239 case OPERATOR_OR:
e440a328 6240 case OPERATOR_XOR:
e440a328 6241 case OPERATOR_MULT:
e440a328 6242 break;
6243 case OPERATOR_DIV:
a32698ee 6244 if (left_type->float_type() != NULL || left_type->complex_type() != NULL)
6245 break;
729f8831 6246 // Fall through.
e440a328 6247 case OPERATOR_MOD:
29a2d1d8 6248 is_idiv_op = true;
e440a328 6249 break;
6250 case OPERATOR_LSHIFT:
e440a328 6251 case OPERATOR_RSHIFT:
e440a328 6252 is_shift_op = true;
6253 break;
e440a328 6254 case OPERATOR_BITCLEAR:
a32698ee 6255 this->right_ = Expression::make_unary(OPERATOR_XOR, this->right_, loc);
6256 case OPERATOR_AND:
e440a328 6257 break;
6258 default:
c3e6f413 6259 go_unreachable();
e440a328 6260 }
6261
736a16ba 6262 // The only binary operation for string is +, and that should have
6263 // been converted to a String_concat_expression in do_lower.
6264 go_assert(!left_type->is_string_type());
a32698ee 6265
6266 // For complex division Go might want slightly different results than the
6267 // backend implementation provides, so we have our own runtime routine.
1850e20c 6268 if (this->op_ == OPERATOR_DIV && this->left_->type()->complex_type() != NULL)
6269 {
a32698ee 6270 Runtime::Function complex_code;
1850e20c 6271 switch (this->left_->type()->complex_type()->bits())
6272 {
6273 case 64:
a32698ee 6274 complex_code = Runtime::COMPLEX64_DIV;
1850e20c 6275 break;
6276 case 128:
a32698ee 6277 complex_code = Runtime::COMPLEX128_DIV;
1850e20c 6278 break;
6279 default:
6280 go_unreachable();
6281 }
a32698ee 6282 Expression* complex_div =
6283 Runtime::make_call(complex_code, loc, 2, this->left_, this->right_);
ea664253 6284 return complex_div->get_backend(context);
1850e20c 6285 }
6286
ea664253 6287 Bexpression* left = this->left_->get_backend(context);
6288 Bexpression* right = this->right_->get_backend(context);
e440a328 6289
a32698ee 6290 Type* type = use_left_type ? left_type : right_type;
6291 Btype* btype = type->get_backend(gogo);
6292
6293 Bexpression* ret =
6294 gogo->backend()->binary_expression(this->op_, left, right, loc);
6295 ret = gogo->backend()->convert_expression(btype, ret, loc);
e440a328 6296
a32698ee 6297 // Initialize overflow constants.
6298 Bexpression* overflow;
6299 mpz_t zero;
6300 mpz_init_set_ui(zero, 0UL);
6301 mpz_t one;
6302 mpz_init_set_ui(one, 1UL);
6303 mpz_t neg_one;
6304 mpz_init_set_si(neg_one, -1);
e440a328 6305
a32698ee 6306 Btype* left_btype = left_type->get_backend(gogo);
6307 Btype* right_btype = right_type->get_backend(gogo);
e440a328 6308
6309 // In Go, a shift larger than the size of the type is well-defined.
a32698ee 6310 // This is not true in C, so we need to insert a conditional.
e440a328 6311 if (is_shift_op)
6312 {
a32698ee 6313 go_assert(left_type->integer_type() != NULL);
e440a328 6314
a32698ee 6315 int bits = left_type->integer_type()->bits();
a7c5b619 6316
6317 Numeric_constant nc;
6318 unsigned long ul;
6319 if (!this->right_->numeric_constant_value(&nc)
6320 || nc.to_unsigned_long(&ul) != Numeric_constant::NC_UL_VALID
6321 || ul >= static_cast<unsigned long>(bits))
e440a328 6322 {
a7c5b619 6323 mpz_t bitsval;
6324 mpz_init_set_ui(bitsval, bits);
6325 Bexpression* bits_expr =
6326 gogo->backend()->integer_constant_expression(right_btype, bitsval);
6327 Bexpression* compare =
6328 gogo->backend()->binary_expression(OPERATOR_LT,
6329 right, bits_expr, loc);
6330
6331 Bexpression* zero_expr =
6332 gogo->backend()->integer_constant_expression(left_btype, zero);
6333 overflow = zero_expr;
6334 Bfunction* bfn = context->function()->func_value()->get_decl();
6335 if (this->op_ == OPERATOR_RSHIFT
6336 && !left_type->integer_type()->is_unsigned())
6337 {
6338 Bexpression* neg_expr =
6339 gogo->backend()->binary_expression(OPERATOR_LT, left,
6340 zero_expr, loc);
6341 Bexpression* neg_one_expr =
6342 gogo->backend()->integer_constant_expression(left_btype,
6343 neg_one);
6344 overflow = gogo->backend()->conditional_expression(bfn,
6345 btype,
6346 neg_expr,
6347 neg_one_expr,
6348 zero_expr,
6349 loc);
6350 }
6351 ret = gogo->backend()->conditional_expression(bfn, btype, compare,
6352 ret, overflow, loc);
6353 mpz_clear(bitsval);
29a2d1d8 6354 }
29a2d1d8 6355 }
6356
6357 // Add checks for division by zero and division overflow as needed.
6358 if (is_idiv_op)
6359 {
5c3f3470 6360 if (gogo->check_divide_by_zero())
29a2d1d8 6361 {
6362 // right == 0
a32698ee 6363 Bexpression* zero_expr =
6364 gogo->backend()->integer_constant_expression(right_btype, zero);
6365 Bexpression* check =
6366 gogo->backend()->binary_expression(OPERATOR_EQEQ,
6367 right, zero_expr, loc);
29a2d1d8 6368
a32698ee 6369 // __go_runtime_error(RUNTIME_ERROR_DIVISION_BY_ZERO)
29a2d1d8 6370 int errcode = RUNTIME_ERROR_DIVISION_BY_ZERO;
ea664253 6371 Bexpression* crash = gogo->runtime_error(errcode,
6372 loc)->get_backend(context);
29a2d1d8 6373
6374 // right == 0 ? (__go_runtime_error(...), 0) : ret
93715b75 6375 Bfunction* bfn = context->function()->func_value()->get_decl();
6376 ret = gogo->backend()->conditional_expression(bfn, btype,
6377 check, crash,
ea664253 6378 ret, loc);
b13c66cd 6379 }
6380
5c3f3470 6381 if (gogo->check_divide_overflow())
29a2d1d8 6382 {
6383 // right == -1
6384 // FIXME: It would be nice to say that this test is expected
6385 // to return false.
a32698ee 6386
6387 Bexpression* neg_one_expr =
6388 gogo->backend()->integer_constant_expression(right_btype, neg_one);
6389 Bexpression* check =
6390 gogo->backend()->binary_expression(OPERATOR_EQEQ,
6391 right, neg_one_expr, loc);
6392
6393 Bexpression* zero_expr =
6394 gogo->backend()->integer_constant_expression(btype, zero);
6395 Bexpression* one_expr =
6396 gogo->backend()->integer_constant_expression(btype, one);
93715b75 6397 Bfunction* bfn = context->function()->func_value()->get_decl();
a32698ee 6398
6399 if (type->integer_type()->is_unsigned())
29a2d1d8 6400 {
6401 // An unsigned -1 is the largest possible number, so
6402 // dividing is always 1 or 0.
a32698ee 6403
6404 Bexpression* cmp =
6405 gogo->backend()->binary_expression(OPERATOR_EQEQ,
6406 left, right, loc);
29a2d1d8 6407 if (this->op_ == OPERATOR_DIV)
a32698ee 6408 overflow =
93715b75 6409 gogo->backend()->conditional_expression(bfn, btype, cmp,
a32698ee 6410 one_expr, zero_expr,
6411 loc);
29a2d1d8 6412 else
a32698ee 6413 overflow =
93715b75 6414 gogo->backend()->conditional_expression(bfn, btype, cmp,
a32698ee 6415 zero_expr, left,
6416 loc);
29a2d1d8 6417 }
6418 else
6419 {
6420 // Computing left / -1 is the same as computing - left,
6421 // which does not overflow since Go sets -fwrapv.
6422 if (this->op_ == OPERATOR_DIV)
a32698ee 6423 {
6424 Expression* negate_expr =
6425 Expression::make_unary(OPERATOR_MINUS, this->left_, loc);
ea664253 6426 overflow = negate_expr->get_backend(context);
a32698ee 6427 }
29a2d1d8 6428 else
a32698ee 6429 overflow = zero_expr;
29a2d1d8 6430 }
a32698ee 6431 overflow = gogo->backend()->convert_expression(btype, overflow, loc);
29a2d1d8 6432
6433 // right == -1 ? - left : ret
93715b75 6434 ret = gogo->backend()->conditional_expression(bfn, btype,
6435 check, overflow,
a32698ee 6436 ret, loc);
29a2d1d8 6437 }
e440a328 6438 }
6439
a32698ee 6440 mpz_clear(zero);
6441 mpz_clear(one);
6442 mpz_clear(neg_one);
ea664253 6443 return ret;
e440a328 6444}
6445
6446// Export a binary expression.
6447
6448void
548be246 6449Binary_expression::do_export(Export_function_body* efb) const
e440a328 6450{
548be246 6451 efb->write_c_string("(");
6452 this->left_->export_expression(efb);
e440a328 6453 switch (this->op_)
6454 {
6455 case OPERATOR_OROR:
548be246 6456 efb->write_c_string(" || ");
e440a328 6457 break;
6458 case OPERATOR_ANDAND:
548be246 6459 efb->write_c_string(" && ");
e440a328 6460 break;
6461 case OPERATOR_EQEQ:
548be246 6462 efb->write_c_string(" == ");
e440a328 6463 break;
6464 case OPERATOR_NOTEQ:
548be246 6465 efb->write_c_string(" != ");
e440a328 6466 break;
6467 case OPERATOR_LT:
548be246 6468 efb->write_c_string(" < ");
e440a328 6469 break;
6470 case OPERATOR_LE:
548be246 6471 efb->write_c_string(" <= ");
e440a328 6472 break;
6473 case OPERATOR_GT:
548be246 6474 efb->write_c_string(" > ");
e440a328 6475 break;
6476 case OPERATOR_GE:
548be246 6477 efb->write_c_string(" >= ");
e440a328 6478 break;
6479 case OPERATOR_PLUS:
548be246 6480 efb->write_c_string(" + ");
e440a328 6481 break;
6482 case OPERATOR_MINUS:
548be246 6483 efb->write_c_string(" - ");
e440a328 6484 break;
6485 case OPERATOR_OR:
548be246 6486 efb->write_c_string(" | ");
e440a328 6487 break;
6488 case OPERATOR_XOR:
548be246 6489 efb->write_c_string(" ^ ");
e440a328 6490 break;
6491 case OPERATOR_MULT:
548be246 6492 efb->write_c_string(" * ");
e440a328 6493 break;
6494 case OPERATOR_DIV:
548be246 6495 efb->write_c_string(" / ");
e440a328 6496 break;
6497 case OPERATOR_MOD:
548be246 6498 efb->write_c_string(" % ");
e440a328 6499 break;
6500 case OPERATOR_LSHIFT:
548be246 6501 efb->write_c_string(" << ");
e440a328 6502 break;
6503 case OPERATOR_RSHIFT:
548be246 6504 efb->write_c_string(" >> ");
e440a328 6505 break;
6506 case OPERATOR_AND:
548be246 6507 efb->write_c_string(" & ");
e440a328 6508 break;
6509 case OPERATOR_BITCLEAR:
548be246 6510 efb->write_c_string(" &^ ");
e440a328 6511 break;
6512 default:
c3e6f413 6513 go_unreachable();
e440a328 6514 }
548be246 6515 this->right_->export_expression(efb);
6516 efb->write_c_string(")");
e440a328 6517}
6518
6519// Import a binary expression.
6520
6521Expression*
bc8e2ef4 6522Binary_expression::do_import(Import_expression* imp, Location loc)
e440a328 6523{
6524 imp->require_c_string("(");
6525
9b92780c 6526 Expression* left = Expression::import_expression(imp, loc);
e440a328 6527
6528 Operator op;
6529 if (imp->match_c_string(" || "))
6530 {
6531 op = OPERATOR_OROR;
6532 imp->advance(4);
6533 }
6534 else if (imp->match_c_string(" && "))
6535 {
6536 op = OPERATOR_ANDAND;
6537 imp->advance(4);
6538 }
6539 else if (imp->match_c_string(" == "))
6540 {
6541 op = OPERATOR_EQEQ;
6542 imp->advance(4);
6543 }
6544 else if (imp->match_c_string(" != "))
6545 {
6546 op = OPERATOR_NOTEQ;
6547 imp->advance(4);
6548 }
6549 else if (imp->match_c_string(" < "))
6550 {
6551 op = OPERATOR_LT;
6552 imp->advance(3);
6553 }
6554 else if (imp->match_c_string(" <= "))
6555 {
6556 op = OPERATOR_LE;
6557 imp->advance(4);
6558 }
6559 else if (imp->match_c_string(" > "))
6560 {
6561 op = OPERATOR_GT;
6562 imp->advance(3);
6563 }
6564 else if (imp->match_c_string(" >= "))
6565 {
6566 op = OPERATOR_GE;
6567 imp->advance(4);
6568 }
6569 else if (imp->match_c_string(" + "))
6570 {
6571 op = OPERATOR_PLUS;
6572 imp->advance(3);
6573 }
6574 else if (imp->match_c_string(" - "))
6575 {
6576 op = OPERATOR_MINUS;
6577 imp->advance(3);
6578 }
6579 else if (imp->match_c_string(" | "))
6580 {
6581 op = OPERATOR_OR;
6582 imp->advance(3);
6583 }
6584 else if (imp->match_c_string(" ^ "))
6585 {
6586 op = OPERATOR_XOR;
6587 imp->advance(3);
6588 }
6589 else if (imp->match_c_string(" * "))
6590 {
6591 op = OPERATOR_MULT;
6592 imp->advance(3);
6593 }
6594 else if (imp->match_c_string(" / "))
6595 {
6596 op = OPERATOR_DIV;
6597 imp->advance(3);
6598 }
6599 else if (imp->match_c_string(" % "))
6600 {
6601 op = OPERATOR_MOD;
6602 imp->advance(3);
6603 }
6604 else if (imp->match_c_string(" << "))
6605 {
6606 op = OPERATOR_LSHIFT;
6607 imp->advance(4);
6608 }
6609 else if (imp->match_c_string(" >> "))
6610 {
6611 op = OPERATOR_RSHIFT;
6612 imp->advance(4);
6613 }
6614 else if (imp->match_c_string(" & "))
6615 {
6616 op = OPERATOR_AND;
6617 imp->advance(3);
6618 }
6619 else if (imp->match_c_string(" &^ "))
6620 {
6621 op = OPERATOR_BITCLEAR;
6622 imp->advance(4);
6623 }
6624 else
6625 {
631d5788 6626 go_error_at(imp->location(), "unrecognized binary operator");
9b92780c 6627 return Expression::make_error(loc);
e440a328 6628 }
6629
9b92780c 6630 Expression* right = Expression::import_expression(imp, loc);
e440a328 6631
6632 imp->require_c_string(")");
6633
9b92780c 6634 return Expression::make_binary(op, left, right, loc);
e440a328 6635}
6636
d751bb78 6637// Dump ast representation of a binary expression.
6638
6639void
6640Binary_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
6641{
6642 ast_dump_context->ostream() << "(";
6643 ast_dump_context->dump_expression(this->left_);
6644 ast_dump_context->ostream() << " ";
6645 ast_dump_context->dump_operator(this->op_);
6646 ast_dump_context->ostream() << " ";
6647 ast_dump_context->dump_expression(this->right_);
6648 ast_dump_context->ostream() << ") ";
6649}
6650
e440a328 6651// Make a binary expression.
6652
6653Expression*
6654Expression::make_binary(Operator op, Expression* left, Expression* right,
b13c66cd 6655 Location location)
e440a328 6656{
6657 return new Binary_expression(op, left, right, location);
6658}
6659
6660// Implement a comparison.
6661
a32698ee 6662Bexpression*
6663Expression::comparison(Translate_context* context, Type* result_type,
6664 Operator op, Expression* left, Expression* right,
6665 Location location)
e440a328 6666{
2387f644 6667 Type* left_type = left->type();
6668 Type* right_type = right->type();
ceeb12d7 6669
e67508fa 6670 Expression* zexpr = Expression::make_integer_ul(0, NULL, location);
1b1f2abf 6671
15c67ee2 6672 if (left_type->is_string_type() && right_type->is_string_type())
e440a328 6673 {
6098d6cb 6674 if (op == OPERATOR_EQEQ || op == OPERATOR_NOTEQ)
6675 {
6676 left = Runtime::make_call(Runtime::EQSTRING, location, 2,
6677 left, right);
6678 right = Expression::make_boolean(true, location);
6679 }
6680 else
6681 {
6682 left = Runtime::make_call(Runtime::CMPSTRING, location, 2,
6683 left, right);
6684 right = zexpr;
6685 }
e440a328 6686 }
15c67ee2 6687 else if ((left_type->interface_type() != NULL
6688 && right_type->interface_type() == NULL
6689 && !right_type->is_nil_type())
6690 || (left_type->interface_type() == NULL
6691 && !left_type->is_nil_type()
6692 && right_type->interface_type() != NULL))
e440a328 6693 {
6694 // Comparing an interface value to a non-interface value.
6695 if (left_type->interface_type() == NULL)
6696 {
6697 std::swap(left_type, right_type);
2387f644 6698 std::swap(left, right);
e440a328 6699 }
6700
6701 // The right operand is not an interface. We need to take its
6702 // address if it is not a pointer.
ceeb12d7 6703 Expression* pointer_arg = NULL;
e440a328 6704 if (right_type->points_to() != NULL)
2387f644 6705 pointer_arg = right;
e440a328 6706 else
6707 {
2387f644 6708 go_assert(right->is_addressable());
6709 pointer_arg = Expression::make_unary(OPERATOR_AND, right,
ceeb12d7 6710 location);
e440a328 6711 }
e440a328 6712
2387f644 6713 Expression* descriptor =
6714 Expression::make_type_descriptor(right_type, location);
6715 left =
ceeb12d7 6716 Runtime::make_call((left_type->interface_type()->is_empty()
6098d6cb 6717 ? Runtime::EFACEVALEQ
6718 : Runtime::IFACEVALEQ),
2387f644 6719 location, 3, left, descriptor,
ceeb12d7 6720 pointer_arg);
6098d6cb 6721 go_assert(op == OPERATOR_EQEQ || op == OPERATOR_NOTEQ);
6722 right = Expression::make_boolean(true, location);
e440a328 6723 }
6724 else if (left_type->interface_type() != NULL
6725 && right_type->interface_type() != NULL)
6726 {
ceeb12d7 6727 Runtime::Function compare_function;
739bad04 6728 if (left_type->interface_type()->is_empty()
6729 && right_type->interface_type()->is_empty())
6098d6cb 6730 compare_function = Runtime::EFACEEQ;
739bad04 6731 else if (!left_type->interface_type()->is_empty()
6732 && !right_type->interface_type()->is_empty())
6098d6cb 6733 compare_function = Runtime::IFACEEQ;
739bad04 6734 else
6735 {
6736 if (left_type->interface_type()->is_empty())
6737 {
739bad04 6738 std::swap(left_type, right_type);
2387f644 6739 std::swap(left, right);
739bad04 6740 }
c484d925 6741 go_assert(!left_type->interface_type()->is_empty());
6742 go_assert(right_type->interface_type()->is_empty());
6098d6cb 6743 compare_function = Runtime::IFACEEFACEEQ;
739bad04 6744 }
6745
2387f644 6746 left = Runtime::make_call(compare_function, location, 2, left, right);
6098d6cb 6747 go_assert(op == OPERATOR_EQEQ || op == OPERATOR_NOTEQ);
6748 right = Expression::make_boolean(true, location);
e440a328 6749 }
6750
6751 if (left_type->is_nil_type()
6752 && (op == OPERATOR_EQEQ || op == OPERATOR_NOTEQ))
6753 {
6754 std::swap(left_type, right_type);
2387f644 6755 std::swap(left, right);
e440a328 6756 }
6757
6758 if (right_type->is_nil_type())
6759 {
2387f644 6760 right = Expression::make_nil(location);
e440a328 6761 if (left_type->array_type() != NULL
6762 && left_type->array_type()->length() == NULL)
6763 {
6764 Array_type* at = left_type->array_type();
44dbe1d7 6765 bool is_lvalue = false;
6766 left = at->get_value_pointer(context->gogo(), left, is_lvalue);
e440a328 6767 }
6768 else if (left_type->interface_type() != NULL)
6769 {
6770 // An interface is nil if the first field is nil.
2387f644 6771 left = Expression::make_field_reference(left, 0, location);
e440a328 6772 }
6773 }
6774
ea664253 6775 Bexpression* left_bexpr = left->get_backend(context);
6776 Bexpression* right_bexpr = right->get_backend(context);
e90c9dfc 6777
a32698ee 6778 Gogo* gogo = context->gogo();
6779 Bexpression* ret = gogo->backend()->binary_expression(op, left_bexpr,
6780 right_bexpr, location);
6781 if (result_type != NULL)
6782 ret = gogo->backend()->convert_expression(result_type->get_backend(gogo),
6783 ret, location);
e440a328 6784 return ret;
6785}
6786
736a16ba 6787// Class String_concat_expression.
6788
6789bool
6790String_concat_expression::do_is_constant() const
6791{
6792 for (Expression_list::const_iterator pe = this->exprs_->begin();
6793 pe != this->exprs_->end();
6794 ++pe)
6795 {
6796 if (!(*pe)->is_constant())
6797 return false;
6798 }
6799 return true;
6800}
6801
6802bool
3ae06f68 6803String_concat_expression::do_is_static_initializer() const
736a16ba 6804{
6805 for (Expression_list::const_iterator pe = this->exprs_->begin();
6806 pe != this->exprs_->end();
6807 ++pe)
6808 {
3ae06f68 6809 if (!(*pe)->is_static_initializer())
736a16ba 6810 return false;
6811 }
6812 return true;
6813}
6814
6815Type*
6816String_concat_expression::do_type()
6817{
6818 Type* t = this->exprs_->front()->type();
6819 Expression_list::iterator pe = this->exprs_->begin();
6820 ++pe;
6821 for (; pe != this->exprs_->end(); ++pe)
6822 {
6823 Type* t1;
6824 if (!Binary_expression::operation_type(OPERATOR_PLUS, t,
6825 (*pe)->type(),
6826 &t1))
6827 return Type::make_error_type();
6828 t = t1;
6829 }
6830 return t;
6831}
6832
6833void
6834String_concat_expression::do_determine_type(const Type_context* context)
6835{
6836 Type_context subcontext(*context);
6837 for (Expression_list::iterator pe = this->exprs_->begin();
6838 pe != this->exprs_->end();
6839 ++pe)
6840 {
6841 Type* t = (*pe)->type();
6842 if (!t->is_abstract())
6843 {
6844 subcontext.type = t;
6845 break;
6846 }
6847 }
6848 if (subcontext.type == NULL)
6849 subcontext.type = this->exprs_->front()->type();
6850 for (Expression_list::iterator pe = this->exprs_->begin();
6851 pe != this->exprs_->end();
6852 ++pe)
6853 (*pe)->determine_type(&subcontext);
6854}
6855
6856void
6857String_concat_expression::do_check_types(Gogo*)
6858{
6859 if (this->is_error_expression())
6860 return;
6861 Type* t = this->exprs_->front()->type();
6862 if (t->is_error())
6863 {
6864 this->set_is_error();
6865 return;
6866 }
6867 Expression_list::iterator pe = this->exprs_->begin();
6868 ++pe;
6869 for (; pe != this->exprs_->end(); ++pe)
6870 {
6871 Type* t1 = (*pe)->type();
6872 if (!Type::are_compatible_for_binop(t, t1))
6873 {
6874 this->report_error("incompatible types in binary expression");
6875 return;
6876 }
6877 if (!Binary_expression::check_operator_type(OPERATOR_PLUS, t, t1,
6878 this->location()))
6879 {
6880 this->set_is_error();
6881 return;
6882 }
6883 }
6884}
6885
6886Expression*
6887String_concat_expression::do_flatten(Gogo*, Named_object*,
6888 Statement_inserter*)
6889{
6890 if (this->is_error_expression())
6891 return this;
6892 Location loc = this->location();
6893 Type* type = this->type();
6894 Expression* nil_arg = Expression::make_nil(loc);
6895 Expression* call;
6896 switch (this->exprs_->size())
6897 {
6898 case 0: case 1:
6899 go_unreachable();
6900
6901 case 2: case 3: case 4: case 5:
6902 {
6903 Expression* len = Expression::make_integer_ul(this->exprs_->size(),
6904 NULL, loc);
6905 Array_type* arg_type = Type::make_array_type(type, len);
6906 arg_type->set_is_array_incomparable();
6907 Expression* arg =
6908 Expression::make_array_composite_literal(arg_type, this->exprs_,
6909 loc);
6910 Runtime::Function code;
6911 switch (this->exprs_->size())
6912 {
6913 default:
6914 go_unreachable();
6915 case 2:
6916 code = Runtime::CONCATSTRING2;
6917 break;
6918 case 3:
6919 code = Runtime::CONCATSTRING3;
6920 break;
6921 case 4:
6922 code = Runtime::CONCATSTRING4;
6923 break;
6924 case 5:
6925 code = Runtime::CONCATSTRING5;
6926 break;
6927 }
6928 call = Runtime::make_call(code, loc, 2, nil_arg, arg);
6929 }
6930 break;
6931
6932 default:
6933 {
6934 Type* arg_type = Type::make_array_type(type, NULL);
6935 Slice_construction_expression* sce =
6936 Expression::make_slice_composite_literal(arg_type, this->exprs_,
6937 loc);
6938 sce->set_storage_does_not_escape();
6939 call = Runtime::make_call(Runtime::CONCATSTRINGS, loc, 2, nil_arg,
6940 sce);
6941 }
6942 break;
6943 }
6944
6945 return Expression::make_cast(type, call, loc);
6946}
6947
6948void
6949String_concat_expression::do_dump_expression(
6950 Ast_dump_context* ast_dump_context) const
6951{
6952 ast_dump_context->ostream() << "concat(";
6953 ast_dump_context->dump_expression_list(this->exprs_, false);
6954 ast_dump_context->ostream() << ")";
6955}
6956
6957Expression*
6958Expression::make_string_concat(Expression_list* exprs)
6959{
6960 return new String_concat_expression(exprs);
6961}
6962
e440a328 6963// Class Bound_method_expression.
6964
6965// Traversal.
6966
6967int
6968Bound_method_expression::do_traverse(Traverse* traverse)
6969{
e0659c9e 6970 return Expression::traverse(&this->expr_, traverse);
e440a328 6971}
6972
6973// Return the type of a bound method expression. The type of this
0afbb937 6974// object is simply the type of the method with no receiver.
e440a328 6975
6976Type*
6977Bound_method_expression::do_type()
6978{
0afbb937 6979 Named_object* fn = this->method_->named_object();
6980 Function_type* fntype;
6981 if (fn->is_function())
6982 fntype = fn->func_value()->type();
6983 else if (fn->is_function_declaration())
6984 fntype = fn->func_declaration_value()->type();
e0659c9e 6985 else
6986 return Type::make_error_type();
0afbb937 6987 return fntype->copy_without_receiver();
e440a328 6988}
6989
6990// Determine the types of a method expression.
6991
6992void
6993Bound_method_expression::do_determine_type(const Type_context*)
6994{
0afbb937 6995 Named_object* fn = this->method_->named_object();
6996 Function_type* fntype;
6997 if (fn->is_function())
6998 fntype = fn->func_value()->type();
6999 else if (fn->is_function_declaration())
7000 fntype = fn->func_declaration_value()->type();
7001 else
7002 fntype = NULL;
e440a328 7003 if (fntype == NULL || !fntype->is_method())
7004 this->expr_->determine_type_no_context();
7005 else
7006 {
7007 Type_context subcontext(fntype->receiver()->type(), false);
7008 this->expr_->determine_type(&subcontext);
7009 }
7010}
7011
7012// Check the types of a method expression.
7013
7014void
7015Bound_method_expression::do_check_types(Gogo*)
7016{
0afbb937 7017 Named_object* fn = this->method_->named_object();
7018 if (!fn->is_function() && !fn->is_function_declaration())
7019 {
7020 this->report_error(_("object is not a method"));
7021 return;
7022 }
7023
7024 Function_type* fntype;
7025 if (fn->is_function())
7026 fntype = fn->func_value()->type();
7027 else if (fn->is_function_declaration())
7028 fntype = fn->func_declaration_value()->type();
e440a328 7029 else
0afbb937 7030 go_unreachable();
7031 Type* rtype = fntype->receiver()->type()->deref();
7032 Type* etype = (this->expr_type_ != NULL
7033 ? this->expr_type_
7034 : this->expr_->type());
7035 etype = etype->deref();
3a522dcc 7036 if (!Type::are_identical(rtype, etype, Type::COMPARE_TAGS, NULL))
0afbb937 7037 this->report_error(_("method type does not match object type"));
7038}
7039
7040// If a bound method expression is not simply called, then it is
7041// represented as a closure. The closure will hold a single variable,
7042// the receiver to pass to the method. The function will be a simple
7043// thunk that pulls that value from the closure and calls the method
7044// with the remaining arguments.
7045//
7046// Because method values are not common, we don't build all thunks for
7047// every methods, but instead only build them as we need them. In
7048// particular, we even build them on demand for methods defined in
7049// other packages.
7050
7051Bound_method_expression::Method_value_thunks
7052 Bound_method_expression::method_value_thunks;
7053
7054// Find or create the thunk for METHOD.
7055
7056Named_object*
7057Bound_method_expression::create_thunk(Gogo* gogo, const Method* method,
7058 Named_object* fn)
7059{
7060 std::pair<Named_object*, Named_object*> val(fn, NULL);
7061 std::pair<Method_value_thunks::iterator, bool> ins =
7062 Bound_method_expression::method_value_thunks.insert(val);
7063 if (!ins.second)
7064 {
7065 // We have seen this method before.
7066 go_assert(ins.first->second != NULL);
7067 return ins.first->second;
7068 }
7069
7070 Location loc = fn->location();
7071
7072 Function_type* orig_fntype;
7073 if (fn->is_function())
7074 orig_fntype = fn->func_value()->type();
7075 else if (fn->is_function_declaration())
7076 orig_fntype = fn->func_declaration_value()->type();
7077 else
7078 orig_fntype = NULL;
7079
7080 if (orig_fntype == NULL || !orig_fntype->is_method())
e440a328 7081 {
13f2fdb8 7082 ins.first->second =
7083 Named_object::make_erroneous_name(gogo->thunk_name());
0afbb937 7084 return ins.first->second;
e440a328 7085 }
0afbb937 7086
7087 Struct_field_list* sfl = new Struct_field_list();
f8bdf81a 7088 // The type here is wrong--it should be the C function type. But it
7089 // doesn't really matter.
0afbb937 7090 Type* vt = Type::make_pointer_type(Type::make_void_type());
13f2fdb8 7091 sfl->push_back(Struct_field(Typed_identifier("fn", vt, loc)));
7092 sfl->push_back(Struct_field(Typed_identifier("val",
0afbb937 7093 orig_fntype->receiver()->type(),
7094 loc)));
6bf4793c 7095 Struct_type* st = Type::make_struct_type(sfl, loc);
7096 st->set_is_struct_incomparable();
7097 Type* closure_type = Type::make_pointer_type(st);
0afbb937 7098
f8bdf81a 7099 Function_type* new_fntype = orig_fntype->copy_with_names();
0afbb937 7100
13f2fdb8 7101 std::string thunk_name = gogo->thunk_name();
da244e59 7102 Named_object* new_no = gogo->start_function(thunk_name, new_fntype,
0afbb937 7103 false, loc);
7104
f8bdf81a 7105 Variable* cvar = new Variable(closure_type, NULL, false, false, false, loc);
7106 cvar->set_is_used();
1ecc6157 7107 cvar->set_is_closure();
da244e59 7108 Named_object* cp = Named_object::make_variable("$closure" + thunk_name,
7109 NULL, cvar);
f8bdf81a 7110 new_no->func_value()->set_closure_var(cp);
0afbb937 7111
f8bdf81a 7112 gogo->start_block(loc);
0afbb937 7113
7114 // Field 0 of the closure is the function code pointer, field 1 is
7115 // the value on which to invoke the method.
7116 Expression* arg = Expression::make_var_reference(cp, loc);
f614ea8b 7117 arg = Expression::make_dereference(arg, NIL_CHECK_NOT_NEEDED, loc);
0afbb937 7118 arg = Expression::make_field_reference(arg, 1, loc);
7119
7120 Expression* bme = Expression::make_bound_method(arg, method, fn, loc);
7121
7122 const Typed_identifier_list* orig_params = orig_fntype->parameters();
7123 Expression_list* args;
7124 if (orig_params == NULL || orig_params->empty())
7125 args = NULL;
7126 else
7127 {
7128 const Typed_identifier_list* new_params = new_fntype->parameters();
7129 args = new Expression_list();
7130 for (Typed_identifier_list::const_iterator p = new_params->begin();
f8bdf81a 7131 p != new_params->end();
0afbb937 7132 ++p)
7133 {
7134 Named_object* p_no = gogo->lookup(p->name(), NULL);
7135 go_assert(p_no != NULL
7136 && p_no->is_variable()
7137 && p_no->var_value()->is_parameter());
7138 args->push_back(Expression::make_var_reference(p_no, loc));
7139 }
7140 }
7141
7142 Call_expression* call = Expression::make_call(bme, args,
7143 orig_fntype->is_varargs(),
7144 loc);
7145 call->set_varargs_are_lowered();
7146
7147 Statement* s = Statement::make_return_from_call(call, loc);
7148 gogo->add_statement(s);
7149 Block* b = gogo->finish_block(loc);
7150 gogo->add_block(b, loc);
7151 gogo->lower_block(new_no, b);
a32698ee 7152 gogo->flatten_block(new_no, b);
0afbb937 7153 gogo->finish_function(loc);
7154
7155 ins.first->second = new_no;
7156 return new_no;
7157}
7158
7159// Return an expression to check *REF for nil while dereferencing
7160// according to FIELD_INDEXES. Update *REF to build up the field
7161// reference. This is a static function so that we don't have to
7162// worry about declaring Field_indexes in expressions.h.
7163
7164static Expression*
7165bme_check_nil(const Method::Field_indexes* field_indexes, Location loc,
7166 Expression** ref)
7167{
7168 if (field_indexes == NULL)
7169 return Expression::make_boolean(false, loc);
7170 Expression* cond = bme_check_nil(field_indexes->next, loc, ref);
7171 Struct_type* stype = (*ref)->type()->deref()->struct_type();
7172 go_assert(stype != NULL
7173 && field_indexes->field_index < stype->field_count());
7174 if ((*ref)->type()->struct_type() == NULL)
7175 {
7176 go_assert((*ref)->type()->points_to() != NULL);
7177 Expression* n = Expression::make_binary(OPERATOR_EQEQ, *ref,
7178 Expression::make_nil(loc),
7179 loc);
7180 cond = Expression::make_binary(OPERATOR_OROR, cond, n, loc);
f614ea8b 7181 *ref = Expression::make_dereference(*ref, Expression::NIL_CHECK_DEFAULT,
7182 loc);
0afbb937 7183 go_assert((*ref)->type()->struct_type() == stype);
7184 }
7185 *ref = Expression::make_field_reference(*ref, field_indexes->field_index,
7186 loc);
7187 return cond;
e440a328 7188}
7189
cd39797e 7190// Flatten a method value into a struct with nil checks. We can't do
7191// this in the lowering phase, because if the method value is called
7192// directly we don't need a thunk. That case will have been handled
7193// by Call_expression::do_lower, so if we get here then we do need a
7194// thunk.
e440a328 7195
cd39797e 7196Expression*
7197Bound_method_expression::do_flatten(Gogo* gogo, Named_object*,
7198 Statement_inserter* inserter)
e440a328 7199{
cd39797e 7200 Location loc = this->location();
7201
7202 Named_object* thunk = Bound_method_expression::create_thunk(gogo,
0afbb937 7203 this->method_,
7204 this->function_);
7205 if (thunk->is_erroneous())
7206 {
7207 go_assert(saw_errors());
cd39797e 7208 return Expression::make_error(loc);
0afbb937 7209 }
7210
cd39797e 7211 // Force the expression into a variable. This is only necessary if
7212 // we are going to do nil checks below, but it's easy enough to
7213 // always do it.
7214 Expression* expr = this->expr_;
7215 if (!expr->is_variable())
7216 {
7217 Temporary_statement* etemp = Statement::make_temporary(NULL, expr, loc);
7218 inserter->insert(etemp);
7219 expr = Expression::make_temporary_reference(etemp, loc);
7220 }
0afbb937 7221
7222 // If the method expects a value, and we have a pointer, we need to
7223 // dereference the pointer.
7224
7225 Named_object* fn = this->method_->named_object();
cd39797e 7226 Function_type *fntype;
0afbb937 7227 if (fn->is_function())
7228 fntype = fn->func_value()->type();
7229 else if (fn->is_function_declaration())
7230 fntype = fn->func_declaration_value()->type();
7231 else
7232 go_unreachable();
7233
cd39797e 7234 Expression* val = expr;
0afbb937 7235 if (fntype->receiver()->type()->points_to() == NULL
7236 && val->type()->points_to() != NULL)
f614ea8b 7237 val = Expression::make_dereference(val, NIL_CHECK_DEFAULT, loc);
0afbb937 7238
7239 // Note that we are ignoring this->expr_type_ here. The thunk will
7240 // expect a closure whose second field has type this->expr_type_ (if
7241 // that is not NULL). We are going to pass it a closure whose
7242 // second field has type this->expr_->type(). Since
7243 // this->expr_type_ is only not-NULL for pointer types, we can get
7244 // away with this.
7245
7246 Struct_field_list* fields = new Struct_field_list();
13f2fdb8 7247 fields->push_back(Struct_field(Typed_identifier("fn",
0afbb937 7248 thunk->func_value()->type(),
7249 loc)));
13f2fdb8 7250 fields->push_back(Struct_field(Typed_identifier("val", val->type(), loc)));
0afbb937 7251 Struct_type* st = Type::make_struct_type(fields, loc);
6bf4793c 7252 st->set_is_struct_incomparable();
0afbb937 7253
7254 Expression_list* vals = new Expression_list();
7255 vals->push_back(Expression::make_func_code_reference(thunk, loc));
7256 vals->push_back(val);
7257
7258 Expression* ret = Expression::make_struct_composite_literal(st, vals, loc);
c1177ba4 7259 ret = Expression::make_heap_expression(ret, loc);
0afbb937 7260
c1177ba4 7261 Node* n = Node::make_node(this);
7262 if ((n->encoding() & ESCAPE_MASK) == Node::ESCAPE_NONE)
7263 ret->heap_expression()->set_allocate_on_stack();
7264 else if (gogo->compiling_runtime() && gogo->package_name() == "runtime")
7265 go_error_at(loc, "%s escapes to heap, not allowed in runtime",
7266 n->ast_format(gogo).c_str());
cd39797e 7267
7268 // If necessary, check whether the expression or any embedded
7269 // pointers are nil.
0afbb937 7270
df7ef1fd 7271 Expression* nil_check = NULL;
0afbb937 7272 if (this->method_->field_indexes() != NULL)
7273 {
0afbb937 7274 Expression* ref = expr;
7275 nil_check = bme_check_nil(this->method_->field_indexes(), loc, &ref);
7276 expr = ref;
7277 }
7278
7279 if (this->method_->is_value_method() && expr->type()->points_to() != NULL)
7280 {
7281 Expression* n = Expression::make_binary(OPERATOR_EQEQ, expr,
7282 Expression::make_nil(loc),
7283 loc);
7284 if (nil_check == NULL)
7285 nil_check = n;
7286 else
7287 nil_check = Expression::make_binary(OPERATOR_OROR, nil_check, n, loc);
7288 }
7289
7290 if (nil_check != NULL)
7291 {
cd39797e 7292 Expression* crash = gogo->runtime_error(RUNTIME_ERROR_NIL_DEREFERENCE,
7293 loc);
7294 // Fix the type of the conditional expression by pretending to
7295 // evaluate to RET either way through the conditional.
7296 crash = Expression::make_compound(crash, ret, loc);
7297 ret = Expression::make_conditional(nil_check, crash, ret, loc);
7298 }
7299
7300 // RET is a pointer to a struct, but we want a function type.
7301 ret = Expression::make_unsafe_cast(this->type(), ret, loc);
7302
7303 return ret;
e440a328 7304}
7305
d751bb78 7306// Dump ast representation of a bound method expression.
7307
7308void
7309Bound_method_expression::do_dump_expression(Ast_dump_context* ast_dump_context)
7310 const
7311{
7312 if (this->expr_type_ != NULL)
7313 ast_dump_context->ostream() << "(";
7314 ast_dump_context->dump_expression(this->expr_);
7315 if (this->expr_type_ != NULL)
7316 {
7317 ast_dump_context->ostream() << ":";
7318 ast_dump_context->dump_type(this->expr_type_);
7319 ast_dump_context->ostream() << ")";
7320 }
7321
0afbb937 7322 ast_dump_context->ostream() << "." << this->function_->name();
d751bb78 7323}
7324
e440a328 7325// Make a method expression.
7326
7327Bound_method_expression*
0afbb937 7328Expression::make_bound_method(Expression* expr, const Method* method,
7329 Named_object* function, Location location)
e440a328 7330{
0afbb937 7331 return new Bound_method_expression(expr, method, function, location);
e440a328 7332}
7333
7334// Class Builtin_call_expression. This is used for a call to a
7335// builtin function.
7336
e440a328 7337Builtin_call_expression::Builtin_call_expression(Gogo* gogo,
7338 Expression* fn,
7339 Expression_list* args,
7340 bool is_varargs,
b13c66cd 7341 Location location)
e440a328 7342 : Call_expression(fn, args, is_varargs, location),
6334270b 7343 gogo_(gogo), code_(BUILTIN_INVALID), seen_(false),
7344 recover_arg_is_set_(false)
e440a328 7345{
7346 Func_expression* fnexp = this->fn()->func_expression();
79651b1f 7347 if (fnexp == NULL)
7348 {
7349 this->code_ = BUILTIN_INVALID;
7350 return;
7351 }
e440a328 7352 const std::string& name(fnexp->named_object()->name());
7353 if (name == "append")
7354 this->code_ = BUILTIN_APPEND;
7355 else if (name == "cap")
7356 this->code_ = BUILTIN_CAP;
7357 else if (name == "close")
7358 this->code_ = BUILTIN_CLOSE;
48080209 7359 else if (name == "complex")
7360 this->code_ = BUILTIN_COMPLEX;
e440a328 7361 else if (name == "copy")
7362 this->code_ = BUILTIN_COPY;
1cce762f 7363 else if (name == "delete")
7364 this->code_ = BUILTIN_DELETE;
e440a328 7365 else if (name == "imag")
7366 this->code_ = BUILTIN_IMAG;
7367 else if (name == "len")
7368 this->code_ = BUILTIN_LEN;
7369 else if (name == "make")
7370 this->code_ = BUILTIN_MAKE;
7371 else if (name == "new")
7372 this->code_ = BUILTIN_NEW;
7373 else if (name == "panic")
7374 this->code_ = BUILTIN_PANIC;
7375 else if (name == "print")
7376 this->code_ = BUILTIN_PRINT;
7377 else if (name == "println")
7378 this->code_ = BUILTIN_PRINTLN;
7379 else if (name == "real")
7380 this->code_ = BUILTIN_REAL;
7381 else if (name == "recover")
7382 this->code_ = BUILTIN_RECOVER;
7383 else if (name == "Alignof")
7384 this->code_ = BUILTIN_ALIGNOF;
7385 else if (name == "Offsetof")
7386 this->code_ = BUILTIN_OFFSETOF;
7387 else if (name == "Sizeof")
7388 this->code_ = BUILTIN_SIZEOF;
7389 else
c3e6f413 7390 go_unreachable();
e440a328 7391}
7392
7393// Return whether this is a call to recover. This is a virtual
7394// function called from the parent class.
7395
7396bool
7397Builtin_call_expression::do_is_recover_call() const
7398{
7399 if (this->classification() == EXPRESSION_ERROR)
7400 return false;
7401 return this->code_ == BUILTIN_RECOVER;
7402}
7403
7404// Set the argument for a call to recover.
7405
7406void
7407Builtin_call_expression::do_set_recover_arg(Expression* arg)
7408{
7409 const Expression_list* args = this->args();
c484d925 7410 go_assert(args == NULL || args->empty());
e440a328 7411 Expression_list* new_args = new Expression_list();
7412 new_args->push_back(arg);
7413 this->set_args(new_args);
6334270b 7414 this->recover_arg_is_set_ = true;
e440a328 7415}
7416
e440a328 7417// Lower a builtin call expression. This turns new and make into
7418// specific expressions. We also convert to a constant if we can.
7419
7420Expression*
321e5ad2 7421Builtin_call_expression::do_lower(Gogo*, Named_object* function,
ceeb4318 7422 Statement_inserter* inserter, int)
e440a328 7423{
79651b1f 7424 if (this->is_error_expression())
a9182619 7425 return this;
7426
b13c66cd 7427 Location loc = this->location();
1cce762f 7428
a8725655 7429 if (this->is_varargs() && this->code_ != BUILTIN_APPEND)
7430 {
7431 this->report_error(_("invalid use of %<...%> with builtin function"));
1cce762f 7432 return Expression::make_error(loc);
a8725655 7433 }
7434
393ba00b 7435 if (this->code_ == BUILTIN_OFFSETOF)
7436 {
7437 Expression* arg = this->one_arg();
12e69faa 7438
7439 if (arg->bound_method_expression() != NULL
7440 || arg->interface_field_reference_expression() != NULL)
7441 {
7442 this->report_error(_("invalid use of method value as argument "
7443 "of Offsetof"));
7444 return this;
7445 }
7446
393ba00b 7447 Field_reference_expression* farg = arg->field_reference_expression();
7448 while (farg != NULL)
7449 {
7450 if (!farg->implicit())
7451 break;
7452 // When the selector refers to an embedded field,
7453 // it must not be reached through pointer indirections.
7454 if (farg->expr()->deref() != farg->expr())
7455 {
12e69faa 7456 this->report_error(_("argument of Offsetof implies "
7457 "indirection of an embedded field"));
393ba00b 7458 return this;
7459 }
7460 // Go up until we reach the original base.
7461 farg = farg->expr()->field_reference_expression();
7462 }
7463 }
7464
1cce762f 7465 if (this->is_constant())
e440a328 7466 {
0c77715b 7467 Numeric_constant nc;
7468 if (this->numeric_constant_value(&nc))
7469 return nc.expression(loc);
e440a328 7470 }
1cce762f 7471
7472 switch (this->code_)
e440a328 7473 {
1cce762f 7474 default:
7475 break;
7476
7477 case BUILTIN_NEW:
7478 {
7479 const Expression_list* args = this->args();
7480 if (args == NULL || args->size() < 1)
7481 this->report_error(_("not enough arguments"));
7482 else if (args->size() > 1)
7483 this->report_error(_("too many arguments"));
7484 else
7485 {
7486 Expression* arg = args->front();
7487 if (!arg->is_type_expression())
7488 {
631d5788 7489 go_error_at(arg->location(), "expected type");
1cce762f 7490 this->set_is_error();
7491 }
7492 else
7493 return Expression::make_allocation(arg->type(), loc);
7494 }
7495 }
7496 break;
7497
7498 case BUILTIN_MAKE:
321e5ad2 7499 return this->lower_make(inserter);
1cce762f 7500
7501 case BUILTIN_RECOVER:
e440a328 7502 if (function != NULL)
7503 function->func_value()->set_calls_recover();
7504 else
7505 {
7506 // Calling recover outside of a function always returns the
7507 // nil empty interface.
823c7e3d 7508 Type* eface = Type::make_empty_interface_type(loc);
1cce762f 7509 return Expression::make_cast(eface, Expression::make_nil(loc), loc);
e440a328 7510 }
1cce762f 7511 break;
7512
1cce762f 7513 case BUILTIN_DELETE:
7514 {
7515 // Lower to a runtime function call.
7516 const Expression_list* args = this->args();
7517 if (args == NULL || args->size() < 2)
7518 this->report_error(_("not enough arguments"));
7519 else if (args->size() > 2)
7520 this->report_error(_("too many arguments"));
7521 else if (args->front()->type()->map_type() == NULL)
7522 this->report_error(_("argument 1 must be a map"));
7523 else
7524 {
7525 // Since this function returns no value it must appear in
7526 // a statement by itself, so we don't have to worry about
7527 // order of evaluation of values around it. Evaluate the
7528 // map first to get order of evaluation right.
7529 Map_type* mt = args->front()->type()->map_type();
7530 Temporary_statement* map_temp =
7531 Statement::make_temporary(mt, args->front(), loc);
7532 inserter->insert(map_temp);
7533
7534 Temporary_statement* key_temp =
7535 Statement::make_temporary(mt->key_type(), args->back(), loc);
7536 inserter->insert(key_temp);
7537
0d5530d9 7538 Expression* e1 = Expression::make_type_descriptor(mt, loc);
7539 Expression* e2 = Expression::make_temporary_reference(map_temp,
1cce762f 7540 loc);
0d5530d9 7541 Expression* e3 = Expression::make_temporary_reference(key_temp,
1cce762f 7542 loc);
28819633 7543
7544 // If the call to delete is deferred, and is in a loop,
7545 // then the loop will only have a single instance of the
7546 // temporary variable. Passing the address of the
7547 // temporary variable here means that the deferred call
7548 // will see the last value in the loop, not the current
7549 // value. So for this unusual case copy the value into
7550 // the heap.
7551 if (!this->is_deferred())
7552 e3 = Expression::make_unary(OPERATOR_AND, e3, loc);
7553 else
7554 {
7555 Expression* a = Expression::make_allocation(mt->key_type(),
7556 loc);
7557 Temporary_statement* atemp =
7558 Statement::make_temporary(NULL, a, loc);
7559 inserter->insert(atemp);
7560
7561 a = Expression::make_temporary_reference(atemp, loc);
7562 a = Expression::make_dereference(a, NIL_CHECK_NOT_NEEDED, loc);
7563 Statement* s = Statement::make_assignment(a, e3, loc);
7564 inserter->insert(s);
7565
7566 e3 = Expression::make_temporary_reference(atemp, loc);
7567 }
7568
1cce762f 7569 return Runtime::make_call(Runtime::MAPDELETE, this->location(),
0d5530d9 7570 3, e1, e2, e3);
1cce762f 7571 }
7572 }
7573 break;
88b03a70 7574
7575 case BUILTIN_PRINT:
7576 case BUILTIN_PRINTLN:
7577 // Force all the arguments into temporary variables, so that we
7578 // don't try to evaluate something while holding the print lock.
7579 if (this->args() == NULL)
7580 break;
7581 for (Expression_list::iterator pa = this->args()->begin();
7582 pa != this->args()->end();
7583 ++pa)
7584 {
493ce3ee 7585 if (!(*pa)->is_variable() && !(*pa)->is_constant())
88b03a70 7586 {
7587 Temporary_statement* temp =
7588 Statement::make_temporary(NULL, *pa, loc);
7589 inserter->insert(temp);
7590 *pa = Expression::make_temporary_reference(temp, loc);
7591 }
7592 }
7593 break;
e440a328 7594 }
7595
7596 return this;
7597}
7598
35a54f17 7599// Flatten a builtin call expression. This turns the arguments of copy and
7600// append into temporary expressions.
7601
7602Expression*
321e5ad2 7603Builtin_call_expression::do_flatten(Gogo* gogo, Named_object* function,
35a54f17 7604 Statement_inserter* inserter)
7605{
16cb7fec 7606 Location loc = this->location();
7607
7608 switch (this->code_)
35a54f17 7609 {
16cb7fec 7610 default:
7611 break;
7612
7613 case BUILTIN_APPEND:
d3c55148 7614 return this->flatten_append(gogo, function, inserter, NULL, NULL);
321e5ad2 7615
16cb7fec 7616 case BUILTIN_COPY:
7617 {
7618 Type* at = this->args()->front()->type();
7619 for (Expression_list::iterator pa = this->args()->begin();
7620 pa != this->args()->end();
7621 ++pa)
7622 {
7623 if ((*pa)->is_nil_expression())
7624 {
7625 Expression* nil = Expression::make_nil(loc);
7626 Expression* zero = Expression::make_integer_ul(0, NULL, loc);
7627 *pa = Expression::make_slice_value(at, nil, zero, zero, loc);
7628 }
7629 if (!(*pa)->is_variable())
7630 {
7631 Temporary_statement* temp =
7632 Statement::make_temporary(NULL, *pa, loc);
7633 inserter->insert(temp);
7634 *pa = Expression::make_temporary_reference(temp, loc);
7635 }
7636 }
7637 }
7638 break;
7639
7640 case BUILTIN_PANIC:
35a54f17 7641 for (Expression_list::iterator pa = this->args()->begin();
16cb7fec 7642 pa != this->args()->end();
7643 ++pa)
7644 {
7645 if (!(*pa)->is_variable() && (*pa)->type()->interface_type() != NULL)
55e8ba6a 7646 {
16cb7fec 7647 Temporary_statement* temp =
7648 Statement::make_temporary(NULL, *pa, loc);
7649 inserter->insert(temp);
7650 *pa = Expression::make_temporary_reference(temp, loc);
55e8ba6a 7651 }
16cb7fec 7652 }
7739537f 7653 break;
0d5530d9 7654
7655 case BUILTIN_LEN:
132ed071 7656 case BUILTIN_CAP:
321e5ad2 7657 {
7658 Expression_list::iterator pa = this->args()->begin();
7659 if (!(*pa)->is_variable()
7660 && ((*pa)->type()->map_type() != NULL
7661 || (*pa)->type()->channel_type() != NULL))
7662 {
7663 Temporary_statement* temp =
7664 Statement::make_temporary(NULL, *pa, loc);
7665 inserter->insert(temp);
7666 *pa = Expression::make_temporary_reference(temp, loc);
7667 }
7668 }
7669 break;
35a54f17 7670 }
16cb7fec 7671
35a54f17 7672 return this;
7673}
7674
a9182619 7675// Lower a make expression.
7676
7677Expression*
321e5ad2 7678Builtin_call_expression::lower_make(Statement_inserter* inserter)
a9182619 7679{
b13c66cd 7680 Location loc = this->location();
a9182619 7681
7682 const Expression_list* args = this->args();
7683 if (args == NULL || args->size() < 1)
7684 {
7685 this->report_error(_("not enough arguments"));
7686 return Expression::make_error(this->location());
7687 }
7688
7689 Expression_list::const_iterator parg = args->begin();
7690
7691 Expression* first_arg = *parg;
7692 if (!first_arg->is_type_expression())
7693 {
631d5788 7694 go_error_at(first_arg->location(), "expected type");
a9182619 7695 this->set_is_error();
7696 return Expression::make_error(this->location());
7697 }
7698 Type* type = first_arg->type();
7699
22deed0d 7700 if (!type->in_heap())
7701 go_error_at(first_arg->location(),
7702 "can't make slice of go:notinheap type");
7703
a9182619 7704 bool is_slice = false;
7705 bool is_map = false;
7706 bool is_chan = false;
411eb89e 7707 if (type->is_slice_type())
a9182619 7708 is_slice = true;
7709 else if (type->map_type() != NULL)
7710 is_map = true;
7711 else if (type->channel_type() != NULL)
7712 is_chan = true;
7713 else
7714 {
7715 this->report_error(_("invalid type for make function"));
7716 return Expression::make_error(this->location());
7717 }
7718
f6bc81e6 7719 Type_context int_context(Type::lookup_integer_type("int"), false);
7720
a9182619 7721 ++parg;
7722 Expression* len_arg;
ccea2b36 7723 bool len_small = false;
a9182619 7724 if (parg == args->end())
7725 {
7726 if (is_slice)
7727 {
7728 this->report_error(_("length required when allocating a slice"));
7729 return Expression::make_error(this->location());
7730 }
e67508fa 7731 len_arg = Expression::make_integer_ul(0, NULL, loc);
33d1d391 7732 len_small = true;
a9182619 7733 }
7734 else
7735 {
7736 len_arg = *parg;
f6bc81e6 7737 len_arg->determine_type(&int_context);
a065edc5 7738 if (len_arg->type()->integer_type() == NULL)
7739 {
7740 go_error_at(len_arg->location(), "non-integer len argument in make");
7741 return Expression::make_error(this->location());
7742 }
ccea2b36 7743 if (!this->check_int_value(len_arg, true, &len_small))
1ad00fd4 7744 return Expression::make_error(this->location());
a9182619 7745 ++parg;
7746 }
7747
7748 Expression* cap_arg = NULL;
ccea2b36 7749 bool cap_small = false;
72bf0e6e 7750 Numeric_constant nclen;
7751 Numeric_constant nccap;
7752 unsigned long vlen;
7753 unsigned long vcap;
a9182619 7754 if (is_slice && parg != args->end())
7755 {
7756 cap_arg = *parg;
f6bc81e6 7757 cap_arg->determine_type(&int_context);
a065edc5 7758 if (cap_arg->type()->integer_type() == NULL)
7759 {
7760 go_error_at(cap_arg->location(), "non-integer cap argument in make");
7761 return Expression::make_error(this->location());
7762 }
ccea2b36 7763 if (!this->check_int_value(cap_arg, false, &cap_small))
1ad00fd4 7764 return Expression::make_error(this->location());
7765
1ad00fd4 7766 if (len_arg->numeric_constant_value(&nclen)
7767 && cap_arg->numeric_constant_value(&nccap)
7768 && nclen.to_unsigned_long(&vlen) == Numeric_constant::NC_UL_VALID
7769 && nccap.to_unsigned_long(&vcap) == Numeric_constant::NC_UL_VALID
7770 && vlen > vcap)
a9182619 7771 {
1ad00fd4 7772 this->report_error(_("len larger than cap"));
a9182619 7773 return Expression::make_error(this->location());
7774 }
1ad00fd4 7775
a9182619 7776 ++parg;
7777 }
7778
7779 if (parg != args->end())
7780 {
7781 this->report_error(_("too many arguments to make"));
7782 return Expression::make_error(this->location());
7783 }
7784
b13c66cd 7785 Location type_loc = first_arg->location();
a9182619 7786
7787 Expression* call;
7788 if (is_slice)
7789 {
d633d0fb 7790 Temporary_statement* len_temp = NULL;
7791 if (!len_arg->is_constant())
7792 {
7793 len_temp = Statement::make_temporary(NULL, len_arg, loc);
7794 inserter->insert(len_temp);
7795 len_arg = Expression::make_temporary_reference(len_temp, loc);
7796 }
7797
a9182619 7798 if (cap_arg == NULL)
321e5ad2 7799 {
72bf0e6e 7800 cap_small = len_small;
d633d0fb 7801 if (len_temp == NULL)
7802 cap_arg = len_arg->copy();
7803 else
7804 cap_arg = Expression::make_temporary_reference(len_temp, loc);
7805 }
7806 else if (!cap_arg->is_constant())
7807 {
7808 Temporary_statement* cap_temp = Statement::make_temporary(NULL,
7809 cap_arg,
7810 loc);
7811 inserter->insert(cap_temp);
7812 cap_arg = Expression::make_temporary_reference(cap_temp, loc);
321e5ad2 7813 }
ccea2b36 7814
72bf0e6e 7815 Type* et = type->array_type()->element_type();
7816 Expression* type_arg = Expression::make_type_descriptor(et, type_loc);
ccea2b36 7817 Runtime::Function code = Runtime::MAKESLICE;
7818 if (!len_small || !cap_small)
7819 code = Runtime::MAKESLICE64;
d633d0fb 7820 Expression* mem = Runtime::make_call(code, loc, 3, type_arg, len_arg,
7821 cap_arg);
7822 mem = Expression::make_unsafe_cast(Type::make_pointer_type(et), mem,
7823 loc);
f81232c1 7824 Type* int_type = Type::lookup_integer_type("int");
7825 len_arg = Expression::make_cast(int_type, len_arg->copy(), loc);
7826 cap_arg = Expression::make_cast(int_type, cap_arg->copy(), loc);
7827 call = Expression::make_slice_value(type, mem, len_arg, cap_arg, loc);
a9182619 7828 }
7829 else if (is_map)
321e5ad2 7830 {
7831 Expression* type_arg = Expression::make_type_descriptor(type, type_loc);
33d1d391 7832 if (!len_small)
7833 call = Runtime::make_call(Runtime::MAKEMAP64, loc, 3, type_arg,
7834 len_arg,
7835 Expression::make_nil(loc));
7836 else
7837 {
7838 Numeric_constant nclen;
7839 unsigned long vlen;
7840 if (len_arg->numeric_constant_value(&nclen)
7841 && nclen.to_unsigned_long(&vlen) == Numeric_constant::NC_UL_VALID
7842 && vlen <= Map_type::bucket_size)
7843 call = Runtime::make_call(Runtime::MAKEMAP_SMALL, loc, 0);
7844 else
7845 call = Runtime::make_call(Runtime::MAKEMAP, loc, 3, type_arg,
7846 len_arg,
7847 Expression::make_nil(loc));
7848 }
321e5ad2 7849 }
a9182619 7850 else if (is_chan)
321e5ad2 7851 {
7852 Expression* type_arg = Expression::make_type_descriptor(type, type_loc);
1423c90a 7853 Runtime::Function code = Runtime::MAKECHAN;
7854 if (!len_small)
7855 code = Runtime::MAKECHAN64;
7856 call = Runtime::make_call(code, loc, 2, type_arg, len_arg);
321e5ad2 7857 }
a9182619 7858 else
7859 go_unreachable();
7860
7861 return Expression::make_unsafe_cast(type, call, loc);
7862}
7863
321e5ad2 7864// Flatten a call to the predeclared append function. We do this in
7865// the flatten phase, not the lowering phase, so that we run after
d3c55148 7866// type checking and after order_evaluations. If ASSIGN_LHS is not
7867// NULL, this append is the right-hand-side of an assignment and
7868// ASSIGN_LHS is the left-hand-side; in that case, set LHS directly
7869// rather than returning a slice. This lets us omit a write barrier
7870// in common cases like a = append(a, ...) when the slice does not
7871// need to grow. ENCLOSING is not NULL iff ASSIGN_LHS is not NULL.
321e5ad2 7872
7873Expression*
7874Builtin_call_expression::flatten_append(Gogo* gogo, Named_object* function,
d3c55148 7875 Statement_inserter* inserter,
7876 Expression* assign_lhs,
7877 Block* enclosing)
321e5ad2 7878{
7879 if (this->is_error_expression())
7880 return this;
7881
7882 Location loc = this->location();
7883
7884 const Expression_list* args = this->args();
7885 go_assert(args != NULL && !args->empty());
7886
7887 Type* slice_type = args->front()->type();
7888 go_assert(slice_type->is_slice_type());
7889 Type* element_type = slice_type->array_type()->element_type();
7890
7891 if (args->size() == 1)
7892 {
7893 // append(s) evaluates to s.
d3c55148 7894 if (assign_lhs != NULL)
7895 return NULL;
321e5ad2 7896 return args->front();
7897 }
7898
7899 Type* int_type = Type::lookup_integer_type("int");
7900 Type* uint_type = Type::lookup_integer_type("uint");
7901
7902 // Implementing
7903 // append(s1, s2...)
7904 // or
7905 // append(s1, a1, a2, a3, ...)
7906
7907 // s1tmp := s1
7908 Temporary_statement* s1tmp = Statement::make_temporary(NULL, args->front(),
7909 loc);
7910 inserter->insert(s1tmp);
7911
7912 // l1tmp := len(s1tmp)
7913 Named_object* lenfn = gogo->lookup_global("len");
7914 Expression* lenref = Expression::make_func_reference(lenfn, NULL, loc);
7915 Expression_list* call_args = new Expression_list();
7916 call_args->push_back(Expression::make_temporary_reference(s1tmp, loc));
7917 Expression* len = Expression::make_call(lenref, call_args, false, loc);
7918 gogo->lower_expression(function, inserter, &len);
7919 gogo->flatten_expression(function, inserter, &len);
7920 Temporary_statement* l1tmp = Statement::make_temporary(int_type, len, loc);
7921 inserter->insert(l1tmp);
7922
7923 Temporary_statement* s2tmp = NULL;
7924 Temporary_statement* l2tmp = NULL;
7925 Expression_list* add = NULL;
7926 Expression* len2;
7927 if (this->is_varargs())
7928 {
7929 go_assert(args->size() == 2);
7930
7931 // s2tmp := s2
7932 s2tmp = Statement::make_temporary(NULL, args->back(), loc);
7933 inserter->insert(s2tmp);
7934
7935 // l2tmp := len(s2tmp)
7936 lenref = Expression::make_func_reference(lenfn, NULL, loc);
7937 call_args = new Expression_list();
7938 call_args->push_back(Expression::make_temporary_reference(s2tmp, loc));
7939 len = Expression::make_call(lenref, call_args, false, loc);
7940 gogo->lower_expression(function, inserter, &len);
7941 gogo->flatten_expression(function, inserter, &len);
7942 l2tmp = Statement::make_temporary(int_type, len, loc);
7943 inserter->insert(l2tmp);
7944
7945 // len2 = l2tmp
7946 len2 = Expression::make_temporary_reference(l2tmp, loc);
7947 }
7948 else
7949 {
7950 // We have to ensure that all the arguments are in variables
7951 // now, because otherwise if one of them is an index expression
7952 // into the current slice we could overwrite it before we fetch
7953 // it.
7954 add = new Expression_list();
7955 Expression_list::const_iterator pa = args->begin();
7956 for (++pa; pa != args->end(); ++pa)
7957 {
7958 if ((*pa)->is_variable())
7959 add->push_back(*pa);
7960 else
7961 {
7962 Temporary_statement* tmp = Statement::make_temporary(NULL, *pa,
7963 loc);
7964 inserter->insert(tmp);
7965 add->push_back(Expression::make_temporary_reference(tmp, loc));
7966 }
7967 }
7968
7969 // len2 = len(add)
7970 len2 = Expression::make_integer_ul(add->size(), int_type, loc);
7971 }
7972
7973 // ntmp := l1tmp + len2
7974 Expression* ref = Expression::make_temporary_reference(l1tmp, loc);
7975 Expression* sum = Expression::make_binary(OPERATOR_PLUS, ref, len2, loc);
7976 gogo->lower_expression(function, inserter, &sum);
7977 gogo->flatten_expression(function, inserter, &sum);
7978 Temporary_statement* ntmp = Statement::make_temporary(int_type, sum, loc);
7979 inserter->insert(ntmp);
7980
7981 // s1tmp = uint(ntmp) > uint(cap(s1tmp)) ?
7982 // growslice(type, s1tmp, ntmp) :
7983 // s1tmp[:ntmp]
7984 // Using uint here means that if the computation of ntmp overflowed,
7985 // we will call growslice which will panic.
7986
7987 Expression* left = Expression::make_temporary_reference(ntmp, loc);
7988 left = Expression::make_cast(uint_type, left, loc);
7989
7990 Named_object* capfn = gogo->lookup_global("cap");
7991 Expression* capref = Expression::make_func_reference(capfn, NULL, loc);
7992 call_args = new Expression_list();
7993 call_args->push_back(Expression::make_temporary_reference(s1tmp, loc));
7994 Expression* right = Expression::make_call(capref, call_args, false, loc);
7995 right = Expression::make_cast(uint_type, right, loc);
7996
7997 Expression* cond = Expression::make_binary(OPERATOR_GT, left, right, loc);
7998
7999 Expression* a1 = Expression::make_type_descriptor(element_type, loc);
8000 Expression* a2 = Expression::make_temporary_reference(s1tmp, loc);
8001 Expression* a3 = Expression::make_temporary_reference(ntmp, loc);
8002 Expression* call = Runtime::make_call(Runtime::GROWSLICE, loc, 3,
8003 a1, a2, a3);
8004 call = Expression::make_unsafe_cast(slice_type, call, loc);
8005
8006 ref = Expression::make_temporary_reference(s1tmp, loc);
8007 Expression* zero = Expression::make_integer_ul(0, int_type, loc);
8008 Expression* ref2 = Expression::make_temporary_reference(ntmp, loc);
8009 // FIXME: Mark this index as not requiring bounds checks.
8010 ref = Expression::make_index(ref, zero, ref2, NULL, loc);
8011
d3c55148 8012 if (assign_lhs == NULL)
8013 {
8014 Expression* rhs = Expression::make_conditional(cond, call, ref, loc);
8015
8016 gogo->lower_expression(function, inserter, &rhs);
8017 gogo->flatten_expression(function, inserter, &rhs);
8018
8019 ref = Expression::make_temporary_reference(s1tmp, loc);
8020 Statement* assign = Statement::make_assignment(ref, rhs, loc);
8021 inserter->insert(assign);
8022 }
8023 else
8024 {
8025 gogo->lower_expression(function, inserter, &cond);
8026 gogo->flatten_expression(function, inserter, &cond);
8027 gogo->lower_expression(function, inserter, &call);
8028 gogo->flatten_expression(function, inserter, &call);
8029 gogo->lower_expression(function, inserter, &ref);
8030 gogo->flatten_expression(function, inserter, &ref);
8031
8032 Block* then_block = new Block(enclosing, loc);
8033 Assignment_statement* assign =
8034 Statement::make_assignment(assign_lhs, call, loc);
8035 then_block->add_statement(assign);
321e5ad2 8036
d3c55148 8037 Block* else_block = new Block(enclosing, loc);
8038 assign = Statement::make_assignment(assign_lhs->copy(), ref, loc);
8039 // This assignment will not change the pointer value, so it does
8040 // not need a write barrier.
8041 assign->set_omit_write_barrier();
8042 else_block->add_statement(assign);
321e5ad2 8043
d3c55148 8044 Statement* s = Statement::make_if_statement(cond, then_block,
8045 else_block, loc);
8046 inserter->insert(s);
8047
8048 ref = Expression::make_temporary_reference(s1tmp, loc);
8049 assign = Statement::make_assignment(ref, assign_lhs->copy(), loc);
8050 inserter->insert(assign);
8051 }
321e5ad2 8052
8053 if (this->is_varargs())
8054 {
8055 // copy(s1tmp[l1tmp:], s2tmp)
8056 a1 = Expression::make_temporary_reference(s1tmp, loc);
8057 ref = Expression::make_temporary_reference(l1tmp, loc);
8058 Expression* nil = Expression::make_nil(loc);
8059 // FIXME: Mark this index as not requiring bounds checks.
8060 a1 = Expression::make_index(a1, ref, nil, NULL, loc);
8061
8062 a2 = Expression::make_temporary_reference(s2tmp, loc);
8063
8064 Named_object* copyfn = gogo->lookup_global("copy");
8065 Expression* copyref = Expression::make_func_reference(copyfn, NULL, loc);
8066 call_args = new Expression_list();
8067 call_args->push_back(a1);
8068 call_args->push_back(a2);
8069 call = Expression::make_call(copyref, call_args, false, loc);
8070 gogo->lower_expression(function, inserter, &call);
8071 gogo->flatten_expression(function, inserter, &call);
8072 inserter->insert(Statement::make_statement(call, false));
8073 }
8074 else
8075 {
8076 // For each argument:
8077 // s1tmp[l1tmp+i] = a
8078 unsigned long i = 0;
8079 for (Expression_list::const_iterator pa = add->begin();
8080 pa != add->end();
8081 ++pa, ++i)
8082 {
8083 ref = Expression::make_temporary_reference(s1tmp, loc);
8084 ref2 = Expression::make_temporary_reference(l1tmp, loc);
8085 Expression* off = Expression::make_integer_ul(i, int_type, loc);
8086 ref2 = Expression::make_binary(OPERATOR_PLUS, ref2, off, loc);
8087 // FIXME: Mark this index as not requiring bounds checks.
d3c55148 8088 Expression* lhs = Expression::make_index(ref, ref2, NULL, NULL,
8089 loc);
321e5ad2 8090 gogo->lower_expression(function, inserter, &lhs);
8091 gogo->flatten_expression(function, inserter, &lhs);
03118c21 8092 // The flatten pass runs after the write barrier pass, so we
8093 // need to insert a write barrier here if necessary.
d3c55148 8094 // However, if ASSIGN_LHS is not NULL, we have been called
8095 // directly before the write barrier pass.
8096 Statement* assign;
8097 if (assign_lhs != NULL
8098 || !gogo->assign_needs_write_barrier(lhs))
03118c21 8099 assign = Statement::make_assignment(lhs, *pa, loc);
8100 else
8101 {
8102 Function* f = function == NULL ? NULL : function->func_value();
8103 assign = gogo->assign_with_write_barrier(f, NULL, inserter,
8104 lhs, *pa, loc);
8105 }
321e5ad2 8106 inserter->insert(assign);
8107 }
8108 }
8109
d3c55148 8110 if (assign_lhs != NULL)
8111 return NULL;
8112
321e5ad2 8113 return Expression::make_temporary_reference(s1tmp, loc);
8114}
8115
a9182619 8116// Return whether an expression has an integer value. Report an error
8117// if not. This is used when handling calls to the predeclared make
ccea2b36 8118// function. Set *SMALL if the value is known to fit in type "int".
a9182619 8119
8120bool
ccea2b36 8121Builtin_call_expression::check_int_value(Expression* e, bool is_length,
8122 bool *small)
a9182619 8123{
ccea2b36 8124 *small = false;
8125
0c77715b 8126 Numeric_constant nc;
1ad00fd4 8127 if (e->numeric_constant_value(&nc))
a9182619 8128 {
1ad00fd4 8129 unsigned long v;
8130 switch (nc.to_unsigned_long(&v))
8131 {
8132 case Numeric_constant::NC_UL_VALID:
1b10c5e7 8133 break;
1ad00fd4 8134 case Numeric_constant::NC_UL_NOTINT:
631d5788 8135 go_error_at(e->location(), "non-integer %s argument to make",
8136 is_length ? "len" : "cap");
1ad00fd4 8137 return false;
8138 case Numeric_constant::NC_UL_NEGATIVE:
631d5788 8139 go_error_at(e->location(), "negative %s argument to make",
8140 is_length ? "len" : "cap");
1ad00fd4 8141 return false;
8142 case Numeric_constant::NC_UL_BIG:
8143 // We don't want to give a compile-time error for a 64-bit
8144 // value on a 32-bit target.
1b10c5e7 8145 break;
1ad00fd4 8146 }
1b10c5e7 8147
8148 mpz_t val;
8149 if (!nc.to_int(&val))
8150 go_unreachable();
8151 int bits = mpz_sizeinbase(val, 2);
8152 mpz_clear(val);
8153 Type* int_type = Type::lookup_integer_type("int");
8154 if (bits >= int_type->integer_type()->bits())
8155 {
631d5788 8156 go_error_at(e->location(), "%s argument too large for make",
8157 is_length ? "len" : "cap");
1b10c5e7 8158 return false;
8159 }
8160
ccea2b36 8161 *small = true;
1b10c5e7 8162 return true;
a9182619 8163 }
8164
1ad00fd4 8165 if (e->type()->integer_type() != NULL)
ccea2b36 8166 {
8167 int ebits = e->type()->integer_type()->bits();
8168 int intbits = Type::lookup_integer_type("int")->integer_type()->bits();
8169
8170 // We can treat ebits == intbits as small even for an unsigned
8171 // integer type, because we will convert the value to int and
8172 // then reject it in the runtime if it is negative.
8173 *small = ebits <= intbits;
8174
8175 return true;
8176 }
1ad00fd4 8177
631d5788 8178 go_error_at(e->location(), "non-integer %s argument to make",
8179 is_length ? "len" : "cap");
a9182619 8180 return false;
8181}
8182
e440a328 8183// Return the type of the real or imag functions, given the type of
fcbea5e4 8184// the argument. We need to map complex64 to float32 and complex128
8185// to float64, so it has to be done by name. This returns NULL if it
8186// can't figure out the type.
e440a328 8187
8188Type*
8189Builtin_call_expression::real_imag_type(Type* arg_type)
8190{
8191 if (arg_type == NULL || arg_type->is_abstract())
8192 return NULL;
8193 Named_type* nt = arg_type->named_type();
8194 if (nt == NULL)
8195 return NULL;
8196 while (nt->real_type()->named_type() != NULL)
8197 nt = nt->real_type()->named_type();
48080209 8198 if (nt->name() == "complex64")
e440a328 8199 return Type::lookup_float_type("float32");
8200 else if (nt->name() == "complex128")
8201 return Type::lookup_float_type("float64");
8202 else
8203 return NULL;
8204}
8205
48080209 8206// Return the type of the complex function, given the type of one of the
e440a328 8207// argments. Like real_imag_type, we have to map by name.
8208
8209Type*
48080209 8210Builtin_call_expression::complex_type(Type* arg_type)
e440a328 8211{
8212 if (arg_type == NULL || arg_type->is_abstract())
8213 return NULL;
8214 Named_type* nt = arg_type->named_type();
8215 if (nt == NULL)
8216 return NULL;
8217 while (nt->real_type()->named_type() != NULL)
8218 nt = nt->real_type()->named_type();
48080209 8219 if (nt->name() == "float32")
e440a328 8220 return Type::lookup_complex_type("complex64");
8221 else if (nt->name() == "float64")
8222 return Type::lookup_complex_type("complex128");
8223 else
8224 return NULL;
8225}
8226
8227// Return a single argument, or NULL if there isn't one.
8228
8229Expression*
8230Builtin_call_expression::one_arg() const
8231{
8232 const Expression_list* args = this->args();
aa615cb3 8233 if (args == NULL || args->size() != 1)
e440a328 8234 return NULL;
8235 return args->front();
8236}
8237
83921647 8238// A traversal class which looks for a call or receive expression.
8239
8240class Find_call_expression : public Traverse
8241{
8242 public:
8243 Find_call_expression()
8244 : Traverse(traverse_expressions),
8245 found_(false)
8246 { }
8247
8248 int
8249 expression(Expression**);
8250
8251 bool
8252 found()
8253 { return this->found_; }
8254
8255 private:
8256 bool found_;
8257};
8258
8259int
8260Find_call_expression::expression(Expression** pexpr)
8261{
4714afb2 8262 Expression* expr = *pexpr;
8263 if (!expr->is_constant()
8264 && (expr->call_expression() != NULL
8265 || expr->receive_expression() != NULL))
83921647 8266 {
8267 this->found_ = true;
8268 return TRAVERSE_EXIT;
8269 }
8270 return TRAVERSE_CONTINUE;
8271}
8272
4714afb2 8273// Return whether calling len or cap on EXPR, of array type, is a
8274// constant. The language spec says "the expressions len(s) and
8275// cap(s) are constants if the type of s is an array or pointer to an
8276// array and the expression s does not contain channel receives or
8277// (non-constant) function calls."
8278
8279bool
8280Builtin_call_expression::array_len_is_constant(Expression* expr)
8281{
8282 go_assert(expr->type()->deref()->array_type() != NULL
8283 && !expr->type()->deref()->is_slice_type());
8284 if (expr->is_constant())
8285 return true;
8286 Find_call_expression find_call;
8287 Expression::traverse(&expr, &find_call);
8288 return !find_call.found();
8289}
8290
83921647 8291// Return whether this is constant: len of a string constant, or len
8292// or cap of an array, or unsafe.Sizeof, unsafe.Offsetof,
8293// unsafe.Alignof.
e440a328 8294
8295bool
8296Builtin_call_expression::do_is_constant() const
8297{
12e69faa 8298 if (this->is_error_expression())
8299 return true;
e440a328 8300 switch (this->code_)
8301 {
8302 case BUILTIN_LEN:
8303 case BUILTIN_CAP:
8304 {
0f914071 8305 if (this->seen_)
8306 return false;
8307
e440a328 8308 Expression* arg = this->one_arg();
8309 if (arg == NULL)
8310 return false;
8311 Type* arg_type = arg->type();
8312
8313 if (arg_type->points_to() != NULL
8314 && arg_type->points_to()->array_type() != NULL
411eb89e 8315 && !arg_type->points_to()->is_slice_type())
e440a328 8316 arg_type = arg_type->points_to();
8317
8318 if (arg_type->array_type() != NULL
54934d77 8319 && arg_type->array_type()->length() != NULL)
8320 {
8321 this->seen_ = true;
8322 bool ret = Builtin_call_expression::array_len_is_constant(arg);
8323 this->seen_ = false;
8324 return ret;
8325 }
e440a328 8326
8327 if (this->code_ == BUILTIN_LEN && arg_type->is_string_type())
0f914071 8328 {
8329 this->seen_ = true;
8330 bool ret = arg->is_constant();
8331 this->seen_ = false;
8332 return ret;
8333 }
e440a328 8334 }
8335 break;
8336
8337 case BUILTIN_SIZEOF:
8338 case BUILTIN_ALIGNOF:
8339 return this->one_arg() != NULL;
8340
8341 case BUILTIN_OFFSETOF:
8342 {
8343 Expression* arg = this->one_arg();
8344 if (arg == NULL)
8345 return false;
8346 return arg->field_reference_expression() != NULL;
8347 }
8348
48080209 8349 case BUILTIN_COMPLEX:
e440a328 8350 {
8351 const Expression_list* args = this->args();
8352 if (args != NULL && args->size() == 2)
8353 return args->front()->is_constant() && args->back()->is_constant();
8354 }
8355 break;
8356
8357 case BUILTIN_REAL:
8358 case BUILTIN_IMAG:
8359 {
8360 Expression* arg = this->one_arg();
8361 return arg != NULL && arg->is_constant();
8362 }
8363
8364 default:
8365 break;
8366 }
8367
8368 return false;
8369}
8370
0c77715b 8371// Return a numeric constant if possible.
e440a328 8372
8373bool
0c77715b 8374Builtin_call_expression::do_numeric_constant_value(Numeric_constant* nc) const
e440a328 8375{
8376 if (this->code_ == BUILTIN_LEN
8377 || this->code_ == BUILTIN_CAP)
8378 {
8379 Expression* arg = this->one_arg();
8380 if (arg == NULL)
8381 return false;
8382 Type* arg_type = arg->type();
8383
8384 if (this->code_ == BUILTIN_LEN && arg_type->is_string_type())
8385 {
8386 std::string sval;
8387 if (arg->string_constant_value(&sval))
8388 {
0c77715b 8389 nc->set_unsigned_long(Type::lookup_integer_type("int"),
8390 sval.length());
e440a328 8391 return true;
8392 }
8393 }
8394
8395 if (arg_type->points_to() != NULL
8396 && arg_type->points_to()->array_type() != NULL
411eb89e 8397 && !arg_type->points_to()->is_slice_type())
e440a328 8398 arg_type = arg_type->points_to();
8399
8400 if (arg_type->array_type() != NULL
8401 && arg_type->array_type()->length() != NULL)
8402 {
0f914071 8403 if (this->seen_)
8404 return false;
e440a328 8405 Expression* e = arg_type->array_type()->length();
0f914071 8406 this->seen_ = true;
0c77715b 8407 bool r = e->numeric_constant_value(nc);
0f914071 8408 this->seen_ = false;
8409 if (r)
e440a328 8410 {
0c77715b 8411 if (!nc->set_type(Type::lookup_integer_type("int"), false,
8412 this->location()))
8413 r = false;
e440a328 8414 }
0c77715b 8415 return r;
e440a328 8416 }
8417 }
8418 else if (this->code_ == BUILTIN_SIZEOF
8419 || this->code_ == BUILTIN_ALIGNOF)
8420 {
8421 Expression* arg = this->one_arg();
8422 if (arg == NULL)
8423 return false;
8424 Type* arg_type = arg->type();
5c13bd80 8425 if (arg_type->is_error())
e440a328 8426 return false;
8427 if (arg_type->is_abstract())
7200ac0e 8428 arg_type = arg_type->make_non_abstract_type();
2c809f8f 8429 if (this->seen_)
8430 return false;
927a01eb 8431
3f378015 8432 int64_t ret;
e440a328 8433 if (this->code_ == BUILTIN_SIZEOF)
8434 {
2c809f8f 8435 this->seen_ = true;
8436 bool ok = arg_type->backend_type_size(this->gogo_, &ret);
8437 this->seen_ = false;
8438 if (!ok)
e440a328 8439 return false;
8440 }
8441 else if (this->code_ == BUILTIN_ALIGNOF)
8442 {
2c809f8f 8443 bool ok;
8444 this->seen_ = true;
637bd3af 8445 if (arg->field_reference_expression() == NULL)
2c809f8f 8446 ok = arg_type->backend_type_align(this->gogo_, &ret);
637bd3af 8447 else
e440a328 8448 {
8449 // Calling unsafe.Alignof(s.f) returns the alignment of
8450 // the type of f when it is used as a field in a struct.
2c809f8f 8451 ok = arg_type->backend_type_field_align(this->gogo_, &ret);
e440a328 8452 }
2c809f8f 8453 this->seen_ = false;
8454 if (!ok)
8455 return false;
e440a328 8456 }
8457 else
c3e6f413 8458 go_unreachable();
927a01eb 8459
3f378015 8460 mpz_t zval;
8461 set_mpz_from_int64(&zval, ret);
8462 nc->set_int(Type::lookup_integer_type("uintptr"), zval);
8463 mpz_clear(zval);
e440a328 8464 return true;
8465 }
8466 else if (this->code_ == BUILTIN_OFFSETOF)
8467 {
8468 Expression* arg = this->one_arg();
8469 if (arg == NULL)
8470 return false;
8471 Field_reference_expression* farg = arg->field_reference_expression();
8472 if (farg == NULL)
8473 return false;
2c809f8f 8474 if (this->seen_)
8475 return false;
8476
3f378015 8477 int64_t total_offset = 0;
9a4bd570 8478 while (true)
8479 {
8480 Expression* struct_expr = farg->expr();
8481 Type* st = struct_expr->type();
8482 if (st->struct_type() == NULL)
8483 return false;
8484 if (st->named_type() != NULL)
8485 st->named_type()->convert(this->gogo_);
fbabafbd 8486 if (st->is_error_type())
8487 {
8488 go_assert(saw_errors());
8489 return false;
8490 }
3f378015 8491 int64_t offset;
2c809f8f 8492 this->seen_ = true;
8493 bool ok = st->struct_type()->backend_field_offset(this->gogo_,
8494 farg->field_index(),
8495 &offset);
8496 this->seen_ = false;
8497 if (!ok)
8498 return false;
9a4bd570 8499 total_offset += offset;
8500 if (farg->implicit() && struct_expr->field_reference_expression() != NULL)
8501 {
8502 // Go up until we reach the original base.
8503 farg = struct_expr->field_reference_expression();
8504 continue;
8505 }
8506 break;
8507 }
3f378015 8508 mpz_t zval;
8509 set_mpz_from_int64(&zval, total_offset);
8510 nc->set_int(Type::lookup_integer_type("uintptr"), zval);
8511 mpz_clear(zval);
e440a328 8512 return true;
8513 }
0c77715b 8514 else if (this->code_ == BUILTIN_REAL || this->code_ == BUILTIN_IMAG)
e440a328 8515 {
8516 Expression* arg = this->one_arg();
8517 if (arg == NULL)
8518 return false;
8519
0c77715b 8520 Numeric_constant argnc;
8521 if (!arg->numeric_constant_value(&argnc))
8522 return false;
8523
fcbea5e4 8524 mpc_t val;
8525 if (!argnc.to_complex(&val))
0c77715b 8526 return false;
e440a328 8527
0c77715b 8528 Type* type = Builtin_call_expression::real_imag_type(argnc.type());
8529 if (this->code_ == BUILTIN_REAL)
fcbea5e4 8530 nc->set_float(type, mpc_realref(val));
0c77715b 8531 else
fcbea5e4 8532 nc->set_float(type, mpc_imagref(val));
8533 mpc_clear(val);
0c77715b 8534 return true;
e440a328 8535 }
0c77715b 8536 else if (this->code_ == BUILTIN_COMPLEX)
e440a328 8537 {
8538 const Expression_list* args = this->args();
8539 if (args == NULL || args->size() != 2)
8540 return false;
8541
0c77715b 8542 Numeric_constant rnc;
8543 if (!args->front()->numeric_constant_value(&rnc))
8544 return false;
8545 Numeric_constant inc;
8546 if (!args->back()->numeric_constant_value(&inc))
8547 return false;
8548
8549 if (rnc.type() != NULL
8550 && !rnc.type()->is_abstract()
8551 && inc.type() != NULL
8552 && !inc.type()->is_abstract()
3a522dcc 8553 && !Type::are_identical(rnc.type(), inc.type(),
8554 Type::COMPARE_ERRORS | Type::COMPARE_TAGS,
8555 NULL))
0c77715b 8556 return false;
8557
e440a328 8558 mpfr_t r;
0c77715b 8559 if (!rnc.to_float(&r))
8560 return false;
8561 mpfr_t i;
8562 if (!inc.to_float(&i))
e440a328 8563 {
8564 mpfr_clear(r);
8565 return false;
8566 }
8567
0c77715b 8568 Type* arg_type = rnc.type();
8569 if (arg_type == NULL || arg_type->is_abstract())
8570 arg_type = inc.type();
e440a328 8571
fcbea5e4 8572 mpc_t val;
8573 mpc_init2(val, mpc_precision);
8574 mpc_set_fr_fr(val, r, i, MPC_RNDNN);
e440a328 8575 mpfr_clear(r);
8576 mpfr_clear(i);
8577
fcbea5e4 8578 Type* type = Builtin_call_expression::complex_type(arg_type);
8579 nc->set_complex(type, val);
8580
8581 mpc_clear(val);
8582
0c77715b 8583 return true;
e440a328 8584 }
8585
8586 return false;
8587}
8588
a7549a6a 8589// Give an error if we are discarding the value of an expression which
8590// should not normally be discarded. We don't give an error for
8591// discarding the value of an ordinary function call, but we do for
8592// builtin functions, purely for consistency with the gc compiler.
8593
4f2138d7 8594bool
a7549a6a 8595Builtin_call_expression::do_discarding_value()
8596{
8597 switch (this->code_)
8598 {
8599 case BUILTIN_INVALID:
8600 default:
8601 go_unreachable();
8602
8603 case BUILTIN_APPEND:
8604 case BUILTIN_CAP:
8605 case BUILTIN_COMPLEX:
8606 case BUILTIN_IMAG:
8607 case BUILTIN_LEN:
8608 case BUILTIN_MAKE:
8609 case BUILTIN_NEW:
8610 case BUILTIN_REAL:
8611 case BUILTIN_ALIGNOF:
8612 case BUILTIN_OFFSETOF:
8613 case BUILTIN_SIZEOF:
8614 this->unused_value_error();
4f2138d7 8615 return false;
a7549a6a 8616
8617 case BUILTIN_CLOSE:
8618 case BUILTIN_COPY:
1cce762f 8619 case BUILTIN_DELETE:
a7549a6a 8620 case BUILTIN_PANIC:
8621 case BUILTIN_PRINT:
8622 case BUILTIN_PRINTLN:
8623 case BUILTIN_RECOVER:
4f2138d7 8624 return true;
a7549a6a 8625 }
8626}
8627
e440a328 8628// Return the type.
8629
8630Type*
8631Builtin_call_expression::do_type()
8632{
79651b1f 8633 if (this->is_error_expression())
8634 return Type::make_error_type();
e440a328 8635 switch (this->code_)
8636 {
8637 case BUILTIN_INVALID:
8638 default:
79651b1f 8639 return Type::make_error_type();
e440a328 8640
8641 case BUILTIN_NEW:
e440a328 8642 {
8643 const Expression_list* args = this->args();
8644 if (args == NULL || args->empty())
8645 return Type::make_error_type();
8646 return Type::make_pointer_type(args->front()->type());
8647 }
8648
a065edc5 8649 case BUILTIN_MAKE:
8650 {
8651 const Expression_list* args = this->args();
8652 if (args == NULL || args->empty())
8653 return Type::make_error_type();
8654 return args->front()->type();
8655 }
8656
e440a328 8657 case BUILTIN_CAP:
8658 case BUILTIN_COPY:
8659 case BUILTIN_LEN:
7ba86326 8660 return Type::lookup_integer_type("int");
8661
e440a328 8662 case BUILTIN_ALIGNOF:
8663 case BUILTIN_OFFSETOF:
8664 case BUILTIN_SIZEOF:
7ba86326 8665 return Type::lookup_integer_type("uintptr");
e440a328 8666
8667 case BUILTIN_CLOSE:
1cce762f 8668 case BUILTIN_DELETE:
e440a328 8669 case BUILTIN_PANIC:
8670 case BUILTIN_PRINT:
8671 case BUILTIN_PRINTLN:
8672 return Type::make_void_type();
8673
e440a328 8674 case BUILTIN_RECOVER:
823c7e3d 8675 return Type::make_empty_interface_type(Linemap::predeclared_location());
e440a328 8676
8677 case BUILTIN_APPEND:
8678 {
8679 const Expression_list* args = this->args();
8680 if (args == NULL || args->empty())
8681 return Type::make_error_type();
3ff4863b 8682 Type *ret = args->front()->type();
8683 if (!ret->is_slice_type())
8684 return Type::make_error_type();
8685 return ret;
e440a328 8686 }
8687
8688 case BUILTIN_REAL:
8689 case BUILTIN_IMAG:
8690 {
8691 Expression* arg = this->one_arg();
8692 if (arg == NULL)
8693 return Type::make_error_type();
8694 Type* t = arg->type();
8695 if (t->is_abstract())
8696 t = t->make_non_abstract_type();
8697 t = Builtin_call_expression::real_imag_type(t);
8698 if (t == NULL)
8699 t = Type::make_error_type();
8700 return t;
8701 }
8702
48080209 8703 case BUILTIN_COMPLEX:
e440a328 8704 {
8705 const Expression_list* args = this->args();
8706 if (args == NULL || args->size() != 2)
8707 return Type::make_error_type();
8708 Type* t = args->front()->type();
8709 if (t->is_abstract())
8710 {
8711 t = args->back()->type();
8712 if (t->is_abstract())
8713 t = t->make_non_abstract_type();
8714 }
48080209 8715 t = Builtin_call_expression::complex_type(t);
e440a328 8716 if (t == NULL)
8717 t = Type::make_error_type();
8718 return t;
8719 }
8720 }
8721}
8722
8723// Determine the type.
8724
8725void
8726Builtin_call_expression::do_determine_type(const Type_context* context)
8727{
fb94b0ca 8728 if (!this->determining_types())
8729 return;
8730
e440a328 8731 this->fn()->determine_type_no_context();
8732
8733 const Expression_list* args = this->args();
8734
8735 bool is_print;
8736 Type* arg_type = NULL;
321e5ad2 8737 Type* trailing_arg_types = NULL;
e440a328 8738 switch (this->code_)
8739 {
8740 case BUILTIN_PRINT:
8741 case BUILTIN_PRINTLN:
8742 // Do not force a large integer constant to "int".
8743 is_print = true;
8744 break;
8745
8746 case BUILTIN_REAL:
8747 case BUILTIN_IMAG:
48080209 8748 arg_type = Builtin_call_expression::complex_type(context->type);
f6bc81e6 8749 if (arg_type == NULL)
8750 arg_type = Type::lookup_complex_type("complex128");
e440a328 8751 is_print = false;
8752 break;
8753
48080209 8754 case BUILTIN_COMPLEX:
e440a328 8755 {
48080209 8756 // For the complex function the type of one operand can
e440a328 8757 // determine the type of the other, as in a binary expression.
8758 arg_type = Builtin_call_expression::real_imag_type(context->type);
f6bc81e6 8759 if (arg_type == NULL)
8760 arg_type = Type::lookup_float_type("float64");
e440a328 8761 if (args != NULL && args->size() == 2)
8762 {
8763 Type* t1 = args->front()->type();
c849bb59 8764 Type* t2 = args->back()->type();
e440a328 8765 if (!t1->is_abstract())
8766 arg_type = t1;
8767 else if (!t2->is_abstract())
8768 arg_type = t2;
8769 }
8770 is_print = false;
8771 }
8772 break;
8773
321e5ad2 8774 case BUILTIN_APPEND:
8775 if (!this->is_varargs()
8776 && args != NULL
8777 && !args->empty()
8778 && args->front()->type()->is_slice_type())
8779 trailing_arg_types =
8780 args->front()->type()->array_type()->element_type();
8781 is_print = false;
8782 break;
8783
e440a328 8784 default:
8785 is_print = false;
8786 break;
8787 }
8788
8789 if (args != NULL)
8790 {
8791 for (Expression_list::const_iterator pa = args->begin();
8792 pa != args->end();
8793 ++pa)
8794 {
8795 Type_context subcontext;
8796 subcontext.type = arg_type;
8797
8798 if (is_print)
8799 {
8800 // We want to print large constants, we so can't just
8801 // use the appropriate nonabstract type. Use uint64 for
8802 // an integer if we know it is nonnegative, otherwise
8803 // use int64 for a integer, otherwise use float64 for a
8804 // float or complex128 for a complex.
8805 Type* want_type = NULL;
8806 Type* atype = (*pa)->type();
8807 if (atype->is_abstract())
8808 {
8809 if (atype->integer_type() != NULL)
8810 {
0c77715b 8811 Numeric_constant nc;
8812 if (this->numeric_constant_value(&nc))
8813 {
8814 mpz_t val;
8815 if (nc.to_int(&val))
8816 {
8817 if (mpz_sgn(val) >= 0)
8818 want_type = Type::lookup_integer_type("uint64");
8819 mpz_clear(val);
8820 }
8821 }
8822 if (want_type == NULL)
e440a328 8823 want_type = Type::lookup_integer_type("int64");
e440a328 8824 }
8825 else if (atype->float_type() != NULL)
8826 want_type = Type::lookup_float_type("float64");
8827 else if (atype->complex_type() != NULL)
8828 want_type = Type::lookup_complex_type("complex128");
8829 else if (atype->is_abstract_string_type())
8830 want_type = Type::lookup_string_type();
8831 else if (atype->is_abstract_boolean_type())
8832 want_type = Type::lookup_bool_type();
8833 else
c3e6f413 8834 go_unreachable();
e440a328 8835 subcontext.type = want_type;
8836 }
8837 }
8838
8839 (*pa)->determine_type(&subcontext);
321e5ad2 8840
8841 if (trailing_arg_types != NULL)
8842 {
8843 arg_type = trailing_arg_types;
8844 trailing_arg_types = NULL;
8845 }
e440a328 8846 }
8847 }
8848}
8849
8850// If there is exactly one argument, return true. Otherwise give an
8851// error message and return false.
8852
8853bool
8854Builtin_call_expression::check_one_arg()
8855{
8856 const Expression_list* args = this->args();
8857 if (args == NULL || args->size() < 1)
8858 {
8859 this->report_error(_("not enough arguments"));
8860 return false;
8861 }
8862 else if (args->size() > 1)
8863 {
8864 this->report_error(_("too many arguments"));
8865 return false;
8866 }
8867 if (args->front()->is_error_expression()
5c13bd80 8868 || args->front()->type()->is_error())
e440a328 8869 {
8870 this->set_is_error();
8871 return false;
8872 }
8873 return true;
8874}
8875
8876// Check argument types for a builtin function.
8877
8878void
8879Builtin_call_expression::do_check_types(Gogo*)
8880{
375646ea 8881 if (this->is_error_expression())
8882 return;
e440a328 8883 switch (this->code_)
8884 {
8885 case BUILTIN_INVALID:
8886 case BUILTIN_NEW:
8887 case BUILTIN_MAKE:
cd238b8d 8888 case BUILTIN_DELETE:
e440a328 8889 return;
8890
8891 case BUILTIN_LEN:
8892 case BUILTIN_CAP:
8893 {
8894 // The single argument may be either a string or an array or a
8895 // map or a channel, or a pointer to a closed array.
8896 if (this->check_one_arg())
8897 {
8898 Type* arg_type = this->one_arg()->type();
8899 if (arg_type->points_to() != NULL
8900 && arg_type->points_to()->array_type() != NULL
411eb89e 8901 && !arg_type->points_to()->is_slice_type())
e440a328 8902 arg_type = arg_type->points_to();
8903 if (this->code_ == BUILTIN_CAP)
8904 {
5c13bd80 8905 if (!arg_type->is_error()
e440a328 8906 && arg_type->array_type() == NULL
8907 && arg_type->channel_type() == NULL)
8908 this->report_error(_("argument must be array or slice "
8909 "or channel"));
8910 }
8911 else
8912 {
5c13bd80 8913 if (!arg_type->is_error()
e440a328 8914 && !arg_type->is_string_type()
8915 && arg_type->array_type() == NULL
8916 && arg_type->map_type() == NULL
8917 && arg_type->channel_type() == NULL)
8918 this->report_error(_("argument must be string or "
8919 "array or slice or map or channel"));
8920 }
8921 }
8922 }
8923 break;
8924
8925 case BUILTIN_PRINT:
8926 case BUILTIN_PRINTLN:
8927 {
8928 const Expression_list* args = this->args();
8929 if (args == NULL)
8930 {
8931 if (this->code_ == BUILTIN_PRINT)
631d5788 8932 go_warning_at(this->location(), 0,
e440a328 8933 "no arguments for builtin function %<%s%>",
8934 (this->code_ == BUILTIN_PRINT
8935 ? "print"
8936 : "println"));
8937 }
8938 else
8939 {
8940 for (Expression_list::const_iterator p = args->begin();
8941 p != args->end();
8942 ++p)
8943 {
8944 Type* type = (*p)->type();
5c13bd80 8945 if (type->is_error()
e440a328 8946 || type->is_string_type()
8947 || type->integer_type() != NULL
8948 || type->float_type() != NULL
8949 || type->complex_type() != NULL
8950 || type->is_boolean_type()
8951 || type->points_to() != NULL
8952 || type->interface_type() != NULL
8953 || type->channel_type() != NULL
8954 || type->map_type() != NULL
8955 || type->function_type() != NULL
411eb89e 8956 || type->is_slice_type())
e440a328 8957 ;
acf8e158 8958 else if ((*p)->is_type_expression())
8959 {
8960 // If this is a type expression it's going to give
8961 // an error anyhow, so we don't need one here.
8962 }
e440a328 8963 else
8964 this->report_error(_("unsupported argument type to "
8965 "builtin function"));
8966 }
8967 }
8968 }
8969 break;
8970
8971 case BUILTIN_CLOSE:
e440a328 8972 if (this->check_one_arg())
8973 {
8974 if (this->one_arg()->type()->channel_type() == NULL)
8975 this->report_error(_("argument must be channel"));
5202d986 8976 else if (!this->one_arg()->type()->channel_type()->may_send())
8977 this->report_error(_("cannot close receive-only channel"));
e440a328 8978 }
8979 break;
8980
8981 case BUILTIN_PANIC:
8982 case BUILTIN_SIZEOF:
8983 case BUILTIN_ALIGNOF:
8984 this->check_one_arg();
8985 break;
8986
8987 case BUILTIN_RECOVER:
6334270b 8988 if (this->args() != NULL
8989 && !this->args()->empty()
8990 && !this->recover_arg_is_set_)
e440a328 8991 this->report_error(_("too many arguments"));
8992 break;
8993
8994 case BUILTIN_OFFSETOF:
8995 if (this->check_one_arg())
8996 {
8997 Expression* arg = this->one_arg();
8998 if (arg->field_reference_expression() == NULL)
8999 this->report_error(_("argument must be a field reference"));
9000 }
9001 break;
9002
9003 case BUILTIN_COPY:
9004 {
9005 const Expression_list* args = this->args();
9006 if (args == NULL || args->size() < 2)
9007 {
9008 this->report_error(_("not enough arguments"));
9009 break;
9010 }
9011 else if (args->size() > 2)
9012 {
9013 this->report_error(_("too many arguments"));
9014 break;
9015 }
9016 Type* arg1_type = args->front()->type();
9017 Type* arg2_type = args->back()->type();
5c13bd80 9018 if (arg1_type->is_error() || arg2_type->is_error())
6bebb39d 9019 {
9020 this->set_is_error();
9021 break;
9022 }
e440a328 9023
9024 Type* e1;
411eb89e 9025 if (arg1_type->is_slice_type())
e440a328 9026 e1 = arg1_type->array_type()->element_type();
9027 else
9028 {
9029 this->report_error(_("left argument must be a slice"));
9030 break;
9031 }
9032
411eb89e 9033 if (arg2_type->is_slice_type())
60963afd 9034 {
9035 Type* e2 = arg2_type->array_type()->element_type();
3a522dcc 9036 if (!Type::are_identical(e1, e2, Type::COMPARE_TAGS, NULL))
60963afd 9037 this->report_error(_("element types must be the same"));
9038 }
e440a328 9039 else if (arg2_type->is_string_type())
e440a328 9040 {
60963afd 9041 if (e1->integer_type() == NULL || !e1->integer_type()->is_byte())
9042 this->report_error(_("first argument must be []byte"));
e440a328 9043 }
60963afd 9044 else
9045 this->report_error(_("second argument must be slice or string"));
e440a328 9046 }
9047 break;
9048
9049 case BUILTIN_APPEND:
9050 {
9051 const Expression_list* args = this->args();
321e5ad2 9052 if (args == NULL || args->empty())
e440a328 9053 {
9054 this->report_error(_("not enough arguments"));
9055 break;
9056 }
321e5ad2 9057
9058 Type* slice_type = args->front()->type();
9059 if (!slice_type->is_slice_type())
6bebb39d 9060 {
321e5ad2 9061 if (slice_type->is_error_type())
9062 break;
9063 if (slice_type->is_nil_type())
9064 go_error_at(args->front()->location(), "use of untyped nil");
9065 else
9066 go_error_at(args->front()->location(),
9067 "argument 1 must be a slice");
6bebb39d 9068 this->set_is_error();
9069 break;
9070 }
cd238b8d 9071
321e5ad2 9072 Type* element_type = slice_type->array_type()->element_type();
22deed0d 9073 if (!element_type->in_heap())
9074 go_error_at(args->front()->location(),
9075 "can't append to slice of go:notinheap type");
321e5ad2 9076 if (this->is_varargs())
4fd4fcf4 9077 {
321e5ad2 9078 if (!args->back()->type()->is_slice_type()
9079 && !args->back()->type()->is_string_type())
9080 {
9081 go_error_at(args->back()->location(),
9082 "invalid use of %<...%> with non-slice/non-string");
9083 this->set_is_error();
9084 break;
9085 }
4fd4fcf4 9086
321e5ad2 9087 if (args->size() < 2)
9088 {
9089 this->report_error(_("not enough arguments"));
9090 break;
9091 }
9092 if (args->size() > 2)
9093 {
9094 this->report_error(_("too many arguments"));
9095 break;
9096 }
9097
9098 if (args->back()->type()->is_string_type()
9099 && element_type->integer_type() != NULL
9100 && element_type->integer_type()->is_byte())
9101 {
9102 // Permit append(s1, s2...) when s1 is a slice of
9103 // bytes and s2 is a string type.
9104 }
e440a328 9105 else
9106 {
321e5ad2 9107 // We have to test for assignment compatibility to a
9108 // slice of the element type, which is not necessarily
9109 // the same as the type of the first argument: the
9110 // first argument might have a named type.
9111 Type* check_type = Type::make_array_type(element_type, NULL);
9112 std::string reason;
9113 if (!Type::are_assignable(check_type, args->back()->type(),
9114 &reason))
9115 {
9116 if (reason.empty())
9117 go_error_at(args->back()->location(),
9118 "argument 2 has invalid type");
9119 else
9120 go_error_at(args->back()->location(),
9121 "argument 2 has invalid type (%s)",
9122 reason.c_str());
9123 this->set_is_error();
9124 break;
9125 }
9126 }
9127 }
9128 else
9129 {
9130 Expression_list::const_iterator pa = args->begin();
9131 int i = 2;
9132 for (++pa; pa != args->end(); ++pa, ++i)
9133 {
9134 std::string reason;
9135 if (!Type::are_assignable(element_type, (*pa)->type(),
9136 &reason))
9137 {
9138 if (reason.empty())
9139 go_error_at((*pa)->location(),
9140 "argument %d has incompatible type", i);
9141 else
9142 go_error_at((*pa)->location(),
9143 "argument %d has incompatible type (%s)",
9144 i, reason.c_str());
9145 this->set_is_error();
9146 }
e440a328 9147 }
9148 }
e440a328 9149 }
321e5ad2 9150 break;
e440a328 9151
9152 case BUILTIN_REAL:
9153 case BUILTIN_IMAG:
9154 if (this->check_one_arg())
9155 {
9156 if (this->one_arg()->type()->complex_type() == NULL)
9157 this->report_error(_("argument must have complex type"));
9158 }
9159 break;
9160
48080209 9161 case BUILTIN_COMPLEX:
e440a328 9162 {
9163 const Expression_list* args = this->args();
9164 if (args == NULL || args->size() < 2)
9165 this->report_error(_("not enough arguments"));
9166 else if (args->size() > 2)
9167 this->report_error(_("too many arguments"));
9168 else if (args->front()->is_error_expression()
5c13bd80 9169 || args->front()->type()->is_error()
e440a328 9170 || args->back()->is_error_expression()
5c13bd80 9171 || args->back()->type()->is_error())
e440a328 9172 this->set_is_error();
9173 else if (!Type::are_identical(args->front()->type(),
3a522dcc 9174 args->back()->type(),
9175 Type::COMPARE_TAGS, NULL))
48080209 9176 this->report_error(_("complex arguments must have identical types"));
e440a328 9177 else if (args->front()->type()->float_type() == NULL)
48080209 9178 this->report_error(_("complex arguments must have "
e440a328 9179 "floating-point type"));
9180 }
9181 break;
9182
9183 default:
c3e6f413 9184 go_unreachable();
e440a328 9185 }
9186}
9187
72666aed 9188Expression*
9189Builtin_call_expression::do_copy()
9190{
9191 Call_expression* bce =
9192 new Builtin_call_expression(this->gogo_, this->fn()->copy(),
da244e59 9193 (this->args() == NULL
9194 ? NULL
9195 : this->args()->copy()),
72666aed 9196 this->is_varargs(),
9197 this->location());
9198
9199 if (this->varargs_are_lowered())
9200 bce->set_varargs_are_lowered();
28819633 9201 if (this->is_deferred())
9202 bce->set_is_deferred();
9203 if (this->is_concurrent())
9204 bce->set_is_concurrent();
72666aed 9205 return bce;
9206}
9207
ea664253 9208// Return the backend representation for a builtin function.
e440a328 9209
ea664253 9210Bexpression*
9211Builtin_call_expression::do_get_backend(Translate_context* context)
e440a328 9212{
9213 Gogo* gogo = context->gogo();
b13c66cd 9214 Location location = this->location();
a0d8874e 9215
9216 if (this->is_erroneous_call())
9217 {
9218 go_assert(saw_errors());
9219 return gogo->backend()->error_expression();
9220 }
9221
e440a328 9222 switch (this->code_)
9223 {
9224 case BUILTIN_INVALID:
9225 case BUILTIN_NEW:
9226 case BUILTIN_MAKE:
c3e6f413 9227 go_unreachable();
e440a328 9228
9229 case BUILTIN_LEN:
9230 case BUILTIN_CAP:
9231 {
9232 const Expression_list* args = this->args();
c484d925 9233 go_assert(args != NULL && args->size() == 1);
2c809f8f 9234 Expression* arg = args->front();
e440a328 9235 Type* arg_type = arg->type();
0f914071 9236
9237 if (this->seen_)
9238 {
c484d925 9239 go_assert(saw_errors());
ea664253 9240 return context->backend()->error_expression();
0f914071 9241 }
9242 this->seen_ = true;
0f914071 9243 this->seen_ = false;
e440a328 9244 if (arg_type->points_to() != NULL)
9245 {
9246 arg_type = arg_type->points_to();
c484d925 9247 go_assert(arg_type->array_type() != NULL
411eb89e 9248 && !arg_type->is_slice_type());
f614ea8b 9249 arg = Expression::make_dereference(arg, NIL_CHECK_DEFAULT,
9250 location);
e440a328 9251 }
9252
1b1f2abf 9253 Type* int_type = Type::lookup_integer_type("int");
2c809f8f 9254 Expression* val;
e440a328 9255 if (this->code_ == BUILTIN_LEN)
9256 {
9257 if (arg_type->is_string_type())
2c809f8f 9258 val = Expression::make_string_info(arg, STRING_INFO_LENGTH,
9259 location);
e440a328 9260 else if (arg_type->array_type() != NULL)
0f914071 9261 {
9262 if (this->seen_)
9263 {
c484d925 9264 go_assert(saw_errors());
ea664253 9265 return context->backend()->error_expression();
0f914071 9266 }
9267 this->seen_ = true;
2c809f8f 9268 val = arg_type->array_type()->get_length(gogo, arg);
0f914071 9269 this->seen_ = false;
9270 }
0d5530d9 9271 else if (arg_type->map_type() != NULL
9272 || arg_type->channel_type() != NULL)
9273 {
9274 // The first field is the length. If the pointer is
9275 // nil, the length is zero.
9276 Type* pint_type = Type::make_pointer_type(int_type);
9277 arg = Expression::make_unsafe_cast(pint_type, arg, location);
9278 Expression* nil = Expression::make_nil(location);
9279 nil = Expression::make_cast(pint_type, nil, location);
9280 Expression* cmp = Expression::make_binary(OPERATOR_EQEQ,
9281 arg, nil, location);
9282 Expression* zero = Expression::make_integer_ul(0, int_type,
9283 location);
f614ea8b 9284 Expression* indir =
9285 Expression::make_dereference(arg, NIL_CHECK_NOT_NEEDED,
9286 location);
0d5530d9 9287 val = Expression::make_conditional(cmp, zero, indir, location);
9288 }
e440a328 9289 else
c3e6f413 9290 go_unreachable();
e440a328 9291 }
9292 else
9293 {
9294 if (arg_type->array_type() != NULL)
0f914071 9295 {
9296 if (this->seen_)
9297 {
c484d925 9298 go_assert(saw_errors());
ea664253 9299 return context->backend()->error_expression();
0f914071 9300 }
9301 this->seen_ = true;
2c809f8f 9302 val = arg_type->array_type()->get_capacity(gogo, arg);
0f914071 9303 this->seen_ = false;
9304 }
e440a328 9305 else if (arg_type->channel_type() != NULL)
132ed071 9306 {
9307 // The second field is the capacity. If the pointer
9308 // is nil, the capacity is zero.
9309 Type* uintptr_type = Type::lookup_integer_type("uintptr");
9310 Type* pint_type = Type::make_pointer_type(int_type);
9311 Expression* parg = Expression::make_unsafe_cast(uintptr_type,
9312 arg,
9313 location);
9314 int off = int_type->integer_type()->bits() / 8;
9315 Expression* eoff = Expression::make_integer_ul(off,
9316 uintptr_type,
9317 location);
9318 parg = Expression::make_binary(OPERATOR_PLUS, parg, eoff,
9319 location);
9320 parg = Expression::make_unsafe_cast(pint_type, parg, location);
9321 Expression* nil = Expression::make_nil(location);
9322 nil = Expression::make_cast(pint_type, nil, location);
9323 Expression* cmp = Expression::make_binary(OPERATOR_EQEQ,
9324 arg, nil, location);
9325 Expression* zero = Expression::make_integer_ul(0, int_type,
9326 location);
f614ea8b 9327 Expression* indir =
9328 Expression::make_dereference(parg, NIL_CHECK_NOT_NEEDED,
9329 location);
132ed071 9330 val = Expression::make_conditional(cmp, zero, indir, location);
9331 }
e440a328 9332 else
c3e6f413 9333 go_unreachable();
e440a328 9334 }
9335
2c809f8f 9336 return Expression::make_cast(int_type, val,
ea664253 9337 location)->get_backend(context);
e440a328 9338 }
9339
9340 case BUILTIN_PRINT:
9341 case BUILTIN_PRINTLN:
9342 {
9343 const bool is_ln = this->code_ == BUILTIN_PRINTLN;
88b03a70 9344
9345 Expression* print_stmts = Runtime::make_call(Runtime::PRINTLOCK,
9346 location, 0);
e440a328 9347
9348 const Expression_list* call_args = this->args();
9349 if (call_args != NULL)
9350 {
9351 for (Expression_list::const_iterator p = call_args->begin();
9352 p != call_args->end();
9353 ++p)
9354 {
9355 if (is_ln && p != call_args->begin())
9356 {
2c809f8f 9357 Expression* print_space =
88b03a70 9358 Runtime::make_call(Runtime::PRINTSP, location, 0);
e440a328 9359
2c809f8f 9360 print_stmts =
9361 Expression::make_compound(print_stmts, print_space,
9362 location);
9363 }
e440a328 9364
2c809f8f 9365 Expression* arg = *p;
9366 Type* type = arg->type();
9367 Runtime::Function code;
e440a328 9368 if (type->is_string_type())
88b03a70 9369 code = Runtime::PRINTSTRING;
e440a328 9370 else if (type->integer_type() != NULL
9371 && type->integer_type()->is_unsigned())
9372 {
e440a328 9373 Type* itype = Type::lookup_integer_type("uint64");
2c809f8f 9374 arg = Expression::make_cast(itype, arg, location);
88b03a70 9375 code = Runtime::PRINTUINT;
e440a328 9376 }
9377 else if (type->integer_type() != NULL)
9378 {
e440a328 9379 Type* itype = Type::lookup_integer_type("int64");
2c809f8f 9380 arg = Expression::make_cast(itype, arg, location);
88b03a70 9381 code = Runtime::PRINTINT;
e440a328 9382 }
9383 else if (type->float_type() != NULL)
9384 {
2c809f8f 9385 Type* dtype = Type::lookup_float_type("float64");
9386 arg = Expression::make_cast(dtype, arg, location);
88b03a70 9387 code = Runtime::PRINTFLOAT;
e440a328 9388 }
9389 else if (type->complex_type() != NULL)
9390 {
2c809f8f 9391 Type* ctype = Type::lookup_complex_type("complex128");
9392 arg = Expression::make_cast(ctype, arg, location);
88b03a70 9393 code = Runtime::PRINTCOMPLEX;
e440a328 9394 }
9395 else if (type->is_boolean_type())
88b03a70 9396 code = Runtime::PRINTBOOL;
e440a328 9397 else if (type->points_to() != NULL
9398 || type->channel_type() != NULL
9399 || type->map_type() != NULL
9400 || type->function_type() != NULL)
9401 {
2c809f8f 9402 arg = Expression::make_cast(type, arg, location);
88b03a70 9403 code = Runtime::PRINTPOINTER;
e440a328 9404 }
9405 else if (type->interface_type() != NULL)
9406 {
9407 if (type->interface_type()->is_empty())
88b03a70 9408 code = Runtime::PRINTEFACE;
e440a328 9409 else
88b03a70 9410 code = Runtime::PRINTIFACE;
e440a328 9411 }
411eb89e 9412 else if (type->is_slice_type())
88b03a70 9413 code = Runtime::PRINTSLICE;
e440a328 9414 else
cd238b8d 9415 {
9416 go_assert(saw_errors());
ea664253 9417 return context->backend()->error_expression();
cd238b8d 9418 }
e440a328 9419
2c809f8f 9420 Expression* call = Runtime::make_call(code, location, 1, arg);
88b03a70 9421 print_stmts = Expression::make_compound(print_stmts, call,
9422 location);
e440a328 9423 }
9424 }
9425
9426 if (is_ln)
9427 {
2c809f8f 9428 Expression* print_nl =
88b03a70 9429 Runtime::make_call(Runtime::PRINTNL, location, 0);
9430 print_stmts = Expression::make_compound(print_stmts, print_nl,
9431 location);
e440a328 9432 }
9433
88b03a70 9434 Expression* unlock = Runtime::make_call(Runtime::PRINTUNLOCK,
9435 location, 0);
9436 print_stmts = Expression::make_compound(print_stmts, unlock, location);
32e3ff69 9437
ea664253 9438 return print_stmts->get_backend(context);
e440a328 9439 }
9440
9441 case BUILTIN_PANIC:
9442 {
9443 const Expression_list* args = this->args();
c484d925 9444 go_assert(args != NULL && args->size() == 1);
e440a328 9445 Expression* arg = args->front();
b13c66cd 9446 Type *empty =
823c7e3d 9447 Type::make_empty_interface_type(Linemap::predeclared_location());
2c809f8f 9448 arg = Expression::convert_for_assignment(gogo, empty, arg, location);
9449
9450 Expression* panic =
03ac9de4 9451 Runtime::make_call(Runtime::GOPANIC, location, 1, arg);
ea664253 9452 return panic->get_backend(context);
e440a328 9453 }
9454
9455 case BUILTIN_RECOVER:
9456 {
9457 // The argument is set when building recover thunks. It's a
9458 // boolean value which is true if we can recover a value now.
9459 const Expression_list* args = this->args();
c484d925 9460 go_assert(args != NULL && args->size() == 1);
e440a328 9461 Expression* arg = args->front();
b13c66cd 9462 Type *empty =
823c7e3d 9463 Type::make_empty_interface_type(Linemap::predeclared_location());
e440a328 9464
e440a328 9465 Expression* nil = Expression::make_nil(location);
2c809f8f 9466 nil = Expression::convert_for_assignment(gogo, empty, nil, location);
e440a328 9467
9468 // We need to handle a deferred call to recover specially,
9469 // because it changes whether it can recover a panic or not.
9470 // See test7 in test/recover1.go.
2c809f8f 9471 Expression* recover = Runtime::make_call((this->is_deferred()
03ac9de4 9472 ? Runtime::DEFERREDRECOVER
9473 : Runtime::GORECOVER),
2c809f8f 9474 location, 0);
9475 Expression* cond =
9476 Expression::make_conditional(arg, recover, nil, location);
ea664253 9477 return cond->get_backend(context);
e440a328 9478 }
9479
9480 case BUILTIN_CLOSE:
e440a328 9481 {
9482 const Expression_list* args = this->args();
c484d925 9483 go_assert(args != NULL && args->size() == 1);
e440a328 9484 Expression* arg = args->front();
2c809f8f 9485 Expression* close = Runtime::make_call(Runtime::CLOSE, location,
9486 1, arg);
ea664253 9487 return close->get_backend(context);
e440a328 9488 }
9489
9490 case BUILTIN_SIZEOF:
9491 case BUILTIN_OFFSETOF:
9492 case BUILTIN_ALIGNOF:
9493 {
0c77715b 9494 Numeric_constant nc;
9495 unsigned long val;
9496 if (!this->numeric_constant_value(&nc)
9497 || nc.to_unsigned_long(&val) != Numeric_constant::NC_UL_VALID)
7f1d9abd 9498 {
c484d925 9499 go_assert(saw_errors());
ea664253 9500 return context->backend()->error_expression();
7f1d9abd 9501 }
7ba86326 9502 Type* uintptr_type = Type::lookup_integer_type("uintptr");
2c809f8f 9503 mpz_t ival;
9504 nc.get_int(&ival);
9505 Expression* int_cst =
e67508fa 9506 Expression::make_integer_z(&ival, uintptr_type, location);
2c809f8f 9507 mpz_clear(ival);
ea664253 9508 return int_cst->get_backend(context);
e440a328 9509 }
9510
9511 case BUILTIN_COPY:
9512 {
9513 const Expression_list* args = this->args();
c484d925 9514 go_assert(args != NULL && args->size() == 2);
e440a328 9515 Expression* arg1 = args->front();
9516 Expression* arg2 = args->back();
9517
e440a328 9518 Type* arg1_type = arg1->type();
9519 Array_type* at = arg1_type->array_type();
35a54f17 9520 go_assert(arg1->is_variable());
321e5ad2 9521
9522 Expression* call;
e440a328 9523
9524 Type* arg2_type = arg2->type();
2c809f8f 9525 go_assert(arg2->is_variable());
321e5ad2 9526 if (arg2_type->is_string_type())
9527 call = Runtime::make_call(Runtime::SLICESTRINGCOPY, location,
9528 2, arg1, arg2);
e440a328 9529 else
9530 {
321e5ad2 9531 Type* et = at->element_type();
9532 if (et->has_pointer())
9533 {
9534 Expression* td = Expression::make_type_descriptor(et,
9535 location);
9536 call = Runtime::make_call(Runtime::TYPEDSLICECOPY, location,
9537 3, td, arg1, arg2);
9538 }
9539 else
9540 {
9541 Expression* sz = Expression::make_type_info(et,
9542 TYPE_INFO_SIZE);
9543 call = Runtime::make_call(Runtime::SLICECOPY, location, 3,
9544 arg1, arg2, sz);
9545 }
e440a328 9546 }
2c809f8f 9547
321e5ad2 9548 return call->get_backend(context);
e440a328 9549 }
9550
9551 case BUILTIN_APPEND:
321e5ad2 9552 // Handled in Builtin_call_expression::flatten_append.
9553 go_unreachable();
e440a328 9554
9555 case BUILTIN_REAL:
9556 case BUILTIN_IMAG:
9557 {
9558 const Expression_list* args = this->args();
c484d925 9559 go_assert(args != NULL && args->size() == 1);
2c809f8f 9560
9561 Bexpression* ret;
ea664253 9562 Bexpression* bcomplex = args->front()->get_backend(context);
2c809f8f 9563 if (this->code_ == BUILTIN_REAL)
9564 ret = gogo->backend()->real_part_expression(bcomplex, location);
9565 else
9566 ret = gogo->backend()->imag_part_expression(bcomplex, location);
ea664253 9567 return ret;
e440a328 9568 }
9569
48080209 9570 case BUILTIN_COMPLEX:
e440a328 9571 {
9572 const Expression_list* args = this->args();
c484d925 9573 go_assert(args != NULL && args->size() == 2);
ea664253 9574 Bexpression* breal = args->front()->get_backend(context);
9575 Bexpression* bimag = args->back()->get_backend(context);
9576 return gogo->backend()->complex_expression(breal, bimag, location);
e440a328 9577 }
9578
9579 default:
c3e6f413 9580 go_unreachable();
e440a328 9581 }
9582}
9583
9584// We have to support exporting a builtin call expression, because
9585// code can set a constant to the result of a builtin expression.
9586
9587void
548be246 9588Builtin_call_expression::do_export(Export_function_body* efb) const
e440a328 9589{
0c77715b 9590 Numeric_constant nc;
9591 if (!this->numeric_constant_value(&nc))
9592 {
631d5788 9593 go_error_at(this->location(), "value is not constant");
0c77715b 9594 return;
9595 }
e440a328 9596
0c77715b 9597 if (nc.is_int())
e440a328 9598 {
0c77715b 9599 mpz_t val;
9600 nc.get_int(&val);
548be246 9601 Integer_expression::export_integer(efb, val);
0c77715b 9602 mpz_clear(val);
e440a328 9603 }
0c77715b 9604 else if (nc.is_float())
e440a328 9605 {
9606 mpfr_t fval;
0c77715b 9607 nc.get_float(&fval);
548be246 9608 Float_expression::export_float(efb, fval);
e440a328 9609 mpfr_clear(fval);
9610 }
0c77715b 9611 else if (nc.is_complex())
e440a328 9612 {
fcbea5e4 9613 mpc_t cval;
9614 nc.get_complex(&cval);
548be246 9615 Complex_expression::export_complex(efb, cval);
fcbea5e4 9616 mpc_clear(cval);
e440a328 9617 }
0c77715b 9618 else
9619 go_unreachable();
e440a328 9620
9621 // A trailing space lets us reliably identify the end of the number.
548be246 9622 efb->write_c_string(" ");
e440a328 9623}
9624
9625// Class Call_expression.
9626
8381eda7 9627// A Go function can be viewed in a couple of different ways. The
9628// code of a Go function becomes a backend function with parameters
9629// whose types are simply the backend representation of the Go types.
9630// If there are multiple results, they are returned as a backend
9631// struct.
9632
9633// However, when Go code refers to a function other than simply
9634// calling it, the backend type of that function is actually a struct.
9635// The first field of the struct points to the Go function code
9636// (sometimes a wrapper as described below). The remaining fields
9637// hold addresses of closed-over variables. This struct is called a
9638// closure.
9639
9640// There are a few cases to consider.
9641
9642// A direct function call of a known function in package scope. In
9643// this case there are no closed-over variables, and we know the name
9644// of the function code. We can simply produce a backend call to the
9645// function directly, and not worry about the closure.
9646
9647// A direct function call of a known function literal. In this case
9648// we know the function code and we know the closure. We generate the
9649// function code such that it expects an additional final argument of
9650// the closure type. We pass the closure as the last argument, after
9651// the other arguments.
9652
9653// An indirect function call. In this case we have a closure. We
9654// load the pointer to the function code from the first field of the
9655// closure. We pass the address of the closure as the last argument.
9656
9657// A call to a method of an interface. Type methods are always at
9658// package scope, so we call the function directly, and don't worry
9659// about the closure.
9660
9661// This means that for a function at package scope we have two cases.
9662// One is the direct call, which has no closure. The other is the
9663// indirect call, which does have a closure. We can't simply ignore
9664// the closure, even though it is the last argument, because that will
9665// fail on targets where the function pops its arguments. So when
9666// generating a closure for a package-scope function we set the
9667// function code pointer in the closure to point to a wrapper
9668// function. This wrapper function accepts a final argument that
9669// points to the closure, ignores it, and calls the real function as a
9670// direct function call. This wrapper will normally be efficient, and
9671// can often simply be a tail call to the real function.
9672
9673// We don't use GCC's static chain pointer because 1) we don't need
9674// it; 2) GCC only permits using a static chain to call a known
9675// function, so we can't use it for an indirect call anyhow. Since we
9676// can't use it for an indirect call, we may as well not worry about
9677// using it for a direct call either.
9678
9679// We pass the closure last rather than first because it means that
9680// the function wrapper we put into a closure for a package-scope
9681// function can normally just be a tail call to the real function.
9682
9683// For method expressions we generate a wrapper that loads the
9684// receiver from the closure and then calls the method. This
9685// unfortunately forces reshuffling the arguments, since there is a
9686// new first argument, but we can't avoid reshuffling either for
9687// method expressions or for indirect calls of package-scope
9688// functions, and since the latter are more common we reshuffle for
9689// method expressions.
9690
9691// Note that the Go code retains the Go types. The extra final
9692// argument only appears when we convert to the backend
9693// representation.
9694
e440a328 9695// Traversal.
9696
9697int
9698Call_expression::do_traverse(Traverse* traverse)
9699{
0c0dacab 9700 // If we are calling a function in a different package that returns
9701 // an unnamed type, this may be the only chance we get to traverse
9702 // that type. We don't traverse this->type_ because it may be a
9703 // Call_multiple_result_type that will just lead back here.
9704 if (this->type_ != NULL && !this->type_->is_error_type())
9705 {
9706 Function_type *fntype = this->get_function_type();
9707 if (fntype != NULL && Type::traverse(fntype, traverse) == TRAVERSE_EXIT)
9708 return TRAVERSE_EXIT;
9709 }
e440a328 9710 if (Expression::traverse(&this->fn_, traverse) == TRAVERSE_EXIT)
9711 return TRAVERSE_EXIT;
9712 if (this->args_ != NULL)
9713 {
9714 if (this->args_->traverse(traverse) == TRAVERSE_EXIT)
9715 return TRAVERSE_EXIT;
9716 }
9717 return TRAVERSE_CONTINUE;
9718}
9719
9720// Lower a call statement.
9721
9722Expression*
ceeb4318 9723Call_expression::do_lower(Gogo* gogo, Named_object* function,
9724 Statement_inserter* inserter, int)
e440a328 9725{
b13c66cd 9726 Location loc = this->location();
09ea332d 9727
ceeb4318 9728 // A type cast can look like a function call.
e440a328 9729 if (this->fn_->is_type_expression()
9730 && this->args_ != NULL
9731 && this->args_->size() == 1)
9732 return Expression::make_cast(this->fn_->type(), this->args_->front(),
09ea332d 9733 loc);
e440a328 9734
88f06749 9735 // Because do_type will return an error type and thus prevent future
9736 // errors, check for that case now to ensure that the error gets
9737 // reported.
37448b10 9738 Function_type* fntype = this->get_function_type();
9739 if (fntype == NULL)
88f06749 9740 {
9741 if (!this->fn_->type()->is_error())
9742 this->report_error(_("expected function"));
5f1045b5 9743 this->set_is_error();
9744 return this;
88f06749 9745 }
9746
e440a328 9747 // Handle an argument which is a call to a function which returns
9748 // multiple results.
9749 if (this->args_ != NULL
9750 && this->args_->size() == 1
37448b10 9751 && this->args_->front()->call_expression() != NULL)
e440a328 9752 {
e440a328 9753 size_t rc = this->args_->front()->call_expression()->result_count();
9754 if (rc > 1
37448b10 9755 && ((fntype->parameters() != NULL
9756 && (fntype->parameters()->size() == rc
9757 || (fntype->is_varargs()
9758 && fntype->parameters()->size() - 1 <= rc)))
9759 || fntype->is_builtin()))
e440a328 9760 {
9761 Call_expression* call = this->args_->front()->call_expression();
e90ecd2d 9762 call->set_is_multi_value_arg();
c33af8e4 9763 if (this->is_varargs_)
9764 {
9765 // It is not clear which result of a multiple result call
9766 // the ellipsis operator should be applied to. If we unpack the
9767 // the call into its individual results here, the ellipsis will be
9768 // applied to the last result.
631d5788 9769 go_error_at(call->location(),
9770 _("multiple-value argument in single-value context"));
c33af8e4 9771 return Expression::make_error(call->location());
9772 }
9773
e440a328 9774 Expression_list* args = new Expression_list;
9775 for (size_t i = 0; i < rc; ++i)
9776 args->push_back(Expression::make_call_result(call, i));
9777 // We can't return a new call expression here, because this
42535814 9778 // one may be referenced by Call_result expressions. We
9779 // also can't delete the old arguments, because we may still
9780 // traverse them somewhere up the call stack. FIXME.
e440a328 9781 this->args_ = args;
9782 }
9783 }
9784
37448b10 9785 // Recognize a call to a builtin function.
9786 if (fntype->is_builtin())
28819633 9787 {
9788 Builtin_call_expression* bce =
9789 new Builtin_call_expression(gogo, this->fn_, this->args_,
9790 this->is_varargs_, loc);
9791 if (this->is_deferred_)
9792 bce->set_is_deferred();
9793 if (this->is_concurrent_)
9794 bce->set_is_concurrent();
9795 return bce;
9796 }
37448b10 9797
ceeb4318 9798 // If this call returns multiple results, create a temporary
5731103c 9799 // variable to hold them.
9800 if (this->result_count() > 1 && this->call_temp_ == NULL)
ceeb4318 9801 {
5731103c 9802 Struct_field_list* sfl = new Struct_field_list();
9803 Function_type* fntype = this->get_function_type();
37448b10 9804 const Typed_identifier_list* results = fntype->results();
5731103c 9805 Location loc = this->location();
9806
9807 int i = 0;
9808 char buf[20];
ceeb4318 9809 for (Typed_identifier_list::const_iterator p = results->begin();
5731103c 9810 p != results->end();
9811 ++p, ++i)
9812 {
9813 snprintf(buf, sizeof buf, "res%d", i);
9814 sfl->push_back(Struct_field(Typed_identifier(buf, p->type(), loc)));
9815 }
9816
9817 Struct_type* st = Type::make_struct_type(sfl, loc);
9818 st->set_is_struct_incomparable();
9819 this->call_temp_ = Statement::make_temporary(st, NULL, loc);
9820 inserter->insert(this->call_temp_);
ceeb4318 9821 }
9822
e440a328 9823 // Handle a call to a varargs function by packaging up the extra
9824 // parameters.
37448b10 9825 if (fntype->is_varargs())
e440a328 9826 {
e440a328 9827 const Typed_identifier_list* parameters = fntype->parameters();
c484d925 9828 go_assert(parameters != NULL && !parameters->empty());
e440a328 9829 Type* varargs_type = parameters->back().type();
09ea332d 9830 this->lower_varargs(gogo, function, inserter, varargs_type,
0e9a2e72 9831 parameters->size(), SLICE_STORAGE_MAY_ESCAPE);
09ea332d 9832 }
9833
9834 // If this is call to a method, call the method directly passing the
9835 // object as the first parameter.
9836 Bound_method_expression* bme = this->fn_->bound_method_expression();
9837 if (bme != NULL)
9838 {
0afbb937 9839 Named_object* methodfn = bme->function();
09ea332d 9840 Expression* first_arg = bme->first_argument();
9841
9842 // We always pass a pointer when calling a method.
9843 if (first_arg->type()->points_to() == NULL
9844 && !first_arg->type()->is_error())
9845 {
9846 first_arg = Expression::make_unary(OPERATOR_AND, first_arg, loc);
9847 // We may need to create a temporary variable so that we can
9848 // take the address. We can't do that here because it will
9849 // mess up the order of evaluation.
9850 Unary_expression* ue = static_cast<Unary_expression*>(first_arg);
9851 ue->set_create_temp();
9852 }
9853
9854 // If we are calling a method which was inherited from an
9855 // embedded struct, and the method did not get a stub, then the
9856 // first type may be wrong.
9857 Type* fatype = bme->first_argument_type();
9858 if (fatype != NULL)
9859 {
9860 if (fatype->points_to() == NULL)
9861 fatype = Type::make_pointer_type(fatype);
9862 first_arg = Expression::make_unsafe_cast(fatype, first_arg, loc);
9863 }
9864
9865 Expression_list* new_args = new Expression_list();
9866 new_args->push_back(first_arg);
9867 if (this->args_ != NULL)
9868 {
9869 for (Expression_list::const_iterator p = this->args_->begin();
9870 p != this->args_->end();
9871 ++p)
9872 new_args->push_back(*p);
9873 }
9874
9875 // We have to change in place because this structure may be
9876 // referenced by Call_result_expressions. We can't delete the
9877 // old arguments, because we may be traversing them up in some
9878 // caller. FIXME.
9879 this->args_ = new_args;
0afbb937 9880 this->fn_ = Expression::make_func_reference(methodfn, NULL,
09ea332d 9881 bme->location());
e440a328 9882 }
9883
105f9a24 9884 // Handle a couple of special runtime functions. In the runtime
9885 // package, getcallerpc returns the PC of the caller, and
9886 // getcallersp returns the frame pointer of the caller. Implement
9887 // these by turning them into calls to GCC builtin functions. We
9888 // could implement them in normal code, but then we would have to
9889 // explicitly unwind the stack. These functions are intended to be
9890 // efficient. Note that this technique obviously only works for
33d1d391 9891 // direct calls, but that is the only way they are used.
9892 if (gogo->compiling_runtime() && gogo->package_name() == "runtime")
105f9a24 9893 {
9894 Func_expression* fe = this->fn_->func_expression();
9895 if (fe != NULL
9896 && fe->named_object()->is_function_declaration()
9897 && fe->named_object()->package() == NULL)
9898 {
9899 std::string n = Gogo::unpack_hidden_name(fe->named_object()->name());
33d1d391 9900 if ((this->args_ == NULL || this->args_->size() == 0)
9901 && n == "getcallerpc")
105f9a24 9902 {
9903 static Named_object* builtin_return_address;
9904 return this->lower_to_builtin(&builtin_return_address,
9905 "__builtin_return_address",
9906 0);
9907 }
b5665f52 9908 else if ((this->args_ == NULL || this->args_->size() == 0)
33d1d391 9909 && n == "getcallersp")
105f9a24 9910 {
9911 static Named_object* builtin_frame_address;
9912 return this->lower_to_builtin(&builtin_frame_address,
9913 "__builtin_frame_address",
9914 1);
9915 }
9916 }
9917 }
9918
81affb1d 9919 // If this is a call to an imported function for which we have an
9920 // inlinable function body, add it to the list of functions to give
9921 // to the backend as inlining opportunities.
9922 Func_expression* fe = this->fn_->func_expression();
9923 if (fe != NULL
9924 && fe->named_object()->is_function_declaration()
9925 && fe->named_object()->func_declaration_value()->has_imported_body())
9926 gogo->add_imported_inlinable_function(fe->named_object());
9927
e440a328 9928 return this;
9929}
9930
9931// Lower a call to a varargs function. FUNCTION is the function in
9932// which the call occurs--it's not the function we are calling.
9933// VARARGS_TYPE is the type of the varargs parameter, a slice type.
9934// PARAM_COUNT is the number of parameters of the function we are
9935// calling; the last of these parameters will be the varargs
9936// parameter.
9937
09ea332d 9938void
e440a328 9939Call_expression::lower_varargs(Gogo* gogo, Named_object* function,
ceeb4318 9940 Statement_inserter* inserter,
0e9a2e72 9941 Type* varargs_type, size_t param_count,
9942 Slice_storage_escape_disp escape_disp)
e440a328 9943{
9944 if (this->varargs_are_lowered_)
09ea332d 9945 return;
e440a328 9946
b13c66cd 9947 Location loc = this->location();
e440a328 9948
c484d925 9949 go_assert(param_count > 0);
411eb89e 9950 go_assert(varargs_type->is_slice_type());
e440a328 9951
9952 size_t arg_count = this->args_ == NULL ? 0 : this->args_->size();
9953 if (arg_count < param_count - 1)
9954 {
9955 // Not enough arguments; will be caught in check_types.
09ea332d 9956 return;
e440a328 9957 }
9958
9959 Expression_list* old_args = this->args_;
9960 Expression_list* new_args = new Expression_list();
9961 bool push_empty_arg = false;
9962 if (old_args == NULL || old_args->empty())
9963 {
c484d925 9964 go_assert(param_count == 1);
e440a328 9965 push_empty_arg = true;
9966 }
9967 else
9968 {
9969 Expression_list::const_iterator pa;
9970 int i = 1;
9971 for (pa = old_args->begin(); pa != old_args->end(); ++pa, ++i)
9972 {
9973 if (static_cast<size_t>(i) == param_count)
9974 break;
9975 new_args->push_back(*pa);
9976 }
9977
9978 // We have reached the varargs parameter.
9979
9980 bool issued_error = false;
9981 if (pa == old_args->end())
9982 push_empty_arg = true;
9983 else if (pa + 1 == old_args->end() && this->is_varargs_)
9984 new_args->push_back(*pa);
9985 else if (this->is_varargs_)
9986 {
a6645f74 9987 if ((*pa)->type()->is_slice_type())
9988 this->report_error(_("too many arguments"));
9989 else
9990 {
631d5788 9991 go_error_at(this->location(),
9992 _("invalid use of %<...%> with non-slice"));
a6645f74 9993 this->set_is_error();
9994 }
09ea332d 9995 return;
e440a328 9996 }
e440a328 9997 else
9998 {
9999 Type* element_type = varargs_type->array_type()->element_type();
10000 Expression_list* vals = new Expression_list;
10001 for (; pa != old_args->end(); ++pa, ++i)
10002 {
10003 // Check types here so that we get a better message.
10004 Type* patype = (*pa)->type();
b13c66cd 10005 Location paloc = (*pa)->location();
e440a328 10006 if (!this->check_argument_type(i, element_type, patype,
10007 paloc, issued_error))
10008 continue;
10009 vals->push_back(*pa);
10010 }
0e9a2e72 10011 Slice_construction_expression* sce =
e440a328 10012 Expression::make_slice_composite_literal(varargs_type, vals, loc);
0e9a2e72 10013 if (escape_disp == SLICE_STORAGE_DOES_NOT_ESCAPE)
10014 sce->set_storage_does_not_escape();
10015 Expression* val = sce;
09ea332d 10016 gogo->lower_expression(function, inserter, &val);
e440a328 10017 new_args->push_back(val);
10018 }
10019 }
10020
10021 if (push_empty_arg)
10022 new_args->push_back(Expression::make_nil(loc));
10023
10024 // We can't return a new call expression here, because this one may
6d4c2432 10025 // be referenced by Call_result expressions. FIXME. We can't
10026 // delete OLD_ARGS because we may have both a Call_expression and a
10027 // Builtin_call_expression which refer to them. FIXME.
e440a328 10028 this->args_ = new_args;
10029 this->varargs_are_lowered_ = true;
e440a328 10030}
10031
105f9a24 10032// Return a call to __builtin_return_address or __builtin_frame_address.
10033
10034Expression*
10035Call_expression::lower_to_builtin(Named_object** pno, const char* name,
10036 int arg)
10037{
10038 if (*pno == NULL)
10039 *pno = Gogo::declare_builtin_rf_address(name);
10040
10041 Location loc = this->location();
10042
10043 Expression* fn = Expression::make_func_reference(*pno, NULL, loc);
10044 Expression* a = Expression::make_integer_ul(arg, NULL, loc);
10045 Expression_list *args = new Expression_list();
10046 args->push_back(a);
10047 Expression* call = Expression::make_call(fn, args, false, loc);
10048
10049 // The builtin functions return void*, but the Go functions return uintptr.
10050 Type* uintptr_type = Type::lookup_integer_type("uintptr");
10051 return Expression::make_cast(uintptr_type, call, loc);
10052}
10053
2c809f8f 10054// Flatten a call with multiple results into a temporary.
10055
10056Expression*
b8e86a51 10057Call_expression::do_flatten(Gogo* gogo, Named_object*,
10058 Statement_inserter* inserter)
2c809f8f 10059{
5bf8be8b 10060 if (this->is_erroneous_call())
10061 {
10062 go_assert(saw_errors());
10063 return Expression::make_error(this->location());
10064 }
b8e86a51 10065
91c0fd76 10066 if (this->is_flattened_)
10067 return this;
10068 this->is_flattened_ = true;
10069
b8e86a51 10070 // Add temporary variables for all arguments that require type
10071 // conversion.
10072 Function_type* fntype = this->get_function_type();
9782d556 10073 if (fntype == NULL)
10074 {
10075 go_assert(saw_errors());
10076 return this;
10077 }
b8e86a51 10078 if (this->args_ != NULL && !this->args_->empty()
10079 && fntype->parameters() != NULL && !fntype->parameters()->empty())
10080 {
10081 bool is_interface_method =
10082 this->fn_->interface_field_reference_expression() != NULL;
10083
10084 Expression_list *args = new Expression_list();
10085 Typed_identifier_list::const_iterator pp = fntype->parameters()->begin();
10086 Expression_list::const_iterator pa = this->args_->begin();
10087 if (!is_interface_method && fntype->is_method())
10088 {
10089 // The receiver argument.
10090 args->push_back(*pa);
10091 ++pa;
10092 }
10093 for (; pa != this->args_->end(); ++pa, ++pp)
10094 {
10095 go_assert(pp != fntype->parameters()->end());
3a522dcc 10096 if (Type::are_identical(pp->type(), (*pa)->type(),
10097 Type::COMPARE_TAGS, NULL))
b8e86a51 10098 args->push_back(*pa);
10099 else
10100 {
10101 Location loc = (*pa)->location();
8ba8cc87 10102 Expression* arg = *pa;
10103 if (!arg->is_variable())
10104 {
10105 Temporary_statement *temp =
10106 Statement::make_temporary(NULL, arg, loc);
10107 inserter->insert(temp);
10108 arg = Expression::make_temporary_reference(temp, loc);
10109 }
10110 arg = Expression::convert_for_assignment(gogo, pp->type(), arg,
10111 loc);
10112 args->push_back(arg);
b8e86a51 10113 }
10114 }
10115 delete this->args_;
10116 this->args_ = args;
10117 }
10118
2c809f8f 10119 return this;
10120}
10121
ceeb4318 10122// Get the function type. This can return NULL in error cases.
e440a328 10123
10124Function_type*
10125Call_expression::get_function_type() const
10126{
10127 return this->fn_->type()->function_type();
10128}
10129
10130// Return the number of values which this call will return.
10131
10132size_t
10133Call_expression::result_count() const
10134{
10135 const Function_type* fntype = this->get_function_type();
10136 if (fntype == NULL)
10137 return 0;
10138 if (fntype->results() == NULL)
10139 return 0;
10140 return fntype->results()->size();
10141}
10142
5731103c 10143// Return the temporary that holds the result for a call with multiple
10144// results.
ceeb4318 10145
10146Temporary_statement*
5731103c 10147Call_expression::results() const
ceeb4318 10148{
5731103c 10149 if (this->call_temp_ == NULL)
cd238b8d 10150 {
10151 go_assert(saw_errors());
10152 return NULL;
10153 }
5731103c 10154 return this->call_temp_;
ceeb4318 10155}
10156
1373401e 10157// Set the number of results expected from a call expression.
10158
10159void
10160Call_expression::set_expected_result_count(size_t count)
10161{
10162 go_assert(this->expected_result_count_ == 0);
10163 this->expected_result_count_ = count;
10164}
10165
e440a328 10166// Return whether this is a call to the predeclared function recover.
10167
10168bool
10169Call_expression::is_recover_call() const
10170{
10171 return this->do_is_recover_call();
10172}
10173
10174// Set the argument to the recover function.
10175
10176void
10177Call_expression::set_recover_arg(Expression* arg)
10178{
10179 this->do_set_recover_arg(arg);
10180}
10181
10182// Virtual functions also implemented by Builtin_call_expression.
10183
10184bool
10185Call_expression::do_is_recover_call() const
10186{
10187 return false;
10188}
10189
10190void
10191Call_expression::do_set_recover_arg(Expression*)
10192{
c3e6f413 10193 go_unreachable();
e440a328 10194}
10195
ceeb4318 10196// We have found an error with this call expression; return true if
10197// we should report it.
10198
10199bool
10200Call_expression::issue_error()
10201{
10202 if (this->issued_error_)
10203 return false;
10204 else
10205 {
10206 this->issued_error_ = true;
10207 return true;
10208 }
10209}
10210
5bf8be8b 10211// Whether or not this call contains errors, either in the call or the
10212// arguments to the call.
10213
10214bool
10215Call_expression::is_erroneous_call()
10216{
10217 if (this->is_error_expression() || this->fn()->is_error_expression())
10218 return true;
10219
10220 if (this->args() == NULL)
10221 return false;
10222 for (Expression_list::iterator pa = this->args()->begin();
10223 pa != this->args()->end();
10224 ++pa)
10225 {
10226 if ((*pa)->type()->is_error_type() || (*pa)->is_error_expression())
10227 return true;
10228 }
10229 return false;
10230}
10231
e440a328 10232// Get the type.
10233
10234Type*
10235Call_expression::do_type()
10236{
10237 if (this->type_ != NULL)
10238 return this->type_;
10239
10240 Type* ret;
10241 Function_type* fntype = this->get_function_type();
10242 if (fntype == NULL)
10243 return Type::make_error_type();
10244
10245 const Typed_identifier_list* results = fntype->results();
10246 if (results == NULL)
10247 ret = Type::make_void_type();
10248 else if (results->size() == 1)
10249 ret = results->begin()->type();
10250 else
2801343b 10251 ret = Type::make_call_multiple_result_type(this);
e440a328 10252
10253 this->type_ = ret;
10254
10255 return this->type_;
10256}
10257
10258// Determine types for a call expression. We can use the function
10259// parameter types to set the types of the arguments.
10260
10261void
10262Call_expression::do_determine_type(const Type_context*)
10263{
fb94b0ca 10264 if (!this->determining_types())
10265 return;
10266
e440a328 10267 this->fn_->determine_type_no_context();
10268 Function_type* fntype = this->get_function_type();
10269 const Typed_identifier_list* parameters = NULL;
10270 if (fntype != NULL)
10271 parameters = fntype->parameters();
10272 if (this->args_ != NULL)
10273 {
10274 Typed_identifier_list::const_iterator pt;
10275 if (parameters != NULL)
10276 pt = parameters->begin();
09ea332d 10277 bool first = true;
e440a328 10278 for (Expression_list::const_iterator pa = this->args_->begin();
10279 pa != this->args_->end();
10280 ++pa)
10281 {
09ea332d 10282 if (first)
10283 {
10284 first = false;
10285 // If this is a method, the first argument is the
10286 // receiver.
10287 if (fntype != NULL && fntype->is_method())
10288 {
10289 Type* rtype = fntype->receiver()->type();
10290 // The receiver is always passed as a pointer.
10291 if (rtype->points_to() == NULL)
10292 rtype = Type::make_pointer_type(rtype);
10293 Type_context subcontext(rtype, false);
10294 (*pa)->determine_type(&subcontext);
10295 continue;
10296 }
10297 }
10298
e440a328 10299 if (parameters != NULL && pt != parameters->end())
10300 {
10301 Type_context subcontext(pt->type(), false);
10302 (*pa)->determine_type(&subcontext);
10303 ++pt;
10304 }
10305 else
10306 (*pa)->determine_type_no_context();
10307 }
10308 }
10309}
10310
fb94b0ca 10311// Called when determining types for a Call_expression. Return true
10312// if we should go ahead, false if they have already been determined.
10313
10314bool
10315Call_expression::determining_types()
10316{
10317 if (this->types_are_determined_)
10318 return false;
10319 else
10320 {
10321 this->types_are_determined_ = true;
10322 return true;
10323 }
10324}
10325
e440a328 10326// Check types for parameter I.
10327
10328bool
10329Call_expression::check_argument_type(int i, const Type* parameter_type,
10330 const Type* argument_type,
b13c66cd 10331 Location argument_location,
e440a328 10332 bool issued_error)
10333{
10334 std::string reason;
1eae365b 10335 if (!Type::are_assignable(parameter_type, argument_type, &reason))
e440a328 10336 {
10337 if (!issued_error)
10338 {
10339 if (reason.empty())
631d5788 10340 go_error_at(argument_location, "argument %d has incompatible type", i);
e440a328 10341 else
631d5788 10342 go_error_at(argument_location,
10343 "argument %d has incompatible type (%s)",
10344 i, reason.c_str());
e440a328 10345 }
10346 this->set_is_error();
10347 return false;
10348 }
10349 return true;
10350}
10351
10352// Check types.
10353
10354void
10355Call_expression::do_check_types(Gogo*)
10356{
a6645f74 10357 if (this->classification() == EXPRESSION_ERROR)
10358 return;
10359
e440a328 10360 Function_type* fntype = this->get_function_type();
10361 if (fntype == NULL)
10362 {
5c13bd80 10363 if (!this->fn_->type()->is_error())
e440a328 10364 this->report_error(_("expected function"));
10365 return;
10366 }
10367
1373401e 10368 if (this->expected_result_count_ != 0
10369 && this->expected_result_count_ != this->result_count())
10370 {
10371 if (this->issue_error())
10372 this->report_error(_("function result count mismatch"));
10373 this->set_is_error();
10374 return;
10375 }
10376
09ea332d 10377 bool is_method = fntype->is_method();
10378 if (is_method)
e440a328 10379 {
09ea332d 10380 go_assert(this->args_ != NULL && !this->args_->empty());
10381 Type* rtype = fntype->receiver()->type();
10382 Expression* first_arg = this->args_->front();
1eae365b 10383 // We dereference the values since receivers are always passed
10384 // as pointers.
09ea332d 10385 std::string reason;
1eae365b 10386 if (!Type::are_assignable(rtype->deref(), first_arg->type()->deref(),
10387 &reason))
e440a328 10388 {
09ea332d 10389 if (reason.empty())
10390 this->report_error(_("incompatible type for receiver"));
10391 else
e440a328 10392 {
631d5788 10393 go_error_at(this->location(),
10394 "incompatible type for receiver (%s)",
10395 reason.c_str());
09ea332d 10396 this->set_is_error();
e440a328 10397 }
10398 }
10399 }
10400
10401 // Note that varargs was handled by the lower_varargs() method, so
a6645f74 10402 // we don't have to worry about it here unless something is wrong.
10403 if (this->is_varargs_ && !this->varargs_are_lowered_)
10404 {
10405 if (!fntype->is_varargs())
10406 {
631d5788 10407 go_error_at(this->location(),
10408 _("invalid use of %<...%> calling non-variadic function"));
a6645f74 10409 this->set_is_error();
10410 return;
10411 }
10412 }
e440a328 10413
10414 const Typed_identifier_list* parameters = fntype->parameters();
33d1d391 10415 if (this->args_ == NULL || this->args_->size() == 0)
e440a328 10416 {
10417 if (parameters != NULL && !parameters->empty())
10418 this->report_error(_("not enough arguments"));
10419 }
10420 else if (parameters == NULL)
09ea332d 10421 {
10422 if (!is_method || this->args_->size() > 1)
10423 this->report_error(_("too many arguments"));
10424 }
1373401e 10425 else if (this->args_->size() == 1
10426 && this->args_->front()->call_expression() != NULL
10427 && this->args_->front()->call_expression()->result_count() > 1)
10428 {
10429 // This is F(G()) when G returns more than one result. If the
10430 // results can be matched to parameters, it would have been
10431 // lowered in do_lower. If we get here we know there is a
10432 // mismatch.
10433 if (this->args_->front()->call_expression()->result_count()
10434 < parameters->size())
10435 this->report_error(_("not enough arguments"));
10436 else
10437 this->report_error(_("too many arguments"));
10438 }
e440a328 10439 else
10440 {
10441 int i = 0;
09ea332d 10442 Expression_list::const_iterator pa = this->args_->begin();
10443 if (is_method)
10444 ++pa;
10445 for (Typed_identifier_list::const_iterator pt = parameters->begin();
10446 pt != parameters->end();
10447 ++pt, ++pa, ++i)
e440a328 10448 {
09ea332d 10449 if (pa == this->args_->end())
e440a328 10450 {
09ea332d 10451 this->report_error(_("not enough arguments"));
e440a328 10452 return;
10453 }
10454 this->check_argument_type(i + 1, pt->type(), (*pa)->type(),
10455 (*pa)->location(), false);
10456 }
09ea332d 10457 if (pa != this->args_->end())
10458 this->report_error(_("too many arguments"));
e440a328 10459 }
10460}
10461
72666aed 10462Expression*
10463Call_expression::do_copy()
10464{
10465 Call_expression* call =
10466 Expression::make_call(this->fn_->copy(),
10467 (this->args_ == NULL
10468 ? NULL
10469 : this->args_->copy()),
10470 this->is_varargs_, this->location());
10471
10472 if (this->varargs_are_lowered_)
10473 call->set_varargs_are_lowered();
28819633 10474 if (this->is_deferred_)
10475 call->set_is_deferred();
10476 if (this->is_concurrent_)
10477 call->set_is_concurrent();
72666aed 10478 return call;
10479}
10480
e440a328 10481// Return whether we have to use a temporary variable to ensure that
10482// we evaluate this call expression in order. If the call returns no
ceeb4318 10483// results then it will inevitably be executed last.
e440a328 10484
10485bool
10486Call_expression::do_must_eval_in_order() const
10487{
ceeb4318 10488 return this->result_count() > 0;
e440a328 10489}
10490
e440a328 10491// Get the function and the first argument to use when calling an
10492// interface method.
10493
2387f644 10494Expression*
e440a328 10495Call_expression::interface_method_function(
e440a328 10496 Interface_field_reference_expression* interface_method,
db122cb9 10497 Expression** first_arg_ptr,
10498 Location location)
e440a328 10499{
db122cb9 10500 Expression* object = interface_method->get_underlying_object();
10501 Type* unsafe_ptr_type = Type::make_pointer_type(Type::make_void_type());
10502 *first_arg_ptr =
10503 Expression::make_unsafe_cast(unsafe_ptr_type, object, location);
2387f644 10504 return interface_method->get_function();
e440a328 10505}
10506
10507// Build the call expression.
10508
ea664253 10509Bexpression*
10510Call_expression::do_get_backend(Translate_context* context)
e440a328 10511{
5731103c 10512 Location location = this->location();
10513
2c809f8f 10514 if (this->call_ != NULL)
5731103c 10515 {
10516 // If the call returns multiple results, make a new reference to
10517 // the temporary.
10518 if (this->call_temp_ != NULL)
10519 {
10520 Expression* ref =
10521 Expression::make_temporary_reference(this->call_temp_, location);
10522 return ref->get_backend(context);
10523 }
10524
10525 return this->call_;
10526 }
e440a328 10527
10528 Function_type* fntype = this->get_function_type();
10529 if (fntype == NULL)
ea664253 10530 return context->backend()->error_expression();
e440a328 10531
10532 if (this->fn_->is_error_expression())
ea664253 10533 return context->backend()->error_expression();
e440a328 10534
10535 Gogo* gogo = context->gogo();
e440a328 10536
10537 Func_expression* func = this->fn_->func_expression();
e440a328 10538 Interface_field_reference_expression* interface_method =
10539 this->fn_->interface_field_reference_expression();
10540 const bool has_closure = func != NULL && func->closure() != NULL;
09ea332d 10541 const bool is_interface_method = interface_method != NULL;
e440a328 10542
f8bdf81a 10543 bool has_closure_arg;
8381eda7 10544 if (has_closure)
f8bdf81a 10545 has_closure_arg = true;
8381eda7 10546 else if (func != NULL)
f8bdf81a 10547 has_closure_arg = false;
8381eda7 10548 else if (is_interface_method)
f8bdf81a 10549 has_closure_arg = false;
8381eda7 10550 else
f8bdf81a 10551 has_closure_arg = true;
8381eda7 10552
e440a328 10553 int nargs;
2c809f8f 10554 std::vector<Bexpression*> fn_args;
e440a328 10555 if (this->args_ == NULL || this->args_->empty())
10556 {
f8bdf81a 10557 nargs = is_interface_method ? 1 : 0;
2c809f8f 10558 if (nargs > 0)
10559 fn_args.resize(1);
e440a328 10560 }
09ea332d 10561 else if (fntype->parameters() == NULL || fntype->parameters()->empty())
10562 {
10563 // Passing a receiver parameter.
10564 go_assert(!is_interface_method
10565 && fntype->is_method()
10566 && this->args_->size() == 1);
f8bdf81a 10567 nargs = 1;
2c809f8f 10568 fn_args.resize(1);
ea664253 10569 fn_args[0] = this->args_->front()->get_backend(context);
09ea332d 10570 }
e440a328 10571 else
10572 {
10573 const Typed_identifier_list* params = fntype->parameters();
e440a328 10574
10575 nargs = this->args_->size();
09ea332d 10576 int i = is_interface_method ? 1 : 0;
e440a328 10577 nargs += i;
2c809f8f 10578 fn_args.resize(nargs);
e440a328 10579
10580 Typed_identifier_list::const_iterator pp = params->begin();
09ea332d 10581 Expression_list::const_iterator pe = this->args_->begin();
10582 if (!is_interface_method && fntype->is_method())
10583 {
ea664253 10584 fn_args[i] = (*pe)->get_backend(context);
09ea332d 10585 ++pe;
10586 ++i;
10587 }
10588 for (; pe != this->args_->end(); ++pe, ++pp, ++i)
e440a328 10589 {
c484d925 10590 go_assert(pp != params->end());
2c809f8f 10591 Expression* arg =
10592 Expression::convert_for_assignment(gogo, pp->type(), *pe,
10593 location);
ea664253 10594 fn_args[i] = arg->get_backend(context);
e440a328 10595 }
c484d925 10596 go_assert(pp == params->end());
f8bdf81a 10597 go_assert(i == nargs);
e440a328 10598 }
10599
2c809f8f 10600 Expression* fn;
10601 Expression* closure = NULL;
8381eda7 10602 if (func != NULL)
10603 {
10604 Named_object* no = func->named_object();
2c809f8f 10605 fn = Expression::make_func_code_reference(no, location);
10606 if (has_closure)
10607 closure = func->closure();
8381eda7 10608 }
09ea332d 10609 else if (!is_interface_method)
8381eda7 10610 {
2c809f8f 10611 closure = this->fn_;
10612
10613 // The backend representation of this function type is a pointer
10614 // to a struct whose first field is the actual function to call.
10615 Type* pfntype =
10616 Type::make_pointer_type(
10617 Type::make_pointer_type(Type::make_void_type()));
10618 fn = Expression::make_unsafe_cast(pfntype, this->fn_, location);
f614ea8b 10619 fn = Expression::make_dereference(fn, NIL_CHECK_NOT_NEEDED, location);
2c809f8f 10620 }
e440a328 10621 else
cf609de4 10622 {
2387f644 10623 Expression* first_arg;
db122cb9 10624 fn = this->interface_method_function(interface_method, &first_arg,
10625 location);
ea664253 10626 fn_args[0] = first_arg->get_backend(context);
e440a328 10627 }
10628
1ecc6157 10629 Bexpression* bclosure = NULL;
10630 if (has_closure_arg)
10631 bclosure = closure->get_backend(context);
f8bdf81a 10632 else
1ecc6157 10633 go_assert(closure == NULL);
f8bdf81a 10634
ea664253 10635 Bexpression* bfn = fn->get_backend(context);
80d1e1a8 10636
10637 // When not calling a named function directly, use a type conversion
10638 // in case the type of the function is a recursive type which refers
10639 // to itself. We don't do this for an interface method because 1)
10640 // an interface method never refers to itself, so we always have a
10641 // function type here; 2) we pass an extra first argument to an
10642 // interface method, so fntype is not correct.
10643 if (func == NULL && !is_interface_method)
10644 {
10645 Btype* bft = fntype->get_backend_fntype(gogo);
10646 bfn = gogo->backend()->convert_expression(bft, bfn, location);
10647 }
10648
4ced7af9 10649 Bfunction* bfunction = NULL;
10650 if (context->function())
10651 bfunction = context->function()->func_value()->get_decl();
10652 Bexpression* call = gogo->backend()->call_expression(bfunction, bfn,
10653 fn_args, bclosure,
10654 location);
e440a328 10655
5731103c 10656 if (this->call_temp_ != NULL)
e440a328 10657 {
5731103c 10658 // This case occurs when the call returns multiple results.
e440a328 10659
5731103c 10660 Expression* ref = Expression::make_temporary_reference(this->call_temp_,
10661 location);
10662 Bexpression* bref = ref->get_backend(context);
10663 Bstatement* bassn = gogo->backend()->assignment_statement(bfunction,
10664 bref, call,
10665 location);
e440a328 10666
5731103c 10667 ref = Expression::make_temporary_reference(this->call_temp_, location);
10668 this->call_ = ref->get_backend(context);
10669
10670 return gogo->backend()->compound_expression(bassn, this->call_,
10671 location);
2c809f8f 10672 }
e440a328 10673
2c809f8f 10674 this->call_ = call;
ea664253 10675 return this->call_;
e440a328 10676}
10677
d751bb78 10678// Dump ast representation for a call expressin.
10679
10680void
10681Call_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
10682{
10683 this->fn_->dump_expression(ast_dump_context);
10684 ast_dump_context->ostream() << "(";
10685 if (args_ != NULL)
10686 ast_dump_context->dump_expression_list(this->args_);
10687
10688 ast_dump_context->ostream() << ") ";
10689}
10690
e440a328 10691// Make a call expression.
10692
10693Call_expression*
10694Expression::make_call(Expression* fn, Expression_list* args, bool is_varargs,
b13c66cd 10695 Location location)
e440a328 10696{
10697 return new Call_expression(fn, args, is_varargs, location);
10698}
10699
da244e59 10700// Class Call_result_expression.
e440a328 10701
10702// Traverse a call result.
10703
10704int
10705Call_result_expression::do_traverse(Traverse* traverse)
10706{
10707 if (traverse->remember_expression(this->call_))
10708 {
10709 // We have already traversed the call expression.
10710 return TRAVERSE_CONTINUE;
10711 }
10712 return Expression::traverse(&this->call_, traverse);
10713}
10714
10715// Get the type.
10716
10717Type*
10718Call_result_expression::do_type()
10719{
425dd051 10720 if (this->classification() == EXPRESSION_ERROR)
10721 return Type::make_error_type();
10722
e440a328 10723 // THIS->CALL_ can be replaced with a temporary reference due to
10724 // Call_expression::do_must_eval_in_order when there is an error.
10725 Call_expression* ce = this->call_->call_expression();
10726 if (ce == NULL)
5e85f268 10727 {
10728 this->set_is_error();
10729 return Type::make_error_type();
10730 }
e440a328 10731 Function_type* fntype = ce->get_function_type();
10732 if (fntype == NULL)
5e85f268 10733 {
e37658e2 10734 if (ce->issue_error())
99b3f06f 10735 {
10736 if (!ce->fn()->type()->is_error())
10737 this->report_error(_("expected function"));
10738 }
5e85f268 10739 this->set_is_error();
10740 return Type::make_error_type();
10741 }
e440a328 10742 const Typed_identifier_list* results = fntype->results();
ceeb4318 10743 if (results == NULL || results->size() < 2)
7b8d861f 10744 {
ceeb4318 10745 if (ce->issue_error())
10746 this->report_error(_("number of results does not match "
10747 "number of values"));
7b8d861f 10748 return Type::make_error_type();
10749 }
e440a328 10750 Typed_identifier_list::const_iterator pr = results->begin();
10751 for (unsigned int i = 0; i < this->index_; ++i)
10752 {
10753 if (pr == results->end())
425dd051 10754 break;
e440a328 10755 ++pr;
10756 }
10757 if (pr == results->end())
425dd051 10758 {
ceeb4318 10759 if (ce->issue_error())
10760 this->report_error(_("number of results does not match "
10761 "number of values"));
425dd051 10762 return Type::make_error_type();
10763 }
e440a328 10764 return pr->type();
10765}
10766
425dd051 10767// Check the type. Just make sure that we trigger the warning in
10768// do_type.
e440a328 10769
10770void
10771Call_result_expression::do_check_types(Gogo*)
10772{
425dd051 10773 this->type();
e440a328 10774}
10775
10776// Determine the type. We have nothing to do here, but the 0 result
10777// needs to pass down to the caller.
10778
10779void
10780Call_result_expression::do_determine_type(const Type_context*)
10781{
fb94b0ca 10782 this->call_->determine_type_no_context();
e440a328 10783}
10784
ea664253 10785// Return the backend representation. We just refer to the temporary set by the
10786// call expression. We don't do this at lowering time because it makes it
ceeb4318 10787// hard to evaluate the call at the right time.
e440a328 10788
ea664253 10789Bexpression*
10790Call_result_expression::do_get_backend(Translate_context* context)
e440a328 10791{
ceeb4318 10792 Call_expression* ce = this->call_->call_expression();
cd238b8d 10793 if (ce == NULL)
10794 {
10795 go_assert(this->call_->is_error_expression());
ea664253 10796 return context->backend()->error_expression();
cd238b8d 10797 }
5731103c 10798 Temporary_statement* ts = ce->results();
cd238b8d 10799 if (ts == NULL)
10800 {
10801 go_assert(saw_errors());
ea664253 10802 return context->backend()->error_expression();
cd238b8d 10803 }
ceeb4318 10804 Expression* ref = Expression::make_temporary_reference(ts, this->location());
5731103c 10805 ref = Expression::make_field_reference(ref, this->index_, this->location());
ea664253 10806 return ref->get_backend(context);
e440a328 10807}
10808
d751bb78 10809// Dump ast representation for a call result expression.
10810
10811void
10812Call_result_expression::do_dump_expression(Ast_dump_context* ast_dump_context)
10813 const
10814{
10815 // FIXME: Wouldn't it be better if the call is assigned to a temporary
10816 // (struct) and the fields are referenced instead.
10817 ast_dump_context->ostream() << this->index_ << "@(";
10818 ast_dump_context->dump_expression(this->call_);
10819 ast_dump_context->ostream() << ")";
10820}
10821
e440a328 10822// Make a reference to a single result of a call which returns
10823// multiple results.
10824
10825Expression*
10826Expression::make_call_result(Call_expression* call, unsigned int index)
10827{
10828 return new Call_result_expression(call, index);
10829}
10830
10831// Class Index_expression.
10832
10833// Traversal.
10834
10835int
10836Index_expression::do_traverse(Traverse* traverse)
10837{
10838 if (Expression::traverse(&this->left_, traverse) == TRAVERSE_EXIT
10839 || Expression::traverse(&this->start_, traverse) == TRAVERSE_EXIT
10840 || (this->end_ != NULL
acf2b673 10841 && Expression::traverse(&this->end_, traverse) == TRAVERSE_EXIT)
10842 || (this->cap_ != NULL
10843 && Expression::traverse(&this->cap_, traverse) == TRAVERSE_EXIT))
e440a328 10844 return TRAVERSE_EXIT;
10845 return TRAVERSE_CONTINUE;
10846}
10847
10848// Lower an index expression. This converts the generic index
10849// expression into an array index, a string index, or a map index.
10850
10851Expression*
ceeb4318 10852Index_expression::do_lower(Gogo*, Named_object*, Statement_inserter*, int)
e440a328 10853{
b13c66cd 10854 Location location = this->location();
e440a328 10855 Expression* left = this->left_;
10856 Expression* start = this->start_;
10857 Expression* end = this->end_;
acf2b673 10858 Expression* cap = this->cap_;
e440a328 10859
10860 Type* type = left->type();
5c13bd80 10861 if (type->is_error())
d9f3743a 10862 {
10863 go_assert(saw_errors());
10864 return Expression::make_error(location);
10865 }
b0cf7ddd 10866 else if (left->is_type_expression())
10867 {
631d5788 10868 go_error_at(location, "attempt to index type expression");
b0cf7ddd 10869 return Expression::make_error(location);
10870 }
e440a328 10871 else if (type->array_type() != NULL)
acf2b673 10872 return Expression::make_array_index(left, start, end, cap, location);
e440a328 10873 else if (type->points_to() != NULL
10874 && type->points_to()->array_type() != NULL
411eb89e 10875 && !type->points_to()->is_slice_type())
e440a328 10876 {
f614ea8b 10877 Expression* deref =
10878 Expression::make_dereference(left, NIL_CHECK_DEFAULT, location);
38092374 10879
10880 // For an ordinary index into the array, the pointer will be
10881 // dereferenced. For a slice it will not--the resulting slice
10882 // will simply reuse the pointer, which is incorrect if that
10883 // pointer is nil.
10884 if (end != NULL || cap != NULL)
10885 deref->issue_nil_check();
10886
acf2b673 10887 return Expression::make_array_index(deref, start, end, cap, location);
e440a328 10888 }
10889 else if (type->is_string_type())
acf2b673 10890 {
10891 if (cap != NULL)
10892 {
631d5788 10893 go_error_at(location, "invalid 3-index slice of string");
acf2b673 10894 return Expression::make_error(location);
10895 }
10896 return Expression::make_string_index(left, start, end, location);
10897 }
e440a328 10898 else if (type->map_type() != NULL)
10899 {
acf2b673 10900 if (end != NULL || cap != NULL)
e440a328 10901 {
631d5788 10902 go_error_at(location, "invalid slice of map");
e440a328 10903 return Expression::make_error(location);
10904 }
0d5530d9 10905 return Expression::make_map_index(left, start, location);
e440a328 10906 }
b1aba207 10907 else if (cap != NULL)
10908 {
10909 go_error_at(location,
10910 "invalid 3-index slice of object that is not a slice");
10911 return Expression::make_error(location);
10912 }
10913 else if (end != NULL)
10914 {
10915 go_error_at(location,
10916 ("attempt to slice object that is not "
10917 "array, slice, or string"));
10918 return Expression::make_error(location);
10919 }
e440a328 10920 else
10921 {
631d5788 10922 go_error_at(location,
b1aba207 10923 ("attempt to index object that is not "
10924 "array, slice, string, or map"));
e440a328 10925 return Expression::make_error(location);
10926 }
10927}
10928
acf2b673 10929// Write an indexed expression
10930// (expr[expr:expr:expr], expr[expr:expr] or expr[expr]) to a dump context.
d751bb78 10931
10932void
10933Index_expression::dump_index_expression(Ast_dump_context* ast_dump_context,
10934 const Expression* expr,
10935 const Expression* start,
acf2b673 10936 const Expression* end,
10937 const Expression* cap)
d751bb78 10938{
10939 expr->dump_expression(ast_dump_context);
10940 ast_dump_context->ostream() << "[";
10941 start->dump_expression(ast_dump_context);
10942 if (end != NULL)
10943 {
10944 ast_dump_context->ostream() << ":";
10945 end->dump_expression(ast_dump_context);
10946 }
acf2b673 10947 if (cap != NULL)
10948 {
10949 ast_dump_context->ostream() << ":";
10950 cap->dump_expression(ast_dump_context);
10951 }
d751bb78 10952 ast_dump_context->ostream() << "]";
10953}
10954
10955// Dump ast representation for an index expression.
10956
10957void
10958Index_expression::do_dump_expression(Ast_dump_context* ast_dump_context)
10959 const
10960{
10961 Index_expression::dump_index_expression(ast_dump_context, this->left_,
acf2b673 10962 this->start_, this->end_, this->cap_);
d751bb78 10963}
10964
e440a328 10965// Make an index expression.
10966
10967Expression*
10968Expression::make_index(Expression* left, Expression* start, Expression* end,
acf2b673 10969 Expression* cap, Location location)
e440a328 10970{
acf2b673 10971 return new Index_expression(left, start, end, cap, location);
e440a328 10972}
10973
da244e59 10974// Class Array_index_expression.
e440a328 10975
10976// Array index traversal.
10977
10978int
10979Array_index_expression::do_traverse(Traverse* traverse)
10980{
10981 if (Expression::traverse(&this->array_, traverse) == TRAVERSE_EXIT)
10982 return TRAVERSE_EXIT;
10983 if (Expression::traverse(&this->start_, traverse) == TRAVERSE_EXIT)
10984 return TRAVERSE_EXIT;
10985 if (this->end_ != NULL)
10986 {
10987 if (Expression::traverse(&this->end_, traverse) == TRAVERSE_EXIT)
10988 return TRAVERSE_EXIT;
10989 }
acf2b673 10990 if (this->cap_ != NULL)
10991 {
10992 if (Expression::traverse(&this->cap_, traverse) == TRAVERSE_EXIT)
10993 return TRAVERSE_EXIT;
10994 }
e440a328 10995 return TRAVERSE_CONTINUE;
10996}
10997
10998// Return the type of an array index.
10999
11000Type*
11001Array_index_expression::do_type()
11002{
11003 if (this->type_ == NULL)
11004 {
11005 Array_type* type = this->array_->type()->array_type();
11006 if (type == NULL)
11007 this->type_ = Type::make_error_type();
11008 else if (this->end_ == NULL)
11009 this->type_ = type->element_type();
411eb89e 11010 else if (type->is_slice_type())
e440a328 11011 {
11012 // A slice of a slice has the same type as the original
11013 // slice.
11014 this->type_ = this->array_->type()->deref();
11015 }
11016 else
11017 {
11018 // A slice of an array is a slice.
11019 this->type_ = Type::make_array_type(type->element_type(), NULL);
11020 }
11021 }
11022 return this->type_;
11023}
11024
11025// Set the type of an array index.
11026
11027void
11028Array_index_expression::do_determine_type(const Type_context*)
11029{
11030 this->array_->determine_type_no_context();
f77aa642 11031
11032 Type_context index_context(Type::lookup_integer_type("int"), false);
11033 if (this->start_->is_constant())
11034 this->start_->determine_type(&index_context);
11035 else
11036 this->start_->determine_type_no_context();
e440a328 11037 if (this->end_ != NULL)
f77aa642 11038 {
11039 if (this->end_->is_constant())
11040 this->end_->determine_type(&index_context);
11041 else
11042 this->end_->determine_type_no_context();
11043 }
acf2b673 11044 if (this->cap_ != NULL)
f77aa642 11045 {
11046 if (this->cap_->is_constant())
11047 this->cap_->determine_type(&index_context);
11048 else
11049 this->cap_->determine_type_no_context();
11050 }
e440a328 11051}
11052
11053// Check types of an array index.
11054
11055void
b7327dbf 11056Array_index_expression::do_check_types(Gogo*)
e440a328 11057{
f6bc81e6 11058 Numeric_constant nc;
11059 unsigned long v;
11060 if (this->start_->type()->integer_type() == NULL
11061 && !this->start_->type()->is_error()
11062 && (!this->start_->numeric_constant_value(&nc)
11063 || nc.to_unsigned_long(&v) == Numeric_constant::NC_UL_NOTINT))
e440a328 11064 this->report_error(_("index must be integer"));
11065 if (this->end_ != NULL
11066 && this->end_->type()->integer_type() == NULL
99b3f06f 11067 && !this->end_->type()->is_error()
11068 && !this->end_->is_nil_expression()
f6bc81e6 11069 && !this->end_->is_error_expression()
11070 && (!this->end_->numeric_constant_value(&nc)
11071 || nc.to_unsigned_long(&v) == Numeric_constant::NC_UL_NOTINT))
e440a328 11072 this->report_error(_("slice end must be integer"));
acf2b673 11073 if (this->cap_ != NULL
11074 && this->cap_->type()->integer_type() == NULL
11075 && !this->cap_->type()->is_error()
11076 && !this->cap_->is_nil_expression()
11077 && !this->cap_->is_error_expression()
11078 && (!this->cap_->numeric_constant_value(&nc)
11079 || nc.to_unsigned_long(&v) == Numeric_constant::NC_UL_NOTINT))
11080 this->report_error(_("slice capacity must be integer"));
e440a328 11081
11082 Array_type* array_type = this->array_->type()->array_type();
f9c68f17 11083 if (array_type == NULL)
11084 {
c484d925 11085 go_assert(this->array_->type()->is_error());
f9c68f17 11086 return;
11087 }
e440a328 11088
11089 unsigned int int_bits =
11090 Type::lookup_integer_type("int")->integer_type()->bits();
11091
0c77715b 11092 Numeric_constant lvalnc;
e440a328 11093 mpz_t lval;
e440a328 11094 bool lval_valid = (array_type->length() != NULL
0c77715b 11095 && array_type->length()->numeric_constant_value(&lvalnc)
11096 && lvalnc.to_int(&lval));
11097 Numeric_constant inc;
e440a328 11098 mpz_t ival;
0bd5d859 11099 bool ival_valid = false;
0c77715b 11100 if (this->start_->numeric_constant_value(&inc) && inc.to_int(&ival))
e440a328 11101 {
0bd5d859 11102 ival_valid = true;
e440a328 11103 if (mpz_sgn(ival) < 0
11104 || mpz_sizeinbase(ival, 2) >= int_bits
11105 || (lval_valid
11106 && (this->end_ == NULL
11107 ? mpz_cmp(ival, lval) >= 0
11108 : mpz_cmp(ival, lval) > 0)))
11109 {
631d5788 11110 go_error_at(this->start_->location(), "array index out of bounds");
e440a328 11111 this->set_is_error();
11112 }
11113 }
11114 if (this->end_ != NULL && !this->end_->is_nil_expression())
11115 {
0c77715b 11116 Numeric_constant enc;
11117 mpz_t eval;
acf2b673 11118 bool eval_valid = false;
0c77715b 11119 if (this->end_->numeric_constant_value(&enc) && enc.to_int(&eval))
e440a328 11120 {
acf2b673 11121 eval_valid = true;
0c77715b 11122 if (mpz_sgn(eval) < 0
11123 || mpz_sizeinbase(eval, 2) >= int_bits
11124 || (lval_valid && mpz_cmp(eval, lval) > 0))
e440a328 11125 {
631d5788 11126 go_error_at(this->end_->location(), "array index out of bounds");
e440a328 11127 this->set_is_error();
11128 }
0bd5d859 11129 else if (ival_valid && mpz_cmp(ival, eval) > 0)
11130 this->report_error(_("inverted slice range"));
e440a328 11131 }
acf2b673 11132
11133 Numeric_constant cnc;
11134 mpz_t cval;
11135 if (this->cap_ != NULL
11136 && this->cap_->numeric_constant_value(&cnc) && cnc.to_int(&cval))
11137 {
11138 if (mpz_sgn(cval) < 0
11139 || mpz_sizeinbase(cval, 2) >= int_bits
11140 || (lval_valid && mpz_cmp(cval, lval) > 0))
11141 {
631d5788 11142 go_error_at(this->cap_->location(), "array index out of bounds");
acf2b673 11143 this->set_is_error();
11144 }
11145 else if (ival_valid && mpz_cmp(ival, cval) > 0)
11146 {
631d5788 11147 go_error_at(this->cap_->location(),
11148 "invalid slice index: capacity less than start");
acf2b673 11149 this->set_is_error();
11150 }
11151 else if (eval_valid && mpz_cmp(eval, cval) > 0)
11152 {
631d5788 11153 go_error_at(this->cap_->location(),
11154 "invalid slice index: capacity less than length");
acf2b673 11155 this->set_is_error();
11156 }
11157 mpz_clear(cval);
11158 }
11159
11160 if (eval_valid)
11161 mpz_clear(eval);
e440a328 11162 }
0bd5d859 11163 if (ival_valid)
11164 mpz_clear(ival);
0c77715b 11165 if (lval_valid)
11166 mpz_clear(lval);
e440a328 11167
11168 // A slice of an array requires an addressable array. A slice of a
11169 // slice is always possible.
411eb89e 11170 if (this->end_ != NULL && !array_type->is_slice_type())
88ec30c8 11171 {
11172 if (!this->array_->is_addressable())
8da39c3b 11173 this->report_error(_("slice of unaddressable value"));
88ec30c8 11174 else
b7327dbf 11175 // Set the array address taken but not escape. The escape
11176 // analysis will make it escape to heap when needed.
11177 this->array_->address_taken(false);
88ec30c8 11178 }
e440a328 11179}
11180
71a38860 11181// The subexpressions of an array index must be evaluated in order.
11182// If this is indexing into an array, rather than a slice, then only
11183// the index should be evaluated. Since this is called for values on
11184// the left hand side of an assigment, evaluating the array, meaning
11185// copying the array, will cause a different array to be modified.
11186
11187bool
11188Array_index_expression::do_must_eval_subexpressions_in_order(
11189 int* skip) const
11190{
11191 *skip = this->array_->type()->is_slice_type() ? 0 : 1;
11192 return true;
11193}
11194
2c809f8f 11195// Flatten array indexing by using temporary variables for slices and indexes.
35a54f17 11196
11197Expression*
11198Array_index_expression::do_flatten(Gogo*, Named_object*,
11199 Statement_inserter* inserter)
11200{
11201 Location loc = this->location();
5bf8be8b 11202 Expression* array = this->array_;
11203 Expression* start = this->start_;
11204 Expression* end = this->end_;
11205 Expression* cap = this->cap_;
11206 if (array->is_error_expression()
11207 || array->type()->is_error_type()
11208 || start->is_error_expression()
11209 || start->type()->is_error_type()
11210 || (end != NULL
11211 && (end->is_error_expression() || end->type()->is_error_type()))
11212 || (cap != NULL
11213 && (cap->is_error_expression() || cap->type()->is_error_type())))
11214 {
11215 go_assert(saw_errors());
11216 return Expression::make_error(loc);
11217 }
11218
2c809f8f 11219 Temporary_statement* temp;
5bf8be8b 11220 if (array->type()->is_slice_type() && !array->is_variable())
35a54f17 11221 {
5bf8be8b 11222 temp = Statement::make_temporary(NULL, array, loc);
35a54f17 11223 inserter->insert(temp);
11224 this->array_ = Expression::make_temporary_reference(temp, loc);
11225 }
5bf8be8b 11226 if (!start->is_variable())
2c809f8f 11227 {
5bf8be8b 11228 temp = Statement::make_temporary(NULL, start, loc);
2c809f8f 11229 inserter->insert(temp);
11230 this->start_ = Expression::make_temporary_reference(temp, loc);
11231 }
5bf8be8b 11232 if (end != NULL
11233 && !end->is_nil_expression()
11234 && !end->is_variable())
2c809f8f 11235 {
5bf8be8b 11236 temp = Statement::make_temporary(NULL, end, loc);
2c809f8f 11237 inserter->insert(temp);
11238 this->end_ = Expression::make_temporary_reference(temp, loc);
11239 }
03118c21 11240 if (cap != NULL && !cap->is_variable())
2c809f8f 11241 {
5bf8be8b 11242 temp = Statement::make_temporary(NULL, cap, loc);
2c809f8f 11243 inserter->insert(temp);
11244 this->cap_ = Expression::make_temporary_reference(temp, loc);
11245 }
11246
35a54f17 11247 return this;
11248}
11249
e440a328 11250// Return whether this expression is addressable.
11251
11252bool
11253Array_index_expression::do_is_addressable() const
11254{
11255 // A slice expression is not addressable.
11256 if (this->end_ != NULL)
11257 return false;
11258
11259 // An index into a slice is addressable.
411eb89e 11260 if (this->array_->type()->is_slice_type())
e440a328 11261 return true;
11262
11263 // An index into an array is addressable if the array is
11264 // addressable.
11265 return this->array_->is_addressable();
11266}
11267
bf1323be 11268void
11269Array_index_expression::do_address_taken(bool escapes)
11270{
11271 // In &x[0], if x is a slice, then x's address is not taken.
11272 if (!this->array_->type()->is_slice_type())
11273 this->array_->address_taken(escapes);
11274}
11275
ea664253 11276// Get the backend representation for an array index.
e440a328 11277
ea664253 11278Bexpression*
11279Array_index_expression::do_get_backend(Translate_context* context)
e440a328 11280{
e440a328 11281 Array_type* array_type = this->array_->type()->array_type();
d8cd8e2d 11282 if (array_type == NULL)
11283 {
c484d925 11284 go_assert(this->array_->type()->is_error());
ea664253 11285 return context->backend()->error_expression();
d8cd8e2d 11286 }
35a54f17 11287 go_assert(!array_type->is_slice_type() || this->array_->is_variable());
e440a328 11288
2c809f8f 11289 Location loc = this->location();
11290 Gogo* gogo = context->gogo();
11291
6dfedc16 11292 Type* int_type = Type::lookup_integer_type("int");
11293 Btype* int_btype = int_type->get_backend(gogo);
e440a328 11294
2c809f8f 11295 // We need to convert the length and capacity to the Go "int" type here
11296 // because the length of a fixed-length array could be of type "uintptr"
11297 // and gimple disallows binary operations between "uintptr" and other
11298 // integer types. FIXME.
11299 Bexpression* length = NULL;
a04bfdfc 11300 if (this->end_ == NULL || this->end_->is_nil_expression())
11301 {
35a54f17 11302 Expression* len = array_type->get_length(gogo, this->array_);
ea664253 11303 length = len->get_backend(context);
2c809f8f 11304 length = gogo->backend()->convert_expression(int_btype, length, loc);
a04bfdfc 11305 }
11306
2c809f8f 11307 Bexpression* capacity = NULL;
a04bfdfc 11308 if (this->end_ != NULL)
11309 {
35a54f17 11310 Expression* cap = array_type->get_capacity(gogo, this->array_);
ea664253 11311 capacity = cap->get_backend(context);
2c809f8f 11312 capacity = gogo->backend()->convert_expression(int_btype, capacity, loc);
a04bfdfc 11313 }
11314
2c809f8f 11315 Bexpression* cap_arg = capacity;
acf2b673 11316 if (this->cap_ != NULL)
11317 {
ea664253 11318 cap_arg = this->cap_->get_backend(context);
2c809f8f 11319 cap_arg = gogo->backend()->convert_expression(int_btype, cap_arg, loc);
acf2b673 11320 }
11321
2c809f8f 11322 if (length == NULL)
11323 length = cap_arg;
e440a328 11324
11325 int code = (array_type->length() != NULL
11326 ? (this->end_ == NULL
11327 ? RUNTIME_ERROR_ARRAY_INDEX_OUT_OF_BOUNDS
11328 : RUNTIME_ERROR_ARRAY_SLICE_OUT_OF_BOUNDS)
11329 : (this->end_ == NULL
11330 ? RUNTIME_ERROR_SLICE_INDEX_OUT_OF_BOUNDS
11331 : RUNTIME_ERROR_SLICE_SLICE_OUT_OF_BOUNDS));
ea664253 11332 Bexpression* crash = gogo->runtime_error(code, loc)->get_backend(context);
2c809f8f 11333
6dfedc16 11334 if (this->start_->type()->integer_type() == NULL
11335 && !Type::are_convertible(int_type, this->start_->type(), NULL))
11336 {
11337 go_assert(saw_errors());
11338 return context->backend()->error_expression();
11339 }
d9f3743a 11340
ea664253 11341 Bexpression* bad_index =
d9f3743a 11342 Expression::check_bounds(this->start_, loc)->get_backend(context);
2c809f8f 11343
ea664253 11344 Bexpression* start = this->start_->get_backend(context);
2c809f8f 11345 start = gogo->backend()->convert_expression(int_btype, start, loc);
11346 Bexpression* start_too_large =
11347 gogo->backend()->binary_expression((this->end_ == NULL
11348 ? OPERATOR_GE
11349 : OPERATOR_GT),
11350 start,
11351 (this->end_ == NULL
11352 ? length
11353 : capacity),
11354 loc);
11355 bad_index = gogo->backend()->binary_expression(OPERATOR_OROR, start_too_large,
11356 bad_index, loc);
e440a328 11357
93715b75 11358 Bfunction* bfn = context->function()->func_value()->get_decl();
e440a328 11359 if (this->end_ == NULL)
11360 {
11361 // Simple array indexing. This has to return an l-value, so
2c809f8f 11362 // wrap the index check into START.
11363 start =
93715b75 11364 gogo->backend()->conditional_expression(bfn, int_btype, bad_index,
2c809f8f 11365 crash, start, loc);
e440a328 11366
2c809f8f 11367 Bexpression* ret;
e440a328 11368 if (array_type->length() != NULL)
11369 {
ea664253 11370 Bexpression* array = this->array_->get_backend(context);
2c809f8f 11371 ret = gogo->backend()->array_index_expression(array, start, loc);
e440a328 11372 }
11373 else
11374 {
2c809f8f 11375 // Slice.
11376 Expression* valptr =
44dbe1d7 11377 array_type->get_value_pointer(gogo, this->array_,
11378 this->is_lvalue_);
ea664253 11379 Bexpression* ptr = valptr->get_backend(context);
2c809f8f 11380 ptr = gogo->backend()->pointer_offset_expression(ptr, start, loc);
9b27b43c 11381
11382 Type* ele_type = this->array_->type()->array_type()->element_type();
11383 Btype* ele_btype = ele_type->get_backend(gogo);
11384 ret = gogo->backend()->indirect_expression(ele_btype, ptr, true, loc);
e440a328 11385 }
ea664253 11386 return ret;
e440a328 11387 }
11388
11389 // Array slice.
11390
acf2b673 11391 if (this->cap_ != NULL)
11392 {
2c809f8f 11393 Bexpression* bounds_bcheck =
ea664253 11394 Expression::check_bounds(this->cap_, loc)->get_backend(context);
2c809f8f 11395 bad_index =
11396 gogo->backend()->binary_expression(OPERATOR_OROR, bounds_bcheck,
11397 bad_index, loc);
11398 cap_arg = gogo->backend()->convert_expression(int_btype, cap_arg, loc);
11399
11400 Bexpression* cap_too_small =
11401 gogo->backend()->binary_expression(OPERATOR_LT, cap_arg, start, loc);
11402 Bexpression* cap_too_large =
11403 gogo->backend()->binary_expression(OPERATOR_GT, cap_arg, capacity, loc);
11404 Bexpression* bad_cap =
11405 gogo->backend()->binary_expression(OPERATOR_OROR, cap_too_small,
11406 cap_too_large, loc);
11407 bad_index = gogo->backend()->binary_expression(OPERATOR_OROR, bad_cap,
11408 bad_index, loc);
11409 }
11410
11411 Bexpression* end;
e440a328 11412 if (this->end_->is_nil_expression())
2c809f8f 11413 end = length;
e440a328 11414 else
11415 {
2c809f8f 11416 Bexpression* bounds_bcheck =
ea664253 11417 Expression::check_bounds(this->end_, loc)->get_backend(context);
e440a328 11418
2c809f8f 11419 bad_index =
11420 gogo->backend()->binary_expression(OPERATOR_OROR, bounds_bcheck,
11421 bad_index, loc);
e440a328 11422
ea664253 11423 end = this->end_->get_backend(context);
2c809f8f 11424 end = gogo->backend()->convert_expression(int_btype, end, loc);
11425 Bexpression* end_too_small =
11426 gogo->backend()->binary_expression(OPERATOR_LT, end, start, loc);
11427 Bexpression* end_too_large =
11428 gogo->backend()->binary_expression(OPERATOR_GT, end, cap_arg, loc);
11429 Bexpression* bad_end =
11430 gogo->backend()->binary_expression(OPERATOR_OROR, end_too_small,
11431 end_too_large, loc);
11432 bad_index = gogo->backend()->binary_expression(OPERATOR_OROR, bad_end,
11433 bad_index, loc);
e440a328 11434 }
11435
2c809f8f 11436 Bexpression* result_length =
11437 gogo->backend()->binary_expression(OPERATOR_MINUS, end, start, loc);
e440a328 11438
2c809f8f 11439 Bexpression* result_capacity =
11440 gogo->backend()->binary_expression(OPERATOR_MINUS, cap_arg, start, loc);
e440a328 11441
03118c21 11442 // If the new capacity is zero, don't change val. Otherwise we can
11443 // get a pointer to the next object in memory, keeping it live
11444 // unnecessarily. When the capacity is zero, the actual pointer
11445 // value doesn't matter.
11446 Bexpression* zero =
11447 Expression::make_integer_ul(0, int_type, loc)->get_backend(context);
11448 Bexpression* cond =
11449 gogo->backend()->binary_expression(OPERATOR_EQEQ, result_capacity, zero,
11450 loc);
11451 Bexpression* offset = gogo->backend()->conditional_expression(bfn, int_btype,
11452 cond, zero,
11453 start, loc);
44dbe1d7 11454 Expression* valptr = array_type->get_value_pointer(gogo, this->array_,
11455 this->is_lvalue_);
03118c21 11456 Bexpression* val = valptr->get_backend(context);
11457 val = gogo->backend()->pointer_offset_expression(val, offset, loc);
11458
2c809f8f 11459 Btype* struct_btype = this->type()->get_backend(gogo);
11460 std::vector<Bexpression*> init;
11461 init.push_back(val);
11462 init.push_back(result_length);
11463 init.push_back(result_capacity);
e440a328 11464
2c809f8f 11465 Bexpression* ctor =
11466 gogo->backend()->constructor_expression(struct_btype, init, loc);
93715b75 11467 return gogo->backend()->conditional_expression(bfn, struct_btype, bad_index,
ea664253 11468 crash, ctor, loc);
e440a328 11469}
11470
d751bb78 11471// Dump ast representation for an array index expression.
11472
11473void
11474Array_index_expression::do_dump_expression(Ast_dump_context* ast_dump_context)
11475 const
11476{
11477 Index_expression::dump_index_expression(ast_dump_context, this->array_,
acf2b673 11478 this->start_, this->end_, this->cap_);
d751bb78 11479}
11480
acf2b673 11481// Make an array index expression. END and CAP may be NULL.
e440a328 11482
11483Expression*
11484Expression::make_array_index(Expression* array, Expression* start,
acf2b673 11485 Expression* end, Expression* cap,
11486 Location location)
e440a328 11487{
acf2b673 11488 return new Array_index_expression(array, start, end, cap, location);
e440a328 11489}
11490
50075d74 11491// Class String_index_expression.
e440a328 11492
11493// String index traversal.
11494
11495int
11496String_index_expression::do_traverse(Traverse* traverse)
11497{
11498 if (Expression::traverse(&this->string_, traverse) == TRAVERSE_EXIT)
11499 return TRAVERSE_EXIT;
11500 if (Expression::traverse(&this->start_, traverse) == TRAVERSE_EXIT)
11501 return TRAVERSE_EXIT;
11502 if (this->end_ != NULL)
11503 {
11504 if (Expression::traverse(&this->end_, traverse) == TRAVERSE_EXIT)
11505 return TRAVERSE_EXIT;
11506 }
11507 return TRAVERSE_CONTINUE;
11508}
11509
2c809f8f 11510Expression*
11511String_index_expression::do_flatten(Gogo*, Named_object*,
11512 Statement_inserter* inserter)
e440a328 11513{
2c809f8f 11514 Location loc = this->location();
5bf8be8b 11515 Expression* string = this->string_;
11516 Expression* start = this->start_;
11517 Expression* end = this->end_;
11518 if (string->is_error_expression()
11519 || string->type()->is_error_type()
11520 || start->is_error_expression()
11521 || start->type()->is_error_type()
11522 || (end != NULL
11523 && (end->is_error_expression() || end->type()->is_error_type())))
11524 {
11525 go_assert(saw_errors());
11526 return Expression::make_error(loc);
11527 }
11528
11529 Temporary_statement* temp;
2c809f8f 11530 if (!this->string_->is_variable())
11531 {
11532 temp = Statement::make_temporary(NULL, this->string_, loc);
11533 inserter->insert(temp);
11534 this->string_ = Expression::make_temporary_reference(temp, loc);
11535 }
11536 if (!this->start_->is_variable())
11537 {
11538 temp = Statement::make_temporary(NULL, this->start_, loc);
11539 inserter->insert(temp);
11540 this->start_ = Expression::make_temporary_reference(temp, loc);
11541 }
11542 if (this->end_ != NULL
11543 && !this->end_->is_nil_expression()
11544 && !this->end_->is_variable())
11545 {
11546 temp = Statement::make_temporary(NULL, this->end_, loc);
11547 inserter->insert(temp);
11548 this->end_ = Expression::make_temporary_reference(temp, loc);
11549 }
11550
11551 return this;
11552}
11553
11554// Return the type of a string index.
11555
11556Type*
11557String_index_expression::do_type()
11558{
11559 if (this->end_ == NULL)
11560 return Type::lookup_integer_type("uint8");
11561 else
11562 return this->string_->type();
11563}
11564
11565// Determine the type of a string index.
11566
11567void
11568String_index_expression::do_determine_type(const Type_context*)
11569{
11570 this->string_->determine_type_no_context();
f77aa642 11571
11572 Type_context index_context(Type::lookup_integer_type("int"), false);
11573 if (this->start_->is_constant())
11574 this->start_->determine_type(&index_context);
11575 else
11576 this->start_->determine_type_no_context();
e440a328 11577 if (this->end_ != NULL)
f77aa642 11578 {
11579 if (this->end_->is_constant())
11580 this->end_->determine_type(&index_context);
11581 else
11582 this->end_->determine_type_no_context();
11583 }
e440a328 11584}
11585
11586// Check types of a string index.
11587
11588void
11589String_index_expression::do_check_types(Gogo*)
11590{
acdc230d 11591 Numeric_constant nc;
11592 unsigned long v;
11593 if (this->start_->type()->integer_type() == NULL
11594 && !this->start_->type()->is_error()
11595 && (!this->start_->numeric_constant_value(&nc)
11596 || nc.to_unsigned_long(&v) == Numeric_constant::NC_UL_NOTINT))
e440a328 11597 this->report_error(_("index must be integer"));
11598 if (this->end_ != NULL
11599 && this->end_->type()->integer_type() == NULL
acdc230d 11600 && !this->end_->type()->is_error()
11601 && !this->end_->is_nil_expression()
11602 && !this->end_->is_error_expression()
11603 && (!this->end_->numeric_constant_value(&nc)
11604 || nc.to_unsigned_long(&v) == Numeric_constant::NC_UL_NOTINT))
e440a328 11605 this->report_error(_("slice end must be integer"));
11606
11607 std::string sval;
11608 bool sval_valid = this->string_->string_constant_value(&sval);
11609
0c77715b 11610 Numeric_constant inc;
e440a328 11611 mpz_t ival;
0bd5d859 11612 bool ival_valid = false;
0c77715b 11613 if (this->start_->numeric_constant_value(&inc) && inc.to_int(&ival))
e440a328 11614 {
0bd5d859 11615 ival_valid = true;
e440a328 11616 if (mpz_sgn(ival) < 0
b10f32fb 11617 || (sval_valid
11618 && (this->end_ == NULL
11619 ? mpz_cmp_ui(ival, sval.length()) >= 0
11620 : mpz_cmp_ui(ival, sval.length()) > 0)))
e440a328 11621 {
631d5788 11622 go_error_at(this->start_->location(), "string index out of bounds");
e440a328 11623 this->set_is_error();
11624 }
11625 }
11626 if (this->end_ != NULL && !this->end_->is_nil_expression())
11627 {
0c77715b 11628 Numeric_constant enc;
11629 mpz_t eval;
11630 if (this->end_->numeric_constant_value(&enc) && enc.to_int(&eval))
e440a328 11631 {
0c77715b 11632 if (mpz_sgn(eval) < 0
11633 || (sval_valid && mpz_cmp_ui(eval, sval.length()) > 0))
e440a328 11634 {
631d5788 11635 go_error_at(this->end_->location(), "string index out of bounds");
e440a328 11636 this->set_is_error();
11637 }
0bd5d859 11638 else if (ival_valid && mpz_cmp(ival, eval) > 0)
11639 this->report_error(_("inverted slice range"));
0c77715b 11640 mpz_clear(eval);
e440a328 11641 }
11642 }
0bd5d859 11643 if (ival_valid)
11644 mpz_clear(ival);
e440a328 11645}
11646
ea664253 11647// Get the backend representation for a string index.
e440a328 11648
ea664253 11649Bexpression*
11650String_index_expression::do_get_backend(Translate_context* context)
e440a328 11651{
b13c66cd 11652 Location loc = this->location();
2c809f8f 11653 Expression* string_arg = this->string_;
11654 if (this->string_->type()->points_to() != NULL)
f614ea8b 11655 string_arg = Expression::make_dereference(this->string_,
11656 NIL_CHECK_NOT_NEEDED, loc);
e440a328 11657
2c809f8f 11658 Expression* bad_index = Expression::check_bounds(this->start_, loc);
e440a328 11659
2c809f8f 11660 int code = (this->end_ == NULL
11661 ? RUNTIME_ERROR_STRING_INDEX_OUT_OF_BOUNDS
11662 : RUNTIME_ERROR_STRING_SLICE_OUT_OF_BOUNDS);
e440a328 11663
2c809f8f 11664 Gogo* gogo = context->gogo();
ea664253 11665 Bexpression* crash = gogo->runtime_error(code, loc)->get_backend(context);
1b1f2abf 11666
11667 Type* int_type = Type::lookup_integer_type("int");
e440a328 11668
2c809f8f 11669 // It is possible that an error occurred earlier because the start index
11670 // cannot be represented as an integer type. In this case, we shouldn't
11671 // try casting the starting index into an integer since
11672 // Type_conversion_expression will fail to get the backend representation.
11673 // FIXME.
11674 if (this->start_->type()->integer_type() == NULL
11675 && !Type::are_convertible(int_type, this->start_->type(), NULL))
11676 {
11677 go_assert(saw_errors());
ea664253 11678 return context->backend()->error_expression();
2c809f8f 11679 }
e440a328 11680
2c809f8f 11681 Expression* start = Expression::make_cast(int_type, this->start_, loc);
93715b75 11682 Bfunction* bfn = context->function()->func_value()->get_decl();
e440a328 11683
2c809f8f 11684 if (this->end_ == NULL)
11685 {
11686 Expression* length =
11687 Expression::make_string_info(this->string_, STRING_INFO_LENGTH, loc);
e440a328 11688
2c809f8f 11689 Expression* start_too_large =
11690 Expression::make_binary(OPERATOR_GE, start, length, loc);
11691 bad_index = Expression::make_binary(OPERATOR_OROR, start_too_large,
11692 bad_index, loc);
11693 Expression* bytes =
11694 Expression::make_string_info(this->string_, STRING_INFO_DATA, loc);
e440a328 11695
ea664253 11696 Bexpression* bstart = start->get_backend(context);
11697 Bexpression* ptr = bytes->get_backend(context);
2c809f8f 11698 ptr = gogo->backend()->pointer_offset_expression(ptr, bstart, loc);
9b27b43c 11699 Btype* ubtype = Type::lookup_integer_type("uint8")->get_backend(gogo);
11700 Bexpression* index =
11701 gogo->backend()->indirect_expression(ubtype, ptr, true, loc);
e440a328 11702
2c809f8f 11703 Btype* byte_btype = bytes->type()->points_to()->get_backend(gogo);
ea664253 11704 Bexpression* index_error = bad_index->get_backend(context);
93715b75 11705 return gogo->backend()->conditional_expression(bfn, byte_btype,
11706 index_error, crash,
11707 index, loc);
2c809f8f 11708 }
11709
11710 Expression* end = NULL;
11711 if (this->end_->is_nil_expression())
e67508fa 11712 end = Expression::make_integer_sl(-1, int_type, loc);
e440a328 11713 else
11714 {
2c809f8f 11715 Expression* bounds_check = Expression::check_bounds(this->end_, loc);
11716 bad_index =
11717 Expression::make_binary(OPERATOR_OROR, bounds_check, bad_index, loc);
11718 end = Expression::make_cast(int_type, this->end_, loc);
e440a328 11719 }
2c809f8f 11720
11721 Expression* strslice = Runtime::make_call(Runtime::STRING_SLICE, loc, 3,
11722 string_arg, start, end);
ea664253 11723 Bexpression* bstrslice = strslice->get_backend(context);
2c809f8f 11724
11725 Btype* str_btype = strslice->type()->get_backend(gogo);
ea664253 11726 Bexpression* index_error = bad_index->get_backend(context);
93715b75 11727 return gogo->backend()->conditional_expression(bfn, str_btype, index_error,
ea664253 11728 crash, bstrslice, loc);
e440a328 11729}
11730
d751bb78 11731// Dump ast representation for a string index expression.
11732
11733void
11734String_index_expression::do_dump_expression(Ast_dump_context* ast_dump_context)
11735 const
11736{
acf2b673 11737 Index_expression::dump_index_expression(ast_dump_context, this->string_,
11738 this->start_, this->end_, NULL);
d751bb78 11739}
11740
e440a328 11741// Make a string index expression. END may be NULL.
11742
11743Expression*
11744Expression::make_string_index(Expression* string, Expression* start,
b13c66cd 11745 Expression* end, Location location)
e440a328 11746{
11747 return new String_index_expression(string, start, end, location);
11748}
11749
11750// Class Map_index.
11751
11752// Get the type of the map.
11753
11754Map_type*
11755Map_index_expression::get_map_type() const
11756{
0d5530d9 11757 Map_type* mt = this->map_->type()->map_type();
c7524fae 11758 if (mt == NULL)
c484d925 11759 go_assert(saw_errors());
e440a328 11760 return mt;
11761}
11762
11763// Map index traversal.
11764
11765int
11766Map_index_expression::do_traverse(Traverse* traverse)
11767{
11768 if (Expression::traverse(&this->map_, traverse) == TRAVERSE_EXIT)
11769 return TRAVERSE_EXIT;
11770 return Expression::traverse(&this->index_, traverse);
11771}
11772
2c809f8f 11773// We need to pass in a pointer to the key, so flatten the index into a
11774// temporary variable if it isn't already. The value pointer will be
11775// dereferenced and checked for nil, so flatten into a temporary to avoid
11776// recomputation.
11777
11778Expression*
91c0fd76 11779Map_index_expression::do_flatten(Gogo* gogo, Named_object*,
2c809f8f 11780 Statement_inserter* inserter)
11781{
91c0fd76 11782 Location loc = this->location();
2c809f8f 11783 Map_type* mt = this->get_map_type();
5bf8be8b 11784 if (this->index()->is_error_expression()
11785 || this->index()->type()->is_error_type()
11786 || mt->is_error_type())
11787 {
11788 go_assert(saw_errors());
11789 return Expression::make_error(loc);
11790 }
11791
3a522dcc 11792 if (!Type::are_identical(mt->key_type(), this->index_->type(),
11793 Type::COMPARE_ERRORS | Type::COMPARE_TAGS,
11794 NULL))
91c0fd76 11795 {
11796 if (this->index_->type()->interface_type() != NULL
11797 && !this->index_->is_variable())
11798 {
11799 Temporary_statement* temp =
11800 Statement::make_temporary(NULL, this->index_, loc);
11801 inserter->insert(temp);
11802 this->index_ = Expression::make_temporary_reference(temp, loc);
11803 }
11804 this->index_ = Expression::convert_for_assignment(gogo, mt->key_type(),
11805 this->index_, loc);
11806 }
2c809f8f 11807
11808 if (!this->index_->is_variable())
11809 {
11810 Temporary_statement* temp = Statement::make_temporary(NULL, this->index_,
91c0fd76 11811 loc);
2c809f8f 11812 inserter->insert(temp);
91c0fd76 11813 this->index_ = Expression::make_temporary_reference(temp, loc);
2c809f8f 11814 }
11815
11816 if (this->value_pointer_ == NULL)
0d5530d9 11817 this->get_value_pointer(gogo);
5bf8be8b 11818 if (this->value_pointer_->is_error_expression()
11819 || this->value_pointer_->type()->is_error_type())
11820 return Expression::make_error(loc);
2c809f8f 11821 if (!this->value_pointer_->is_variable())
11822 {
11823 Temporary_statement* temp =
91c0fd76 11824 Statement::make_temporary(NULL, this->value_pointer_, loc);
2c809f8f 11825 inserter->insert(temp);
91c0fd76 11826 this->value_pointer_ = Expression::make_temporary_reference(temp, loc);
2c809f8f 11827 }
11828
11829 return this;
11830}
11831
e440a328 11832// Return the type of a map index.
11833
11834Type*
11835Map_index_expression::do_type()
11836{
c7524fae 11837 Map_type* mt = this->get_map_type();
11838 if (mt == NULL)
11839 return Type::make_error_type();
0d5530d9 11840 return mt->val_type();
e440a328 11841}
11842
11843// Fix the type of a map index.
11844
11845void
11846Map_index_expression::do_determine_type(const Type_context*)
11847{
11848 this->map_->determine_type_no_context();
c7524fae 11849 Map_type* mt = this->get_map_type();
11850 Type* key_type = mt == NULL ? NULL : mt->key_type();
11851 Type_context subcontext(key_type, false);
e440a328 11852 this->index_->determine_type(&subcontext);
11853}
11854
11855// Check types of a map index.
11856
11857void
11858Map_index_expression::do_check_types(Gogo*)
11859{
11860 std::string reason;
c7524fae 11861 Map_type* mt = this->get_map_type();
11862 if (mt == NULL)
11863 return;
11864 if (!Type::are_assignable(mt->key_type(), this->index_->type(), &reason))
e440a328 11865 {
11866 if (reason.empty())
11867 this->report_error(_("incompatible type for map index"));
11868 else
11869 {
631d5788 11870 go_error_at(this->location(), "incompatible type for map index (%s)",
11871 reason.c_str());
e440a328 11872 this->set_is_error();
11873 }
11874 }
11875}
11876
ea664253 11877// Get the backend representation for a map index.
e440a328 11878
ea664253 11879Bexpression*
11880Map_index_expression::do_get_backend(Translate_context* context)
e440a328 11881{
11882 Map_type* type = this->get_map_type();
c7524fae 11883 if (type == NULL)
2c809f8f 11884 {
11885 go_assert(saw_errors());
ea664253 11886 return context->backend()->error_expression();
2c809f8f 11887 }
e440a328 11888
2c809f8f 11889 go_assert(this->value_pointer_ != NULL
11890 && this->value_pointer_->is_variable());
e440a328 11891
f614ea8b 11892 Expression* val = Expression::make_dereference(this->value_pointer_,
11893 NIL_CHECK_NOT_NEEDED,
11894 this->location());
0d5530d9 11895 return val->get_backend(context);
e440a328 11896}
11897
0d5530d9 11898// Get an expression for the map index. This returns an expression
11899// that evaluates to a pointer to a value. If the key is not in the
11900// map, the pointer will point to a zero value.
e440a328 11901
2c809f8f 11902Expression*
0d5530d9 11903Map_index_expression::get_value_pointer(Gogo* gogo)
e440a328 11904{
2c809f8f 11905 if (this->value_pointer_ == NULL)
746d2e73 11906 {
2c809f8f 11907 Map_type* type = this->get_map_type();
11908 if (type == NULL)
746d2e73 11909 {
2c809f8f 11910 go_assert(saw_errors());
11911 return Expression::make_error(this->location());
746d2e73 11912 }
e440a328 11913
2c809f8f 11914 Location loc = this->location();
11915 Expression* map_ref = this->map_;
e440a328 11916
0d5530d9 11917 Expression* index_ptr = Expression::make_unary(OPERATOR_AND,
11918 this->index_,
2c809f8f 11919 loc);
0d5530d9 11920
11921 Expression* zero = type->fat_zero_value(gogo);
11922
11923 Expression* map_index;
11924
11925 if (zero == NULL)
11926 map_index =
11927 Runtime::make_call(Runtime::MAPACCESS1, loc, 3,
11928 Expression::make_type_descriptor(type, loc),
11929 map_ref, index_ptr);
11930 else
11931 map_index =
11932 Runtime::make_call(Runtime::MAPACCESS1_FAT, loc, 4,
11933 Expression::make_type_descriptor(type, loc),
11934 map_ref, index_ptr, zero);
2c809f8f 11935
11936 Type* val_type = type->val_type();
11937 this->value_pointer_ =
11938 Expression::make_unsafe_cast(Type::make_pointer_type(val_type),
11939 map_index, this->location());
11940 }
0d5530d9 11941
2c809f8f 11942 return this->value_pointer_;
e440a328 11943}
11944
d751bb78 11945// Dump ast representation for a map index expression
11946
11947void
11948Map_index_expression::do_dump_expression(Ast_dump_context* ast_dump_context)
11949 const
11950{
acf2b673 11951 Index_expression::dump_index_expression(ast_dump_context, this->map_,
11952 this->index_, NULL, NULL);
d751bb78 11953}
11954
e440a328 11955// Make a map index expression.
11956
11957Map_index_expression*
11958Expression::make_map_index(Expression* map, Expression* index,
b13c66cd 11959 Location location)
e440a328 11960{
11961 return new Map_index_expression(map, index, location);
11962}
11963
11964// Class Field_reference_expression.
11965
149eabc5 11966// Lower a field reference expression. There is nothing to lower, but
11967// this is where we generate the tracking information for fields with
11968// the magic go:"track" tag.
11969
11970Expression*
11971Field_reference_expression::do_lower(Gogo* gogo, Named_object* function,
11972 Statement_inserter* inserter, int)
11973{
11974 Struct_type* struct_type = this->expr_->type()->struct_type();
11975 if (struct_type == NULL)
11976 {
11977 // Error will be reported elsewhere.
11978 return this;
11979 }
11980 const Struct_field* field = struct_type->field(this->field_index_);
11981 if (field == NULL)
11982 return this;
11983 if (!field->has_tag())
11984 return this;
11985 if (field->tag().find("go:\"track\"") == std::string::npos)
11986 return this;
11987
604e278d 11988 // References from functions generated by the compiler don't count.
c6292d1d 11989 if (function != NULL && function->func_value()->is_type_specific_function())
604e278d 11990 return this;
11991
149eabc5 11992 // We have found a reference to a tracked field. Build a call to
11993 // the runtime function __go_fieldtrack with a string that describes
11994 // the field. FIXME: We should only call this once per referenced
11995 // field per function, not once for each reference to the field.
11996
11997 if (this->called_fieldtrack_)
11998 return this;
11999 this->called_fieldtrack_ = true;
12000
12001 Location loc = this->location();
12002
12003 std::string s = "fieldtrack \"";
e65055a5 12004 Named_type* nt = this->expr_->type()->unalias()->named_type();
149eabc5 12005 if (nt == NULL || nt->named_object()->package() == NULL)
12006 s.append(gogo->pkgpath());
12007 else
12008 s.append(nt->named_object()->package()->pkgpath());
12009 s.push_back('.');
12010 if (nt != NULL)
5c29ad36 12011 s.append(Gogo::unpack_hidden_name(nt->name()));
149eabc5 12012 s.push_back('.');
12013 s.append(field->field_name());
12014 s.push_back('"');
12015
12016 // We can't use a string here, because internally a string holds a
12017 // pointer to the actual bytes; when the linker garbage collects the
12018 // string, it won't garbage collect the bytes. So we use a
12019 // [...]byte.
12020
e67508fa 12021 Expression* length_expr = Expression::make_integer_ul(s.length(), NULL, loc);
149eabc5 12022
12023 Type* byte_type = gogo->lookup_global("byte")->type_value();
6bf4793c 12024 Array_type* array_type = Type::make_array_type(byte_type, length_expr);
12025 array_type->set_is_array_incomparable();
149eabc5 12026
12027 Expression_list* bytes = new Expression_list();
12028 for (std::string::const_iterator p = s.begin(); p != s.end(); p++)
12029 {
e67508fa 12030 unsigned char c = static_cast<unsigned char>(*p);
12031 bytes->push_back(Expression::make_integer_ul(c, NULL, loc));
149eabc5 12032 }
12033
12034 Expression* e = Expression::make_composite_literal(array_type, 0, false,
62750cd5 12035 bytes, false, loc);
149eabc5 12036
12037 Variable* var = new Variable(array_type, e, true, false, false, loc);
12038
12039 static int count;
12040 char buf[50];
12041 snprintf(buf, sizeof buf, "fieldtrack.%d", count);
12042 ++count;
12043
12044 Named_object* no = gogo->add_variable(buf, var);
12045 e = Expression::make_var_reference(no, loc);
12046 e = Expression::make_unary(OPERATOR_AND, e, loc);
12047
12048 Expression* call = Runtime::make_call(Runtime::FIELDTRACK, loc, 1, e);
604e278d 12049 gogo->lower_expression(function, inserter, &call);
149eabc5 12050 inserter->insert(Statement::make_statement(call, false));
12051
12052 // Put this function, and the global variable we just created, into
12053 // unique sections. This will permit the linker to garbage collect
12054 // them if they are not referenced. The effect is that the only
12055 // strings, indicating field references, that will wind up in the
12056 // executable will be those for functions that are actually needed.
66a6be58 12057 if (function != NULL)
12058 function->func_value()->set_in_unique_section();
149eabc5 12059 var->set_in_unique_section();
12060
12061 return this;
12062}
12063
e440a328 12064// Return the type of a field reference.
12065
12066Type*
12067Field_reference_expression::do_type()
12068{
b0e628fb 12069 Type* type = this->expr_->type();
5c13bd80 12070 if (type->is_error())
b0e628fb 12071 return type;
12072 Struct_type* struct_type = type->struct_type();
c484d925 12073 go_assert(struct_type != NULL);
e440a328 12074 return struct_type->field(this->field_index_)->type();
12075}
12076
12077// Check the types for a field reference.
12078
12079void
12080Field_reference_expression::do_check_types(Gogo*)
12081{
b0e628fb 12082 Type* type = this->expr_->type();
5c13bd80 12083 if (type->is_error())
b0e628fb 12084 return;
12085 Struct_type* struct_type = type->struct_type();
c484d925 12086 go_assert(struct_type != NULL);
12087 go_assert(struct_type->field(this->field_index_) != NULL);
e440a328 12088}
12089
ea664253 12090// Get the backend representation for a field reference.
e440a328 12091
ea664253 12092Bexpression*
12093Field_reference_expression::do_get_backend(Translate_context* context)
e440a328 12094{
ea664253 12095 Bexpression* bstruct = this->expr_->get_backend(context);
12096 return context->gogo()->backend()->struct_field_expression(bstruct,
12097 this->field_index_,
12098 this->location());
e440a328 12099}
12100
d751bb78 12101// Dump ast representation for a field reference expression.
12102
12103void
12104Field_reference_expression::do_dump_expression(
12105 Ast_dump_context* ast_dump_context) const
12106{
12107 this->expr_->dump_expression(ast_dump_context);
12108 ast_dump_context->ostream() << "." << this->field_index_;
12109}
12110
e440a328 12111// Make a reference to a qualified identifier in an expression.
12112
12113Field_reference_expression*
12114Expression::make_field_reference(Expression* expr, unsigned int field_index,
b13c66cd 12115 Location location)
e440a328 12116{
12117 return new Field_reference_expression(expr, field_index, location);
12118}
12119
12120// Class Interface_field_reference_expression.
12121
2387f644 12122// Return an expression for the pointer to the function to call.
e440a328 12123
2387f644 12124Expression*
12125Interface_field_reference_expression::get_function()
e440a328 12126{
2387f644 12127 Expression* ref = this->expr_;
12128 Location loc = this->location();
12129 if (ref->type()->points_to() != NULL)
f614ea8b 12130 ref = Expression::make_dereference(ref, NIL_CHECK_DEFAULT, loc);
e440a328 12131
2387f644 12132 Expression* mtable =
12133 Expression::make_interface_info(ref, INTERFACE_INFO_METHODS, loc);
12134 Struct_type* mtable_type = mtable->type()->points_to()->struct_type();
e440a328 12135
12136 std::string name = Gogo::unpack_hidden_name(this->name_);
2387f644 12137 unsigned int index;
12138 const Struct_field* field = mtable_type->find_local_field(name, &index);
12139 go_assert(field != NULL);
f614ea8b 12140
12141 mtable = Expression::make_dereference(mtable, NIL_CHECK_NOT_NEEDED, loc);
2387f644 12142 return Expression::make_field_reference(mtable, index, loc);
e440a328 12143}
12144
2387f644 12145// Return an expression for the first argument to pass to the interface
e440a328 12146// function.
12147
2387f644 12148Expression*
12149Interface_field_reference_expression::get_underlying_object()
e440a328 12150{
2387f644 12151 Expression* expr = this->expr_;
12152 if (expr->type()->points_to() != NULL)
f614ea8b 12153 expr = Expression::make_dereference(expr, NIL_CHECK_DEFAULT,
12154 this->location());
2387f644 12155 return Expression::make_interface_info(expr, INTERFACE_INFO_OBJECT,
12156 this->location());
e440a328 12157}
12158
12159// Traversal.
12160
12161int
12162Interface_field_reference_expression::do_traverse(Traverse* traverse)
12163{
12164 return Expression::traverse(&this->expr_, traverse);
12165}
12166
0afbb937 12167// Lower the expression. If this expression is not called, we need to
12168// evaluate the expression twice when converting to the backend
12169// interface. So introduce a temporary variable if necessary.
12170
12171Expression*
9782d556 12172Interface_field_reference_expression::do_flatten(Gogo*, Named_object*,
12173 Statement_inserter* inserter)
0afbb937 12174{
5bf8be8b 12175 if (this->expr_->is_error_expression()
12176 || this->expr_->type()->is_error_type())
12177 {
12178 go_assert(saw_errors());
12179 return Expression::make_error(this->location());
12180 }
12181
2387f644 12182 if (!this->expr_->is_variable())
0afbb937 12183 {
12184 Temporary_statement* temp =
9189e53b 12185 Statement::make_temporary(NULL, this->expr_, this->location());
0afbb937 12186 inserter->insert(temp);
9189e53b 12187 this->expr_ = Expression::make_temporary_reference(temp, this->location());
0afbb937 12188 }
12189 return this;
12190}
12191
e440a328 12192// Return the type of an interface field reference.
12193
12194Type*
12195Interface_field_reference_expression::do_type()
12196{
12197 Type* expr_type = this->expr_->type();
12198
12199 Type* points_to = expr_type->points_to();
12200 if (points_to != NULL)
12201 expr_type = points_to;
12202
12203 Interface_type* interface_type = expr_type->interface_type();
12204 if (interface_type == NULL)
12205 return Type::make_error_type();
12206
12207 const Typed_identifier* method = interface_type->find_method(this->name_);
12208 if (method == NULL)
12209 return Type::make_error_type();
12210
12211 return method->type();
12212}
12213
12214// Determine types.
12215
12216void
12217Interface_field_reference_expression::do_determine_type(const Type_context*)
12218{
12219 this->expr_->determine_type_no_context();
12220}
12221
12222// Check the types for an interface field reference.
12223
12224void
12225Interface_field_reference_expression::do_check_types(Gogo*)
12226{
12227 Type* type = this->expr_->type();
12228
12229 Type* points_to = type->points_to();
12230 if (points_to != NULL)
12231 type = points_to;
12232
12233 Interface_type* interface_type = type->interface_type();
12234 if (interface_type == NULL)
5c491127 12235 {
12236 if (!type->is_error_type())
12237 this->report_error(_("expected interface or pointer to interface"));
12238 }
e440a328 12239 else
12240 {
12241 const Typed_identifier* method =
12242 interface_type->find_method(this->name_);
12243 if (method == NULL)
12244 {
631d5788 12245 go_error_at(this->location(), "method %qs not in interface",
12246 Gogo::message_name(this->name_).c_str());
e440a328 12247 this->set_is_error();
12248 }
12249 }
12250}
12251
0afbb937 12252// If an interface field reference is not simply called, then it is
12253// represented as a closure. The closure will hold a single variable,
12254// the value of the interface on which the method should be called.
12255// The function will be a simple thunk that pulls the value from the
12256// closure and calls the method with the remaining arguments.
12257
12258// Because method values are not common, we don't build all thunks for
12259// all possible interface methods, but instead only build them as we
12260// need them. In particular, we even build them on demand for
12261// interface methods defined in other packages.
12262
12263Interface_field_reference_expression::Interface_method_thunks
12264 Interface_field_reference_expression::interface_method_thunks;
12265
12266// Find or create the thunk to call method NAME on TYPE.
12267
12268Named_object*
12269Interface_field_reference_expression::create_thunk(Gogo* gogo,
12270 Interface_type* type,
12271 const std::string& name)
12272{
12273 std::pair<Interface_type*, Method_thunks*> val(type, NULL);
12274 std::pair<Interface_method_thunks::iterator, bool> ins =
12275 Interface_field_reference_expression::interface_method_thunks.insert(val);
12276 if (ins.second)
12277 {
12278 // This is the first time we have seen this interface.
12279 ins.first->second = new Method_thunks();
12280 }
12281
12282 for (Method_thunks::const_iterator p = ins.first->second->begin();
12283 p != ins.first->second->end();
12284 p++)
12285 if (p->first == name)
12286 return p->second;
12287
12288 Location loc = type->location();
12289
12290 const Typed_identifier* method_id = type->find_method(name);
12291 if (method_id == NULL)
13f2fdb8 12292 return Named_object::make_erroneous_name(gogo->thunk_name());
0afbb937 12293
12294 Function_type* orig_fntype = method_id->type()->function_type();
12295 if (orig_fntype == NULL)
13f2fdb8 12296 return Named_object::make_erroneous_name(gogo->thunk_name());
0afbb937 12297
12298 Struct_field_list* sfl = new Struct_field_list();
f8bdf81a 12299 // The type here is wrong--it should be the C function type. But it
12300 // doesn't really matter.
0afbb937 12301 Type* vt = Type::make_pointer_type(Type::make_void_type());
13f2fdb8 12302 sfl->push_back(Struct_field(Typed_identifier("fn", vt, loc)));
12303 sfl->push_back(Struct_field(Typed_identifier("val", type, loc)));
6bf4793c 12304 Struct_type* st = Type::make_struct_type(sfl, loc);
12305 st->set_is_struct_incomparable();
12306 Type* closure_type = Type::make_pointer_type(st);
0afbb937 12307
f8bdf81a 12308 Function_type* new_fntype = orig_fntype->copy_with_names();
0afbb937 12309
13f2fdb8 12310 std::string thunk_name = gogo->thunk_name();
da244e59 12311 Named_object* new_no = gogo->start_function(thunk_name, new_fntype,
0afbb937 12312 false, loc);
12313
f8bdf81a 12314 Variable* cvar = new Variable(closure_type, NULL, false, false, false, loc);
12315 cvar->set_is_used();
1ecc6157 12316 cvar->set_is_closure();
da244e59 12317 Named_object* cp = Named_object::make_variable("$closure" + thunk_name,
12318 NULL, cvar);
f8bdf81a 12319 new_no->func_value()->set_closure_var(cp);
0afbb937 12320
f8bdf81a 12321 gogo->start_block(loc);
0afbb937 12322
12323 // Field 0 of the closure is the function code pointer, field 1 is
12324 // the value on which to invoke the method.
12325 Expression* arg = Expression::make_var_reference(cp, loc);
f614ea8b 12326 arg = Expression::make_dereference(arg, NIL_CHECK_NOT_NEEDED, loc);
0afbb937 12327 arg = Expression::make_field_reference(arg, 1, loc);
12328
12329 Expression *ifre = Expression::make_interface_field_reference(arg, name,
12330 loc);
12331
12332 const Typed_identifier_list* orig_params = orig_fntype->parameters();
12333 Expression_list* args;
12334 if (orig_params == NULL || orig_params->empty())
12335 args = NULL;
12336 else
12337 {
12338 const Typed_identifier_list* new_params = new_fntype->parameters();
12339 args = new Expression_list();
12340 for (Typed_identifier_list::const_iterator p = new_params->begin();
f8bdf81a 12341 p != new_params->end();
0afbb937 12342 ++p)
12343 {
12344 Named_object* p_no = gogo->lookup(p->name(), NULL);
12345 go_assert(p_no != NULL
12346 && p_no->is_variable()
12347 && p_no->var_value()->is_parameter());
12348 args->push_back(Expression::make_var_reference(p_no, loc));
12349 }
12350 }
12351
12352 Call_expression* call = Expression::make_call(ifre, args,
12353 orig_fntype->is_varargs(),
12354 loc);
12355 call->set_varargs_are_lowered();
12356
12357 Statement* s = Statement::make_return_from_call(call, loc);
12358 gogo->add_statement(s);
12359 Block* b = gogo->finish_block(loc);
12360 gogo->add_block(b, loc);
12361 gogo->lower_block(new_no, b);
a32698ee 12362 gogo->flatten_block(new_no, b);
0afbb937 12363 gogo->finish_function(loc);
12364
12365 ins.first->second->push_back(std::make_pair(name, new_no));
12366 return new_no;
12367}
12368
ea664253 12369// Get the backend representation for a method value.
e440a328 12370
ea664253 12371Bexpression*
12372Interface_field_reference_expression::do_get_backend(Translate_context* context)
e440a328 12373{
0afbb937 12374 Interface_type* type = this->expr_->type()->interface_type();
12375 if (type == NULL)
12376 {
12377 go_assert(saw_errors());
ea664253 12378 return context->backend()->error_expression();
0afbb937 12379 }
12380
12381 Named_object* thunk =
12382 Interface_field_reference_expression::create_thunk(context->gogo(),
12383 type, this->name_);
12384 if (thunk->is_erroneous())
12385 {
12386 go_assert(saw_errors());
ea664253 12387 return context->backend()->error_expression();
0afbb937 12388 }
12389
12390 // FIXME: We should lower this earlier, but we can't it lower it in
12391 // the lowering pass because at that point we don't know whether we
12392 // need to create the thunk or not. If the expression is called, we
12393 // don't need the thunk.
12394
12395 Location loc = this->location();
12396
12397 Struct_field_list* fields = new Struct_field_list();
13f2fdb8 12398 fields->push_back(Struct_field(Typed_identifier("fn",
0afbb937 12399 thunk->func_value()->type(),
12400 loc)));
13f2fdb8 12401 fields->push_back(Struct_field(Typed_identifier("val",
0afbb937 12402 this->expr_->type(),
12403 loc)));
12404 Struct_type* st = Type::make_struct_type(fields, loc);
6bf4793c 12405 st->set_is_struct_incomparable();
0afbb937 12406
12407 Expression_list* vals = new Expression_list();
12408 vals->push_back(Expression::make_func_code_reference(thunk, loc));
12409 vals->push_back(this->expr_);
12410
12411 Expression* expr = Expression::make_struct_composite_literal(st, vals, loc);
ea664253 12412 Bexpression* bclosure =
12413 Expression::make_heap_expression(expr, loc)->get_backend(context);
0afbb937 12414
4df0c2d4 12415 Gogo* gogo = context->gogo();
12416 Btype* btype = this->type()->get_backend(gogo);
12417 bclosure = gogo->backend()->convert_expression(btype, bclosure, loc);
12418
2387f644 12419 Expression* nil_check =
12420 Expression::make_binary(OPERATOR_EQEQ, this->expr_,
12421 Expression::make_nil(loc), loc);
ea664253 12422 Bexpression* bnil_check = nil_check->get_backend(context);
0afbb937 12423
ea664253 12424 Bexpression* bcrash = gogo->runtime_error(RUNTIME_ERROR_NIL_DEREFERENCE,
12425 loc)->get_backend(context);
2387f644 12426
93715b75 12427 Bfunction* bfn = context->function()->func_value()->get_decl();
2387f644 12428 Bexpression* bcond =
93715b75 12429 gogo->backend()->conditional_expression(bfn, NULL,
12430 bnil_check, bcrash, NULL, loc);
0ab48656 12431 Bfunction* bfunction = context->function()->func_value()->get_decl();
12432 Bstatement* cond_statement =
12433 gogo->backend()->expression_statement(bfunction, bcond);
ea664253 12434 return gogo->backend()->compound_expression(cond_statement, bclosure, loc);
e440a328 12435}
12436
d751bb78 12437// Dump ast representation for an interface field reference.
12438
12439void
12440Interface_field_reference_expression::do_dump_expression(
12441 Ast_dump_context* ast_dump_context) const
12442{
12443 this->expr_->dump_expression(ast_dump_context);
12444 ast_dump_context->ostream() << "." << this->name_;
12445}
12446
e440a328 12447// Make a reference to a field in an interface.
12448
12449Expression*
12450Expression::make_interface_field_reference(Expression* expr,
12451 const std::string& field,
b13c66cd 12452 Location location)
e440a328 12453{
12454 return new Interface_field_reference_expression(expr, field, location);
12455}
12456
12457// A general selector. This is a Parser_expression for LEFT.NAME. It
12458// is lowered after we know the type of the left hand side.
12459
12460class Selector_expression : public Parser_expression
12461{
12462 public:
12463 Selector_expression(Expression* left, const std::string& name,
b13c66cd 12464 Location location)
e440a328 12465 : Parser_expression(EXPRESSION_SELECTOR, location),
12466 left_(left), name_(name)
12467 { }
12468
12469 protected:
12470 int
12471 do_traverse(Traverse* traverse)
12472 { return Expression::traverse(&this->left_, traverse); }
12473
12474 Expression*
ceeb4318 12475 do_lower(Gogo*, Named_object*, Statement_inserter*, int);
e440a328 12476
12477 Expression*
12478 do_copy()
12479 {
12480 return new Selector_expression(this->left_->copy(), this->name_,
12481 this->location());
12482 }
12483
d751bb78 12484 void
12485 do_dump_expression(Ast_dump_context* ast_dump_context) const;
12486
e440a328 12487 private:
12488 Expression*
12489 lower_method_expression(Gogo*);
12490
12491 // The expression on the left hand side.
12492 Expression* left_;
12493 // The name on the right hand side.
12494 std::string name_;
12495};
12496
12497// Lower a selector expression once we know the real type of the left
12498// hand side.
12499
12500Expression*
ceeb4318 12501Selector_expression::do_lower(Gogo* gogo, Named_object*, Statement_inserter*,
12502 int)
e440a328 12503{
12504 Expression* left = this->left_;
12505 if (left->is_type_expression())
12506 return this->lower_method_expression(gogo);
12507 return Type::bind_field_or_method(gogo, left->type(), left, this->name_,
12508 this->location());
12509}
12510
12511// Lower a method expression T.M or (*T).M. We turn this into a
12512// function literal.
12513
12514Expression*
12515Selector_expression::lower_method_expression(Gogo* gogo)
12516{
b13c66cd 12517 Location location = this->location();
868b439e 12518 Type* left_type = this->left_->type();
12519 Type* type = left_type;
e440a328 12520 const std::string& name(this->name_);
12521
12522 bool is_pointer;
12523 if (type->points_to() == NULL)
12524 is_pointer = false;
12525 else
12526 {
12527 is_pointer = true;
12528 type = type->points_to();
12529 }
12530 Named_type* nt = type->named_type();
12531 if (nt == NULL)
12532 {
631d5788 12533 go_error_at(location,
12534 ("method expression requires named type or "
12535 "pointer to named type"));
e440a328 12536 return Expression::make_error(location);
12537 }
12538
12539 bool is_ambiguous;
12540 Method* method = nt->method_function(name, &is_ambiguous);
ab1468c3 12541 const Typed_identifier* imethod = NULL;
dcc8506b 12542 if (method == NULL && !is_pointer)
ab1468c3 12543 {
12544 Interface_type* it = nt->interface_type();
12545 if (it != NULL)
12546 imethod = it->find_method(name);
12547 }
12548
868b439e 12549 if ((method == NULL && imethod == NULL)
12550 || (left_type->named_type() != NULL && left_type->points_to() != NULL))
e440a328 12551 {
12552 if (!is_ambiguous)
631d5788 12553 go_error_at(location, "type %<%s%s%> has no method %<%s%>",
12554 is_pointer ? "*" : "",
12555 nt->message_name().c_str(),
12556 Gogo::message_name(name).c_str());
e440a328 12557 else
631d5788 12558 go_error_at(location, "method %<%s%s%> is ambiguous in type %<%s%>",
12559 Gogo::message_name(name).c_str(),
12560 is_pointer ? "*" : "",
12561 nt->message_name().c_str());
e440a328 12562 return Expression::make_error(location);
12563 }
12564
ab1468c3 12565 if (method != NULL && !is_pointer && !method->is_value_method())
e440a328 12566 {
631d5788 12567 go_error_at(location, "method requires pointer (use %<(*%s).%s%>)",
12568 nt->message_name().c_str(),
12569 Gogo::message_name(name).c_str());
e440a328 12570 return Expression::make_error(location);
12571 }
12572
12573 // Build a new function type in which the receiver becomes the first
12574 // argument.
ab1468c3 12575 Function_type* method_type;
12576 if (method != NULL)
12577 {
12578 method_type = method->type();
c484d925 12579 go_assert(method_type->is_method());
ab1468c3 12580 }
12581 else
12582 {
12583 method_type = imethod->type()->function_type();
c484d925 12584 go_assert(method_type != NULL && !method_type->is_method());
ab1468c3 12585 }
e440a328 12586
12587 const char* const receiver_name = "$this";
12588 Typed_identifier_list* parameters = new Typed_identifier_list();
12589 parameters->push_back(Typed_identifier(receiver_name, this->left_->type(),
12590 location));
12591
12592 const Typed_identifier_list* method_parameters = method_type->parameters();
12593 if (method_parameters != NULL)
12594 {
f470da59 12595 int i = 0;
e440a328 12596 for (Typed_identifier_list::const_iterator p = method_parameters->begin();
12597 p != method_parameters->end();
f470da59 12598 ++p, ++i)
12599 {
68883531 12600 if (!p->name().empty())
f470da59 12601 parameters->push_back(*p);
12602 else
12603 {
12604 char buf[20];
12605 snprintf(buf, sizeof buf, "$param%d", i);
12606 parameters->push_back(Typed_identifier(buf, p->type(),
12607 p->location()));
12608 }
12609 }
e440a328 12610 }
12611
12612 const Typed_identifier_list* method_results = method_type->results();
12613 Typed_identifier_list* results;
12614 if (method_results == NULL)
12615 results = NULL;
12616 else
12617 {
12618 results = new Typed_identifier_list();
12619 for (Typed_identifier_list::const_iterator p = method_results->begin();
12620 p != method_results->end();
12621 ++p)
12622 results->push_back(*p);
12623 }
12624
12625 Function_type* fntype = Type::make_function_type(NULL, parameters, results,
12626 location);
12627 if (method_type->is_varargs())
12628 fntype->set_is_varargs();
12629
12630 // We generate methods which always takes a pointer to the receiver
12631 // as their first argument. If this is for a pointer type, we can
12632 // simply reuse the existing function. We use an internal hack to
12633 // get the right type.
8381eda7 12634 // FIXME: This optimization is disabled because it doesn't yet work
12635 // with function descriptors when the method expression is not
12636 // directly called.
12637 if (method != NULL && is_pointer && false)
e440a328 12638 {
12639 Named_object* mno = (method->needs_stub_method()
12640 ? method->stub_object()
12641 : method->named_object());
12642 Expression* f = Expression::make_func_reference(mno, NULL, location);
12643 f = Expression::make_cast(fntype, f, location);
12644 Type_conversion_expression* tce =
12645 static_cast<Type_conversion_expression*>(f);
12646 tce->set_may_convert_function_types();
12647 return f;
12648 }
12649
13f2fdb8 12650 Named_object* no = gogo->start_function(gogo->thunk_name(), fntype, false,
e440a328 12651 location);
12652
12653 Named_object* vno = gogo->lookup(receiver_name, NULL);
c484d925 12654 go_assert(vno != NULL);
e440a328 12655 Expression* ve = Expression::make_var_reference(vno, location);
ab1468c3 12656 Expression* bm;
12657 if (method != NULL)
12658 bm = Type::bind_field_or_method(gogo, nt, ve, name, location);
12659 else
12660 bm = Expression::make_interface_field_reference(ve, name, location);
f690b0bb 12661
12662 // Even though we found the method above, if it has an error type we
12663 // may see an error here.
12664 if (bm->is_error_expression())
463fe805 12665 {
12666 gogo->finish_function(location);
12667 return bm;
12668 }
e440a328 12669
12670 Expression_list* args;
f470da59 12671 if (parameters->size() <= 1)
e440a328 12672 args = NULL;
12673 else
12674 {
12675 args = new Expression_list();
f470da59 12676 Typed_identifier_list::const_iterator p = parameters->begin();
12677 ++p;
12678 for (; p != parameters->end(); ++p)
e440a328 12679 {
12680 vno = gogo->lookup(p->name(), NULL);
c484d925 12681 go_assert(vno != NULL);
e440a328 12682 args->push_back(Expression::make_var_reference(vno, location));
12683 }
12684 }
12685
ceeb4318 12686 gogo->start_block(location);
12687
e440a328 12688 Call_expression* call = Expression::make_call(bm, args,
12689 method_type->is_varargs(),
12690 location);
12691
0afbb937 12692 Statement* s = Statement::make_return_from_call(call, location);
e440a328 12693 gogo->add_statement(s);
12694
ceeb4318 12695 Block* b = gogo->finish_block(location);
12696
12697 gogo->add_block(b, location);
12698
12699 // Lower the call in case there are multiple results.
12700 gogo->lower_block(no, b);
a32698ee 12701 gogo->flatten_block(no, b);
ceeb4318 12702
e440a328 12703 gogo->finish_function(location);
12704
12705 return Expression::make_func_reference(no, NULL, location);
12706}
12707
d751bb78 12708// Dump the ast for a selector expression.
12709
12710void
12711Selector_expression::do_dump_expression(Ast_dump_context* ast_dump_context)
12712 const
12713{
12714 ast_dump_context->dump_expression(this->left_);
12715 ast_dump_context->ostream() << ".";
12716 ast_dump_context->ostream() << this->name_;
12717}
12718
e440a328 12719// Make a selector expression.
12720
12721Expression*
12722Expression::make_selector(Expression* left, const std::string& name,
b13c66cd 12723 Location location)
e440a328 12724{
12725 return new Selector_expression(left, name, location);
12726}
12727
da244e59 12728// Class Allocation_expression.
e440a328 12729
da244e59 12730int
12731Allocation_expression::do_traverse(Traverse* traverse)
e440a328 12732{
da244e59 12733 return Type::traverse(this->type_, traverse);
12734}
e440a328 12735
da244e59 12736Type*
12737Allocation_expression::do_type()
12738{
12739 return Type::make_pointer_type(this->type_);
12740}
e440a328 12741
22deed0d 12742void
12743Allocation_expression::do_check_types(Gogo*)
12744{
12745 if (!this->type_->in_heap())
12746 go_error_at(this->location(), "can't heap allocate go:notinheap type");
12747}
12748
da244e59 12749// Make a copy of an allocation expression.
e440a328 12750
da244e59 12751Expression*
12752Allocation_expression::do_copy()
12753{
12754 Allocation_expression* alloc =
de590a61 12755 new Allocation_expression(this->type_->copy_expressions(),
12756 this->location());
da244e59 12757 if (this->allocate_on_stack_)
12758 alloc->set_allocate_on_stack();
12759 return alloc;
12760}
e440a328 12761
ea664253 12762// Return the backend representation for an allocation expression.
e440a328 12763
ea664253 12764Bexpression*
12765Allocation_expression::do_get_backend(Translate_context* context)
e440a328 12766{
2c809f8f 12767 Gogo* gogo = context->gogo();
12768 Location loc = this->location();
06e83d10 12769 Btype* btype = this->type_->get_backend(gogo);
da244e59 12770
5973ede0 12771 if (this->allocate_on_stack_)
da244e59 12772 {
2a305b85 12773 int64_t size;
12774 bool ok = this->type_->backend_type_size(gogo, &size);
12775 if (!ok)
12776 {
12777 go_assert(saw_errors());
12778 return gogo->backend()->error_expression();
12779 }
06e83d10 12780 Bstatement* decl;
12781 Named_object* fn = context->function();
12782 go_assert(fn != NULL);
12783 Bfunction* fndecl = fn->func_value()->get_or_make_decl(gogo, fn);
12784 Bexpression* zero = gogo->backend()->zero_expression(btype);
12785 Bvariable* temp =
12786 gogo->backend()->temporary_variable(fndecl, context->bblock(), btype,
12787 zero, true, loc, &decl);
12788 Bexpression* ret = gogo->backend()->var_expression(temp, loc);
12789 ret = gogo->backend()->address_expression(ret, loc);
12790 ret = gogo->backend()->compound_expression(decl, ret, loc);
12791 return ret;
da244e59 12792 }
12793
2a305b85 12794 Bexpression* space =
ea664253 12795 gogo->allocate_memory(this->type_, loc)->get_backend(context);
d5d1c295 12796 Btype* pbtype = gogo->backend()->pointer_type(btype);
ea664253 12797 return gogo->backend()->convert_expression(pbtype, space, loc);
e440a328 12798}
12799
d751bb78 12800// Dump ast representation for an allocation expression.
12801
12802void
12803Allocation_expression::do_dump_expression(Ast_dump_context* ast_dump_context)
12804 const
12805{
12806 ast_dump_context->ostream() << "new(";
12807 ast_dump_context->dump_type(this->type_);
12808 ast_dump_context->ostream() << ")";
12809}
12810
e440a328 12811// Make an allocation expression.
12812
12813Expression*
b13c66cd 12814Expression::make_allocation(Type* type, Location location)
e440a328 12815{
12816 return new Allocation_expression(type, location);
12817}
12818
e32de7ba 12819// Class Ordered_value_list.
e440a328 12820
12821int
e32de7ba 12822Ordered_value_list::traverse_vals(Traverse* traverse)
e440a328 12823{
0c4f5a19 12824 if (this->vals_ != NULL)
12825 {
12826 if (this->traverse_order_ == NULL)
12827 {
12828 if (this->vals_->traverse(traverse) == TRAVERSE_EXIT)
12829 return TRAVERSE_EXIT;
12830 }
12831 else
12832 {
e32de7ba 12833 for (std::vector<unsigned long>::const_iterator p =
12834 this->traverse_order_->begin();
0c4f5a19 12835 p != this->traverse_order_->end();
12836 ++p)
12837 {
12838 if (Expression::traverse(&this->vals_->at(*p), traverse)
12839 == TRAVERSE_EXIT)
12840 return TRAVERSE_EXIT;
12841 }
12842 }
12843 }
e32de7ba 12844 return TRAVERSE_CONTINUE;
12845}
12846
12847// Class Struct_construction_expression.
12848
12849// Traversal.
12850
12851int
12852Struct_construction_expression::do_traverse(Traverse* traverse)
12853{
12854 if (this->traverse_vals(traverse) == TRAVERSE_EXIT)
12855 return TRAVERSE_EXIT;
e440a328 12856 if (Type::traverse(this->type_, traverse) == TRAVERSE_EXIT)
12857 return TRAVERSE_EXIT;
12858 return TRAVERSE_CONTINUE;
12859}
12860
12861// Return whether this is a constant initializer.
12862
12863bool
12864Struct_construction_expression::is_constant_struct() const
12865{
e32de7ba 12866 if (this->vals() == NULL)
e440a328 12867 return true;
e32de7ba 12868 for (Expression_list::const_iterator pv = this->vals()->begin();
12869 pv != this->vals()->end();
e440a328 12870 ++pv)
12871 {
12872 if (*pv != NULL
12873 && !(*pv)->is_constant()
12874 && (!(*pv)->is_composite_literal()
12875 || (*pv)->is_nonconstant_composite_literal()))
12876 return false;
12877 }
12878
12879 const Struct_field_list* fields = this->type_->struct_type()->fields();
12880 for (Struct_field_list::const_iterator pf = fields->begin();
12881 pf != fields->end();
12882 ++pf)
12883 {
12884 // There are no constant constructors for interfaces.
12885 if (pf->type()->interface_type() != NULL)
12886 return false;
12887 }
12888
12889 return true;
12890}
12891
3ae06f68 12892// Return whether this struct can be used as a constant initializer.
f9ca30f9 12893
12894bool
3ae06f68 12895Struct_construction_expression::do_is_static_initializer() const
f9ca30f9 12896{
e32de7ba 12897 if (this->vals() == NULL)
f9ca30f9 12898 return true;
e32de7ba 12899 for (Expression_list::const_iterator pv = this->vals()->begin();
12900 pv != this->vals()->end();
f9ca30f9 12901 ++pv)
12902 {
3ae06f68 12903 if (*pv != NULL && !(*pv)->is_static_initializer())
f9ca30f9 12904 return false;
12905 }
de048538 12906
12907 const Struct_field_list* fields = this->type_->struct_type()->fields();
12908 for (Struct_field_list::const_iterator pf = fields->begin();
12909 pf != fields->end();
12910 ++pf)
12911 {
12912 // There are no constant constructors for interfaces.
12913 if (pf->type()->interface_type() != NULL)
12914 return false;
12915 }
12916
f9ca30f9 12917 return true;
12918}
12919
e440a328 12920// Final type determination.
12921
12922void
12923Struct_construction_expression::do_determine_type(const Type_context*)
12924{
e32de7ba 12925 if (this->vals() == NULL)
e440a328 12926 return;
12927 const Struct_field_list* fields = this->type_->struct_type()->fields();
e32de7ba 12928 Expression_list::const_iterator pv = this->vals()->begin();
e440a328 12929 for (Struct_field_list::const_iterator pf = fields->begin();
12930 pf != fields->end();
12931 ++pf, ++pv)
12932 {
e32de7ba 12933 if (pv == this->vals()->end())
e440a328 12934 return;
12935 if (*pv != NULL)
12936 {
12937 Type_context subcontext(pf->type(), false);
12938 (*pv)->determine_type(&subcontext);
12939 }
12940 }
a6cb4c0e 12941 // Extra values are an error we will report elsewhere; we still want
12942 // to determine the type to avoid knockon errors.
e32de7ba 12943 for (; pv != this->vals()->end(); ++pv)
a6cb4c0e 12944 (*pv)->determine_type_no_context();
e440a328 12945}
12946
12947// Check types.
12948
12949void
12950Struct_construction_expression::do_check_types(Gogo*)
12951{
e32de7ba 12952 if (this->vals() == NULL)
e440a328 12953 return;
12954
12955 Struct_type* st = this->type_->struct_type();
e32de7ba 12956 if (this->vals()->size() > st->field_count())
e440a328 12957 {
12958 this->report_error(_("too many expressions for struct"));
12959 return;
12960 }
12961
12962 const Struct_field_list* fields = st->fields();
e32de7ba 12963 Expression_list::const_iterator pv = this->vals()->begin();
e440a328 12964 int i = 0;
12965 for (Struct_field_list::const_iterator pf = fields->begin();
12966 pf != fields->end();
12967 ++pf, ++pv, ++i)
12968 {
e32de7ba 12969 if (pv == this->vals()->end())
e440a328 12970 {
12971 this->report_error(_("too few expressions for struct"));
12972 break;
12973 }
12974
12975 if (*pv == NULL)
12976 continue;
12977
12978 std::string reason;
12979 if (!Type::are_assignable(pf->type(), (*pv)->type(), &reason))
12980 {
12981 if (reason.empty())
631d5788 12982 go_error_at((*pv)->location(),
12983 "incompatible type for field %d in struct construction",
12984 i + 1);
e440a328 12985 else
631d5788 12986 go_error_at((*pv)->location(),
12987 ("incompatible type for field %d in "
12988 "struct construction (%s)"),
12989 i + 1, reason.c_str());
e440a328 12990 this->set_is_error();
12991 }
12992 }
e32de7ba 12993 go_assert(pv == this->vals()->end());
e440a328 12994}
12995
de590a61 12996// Copy.
12997
12998Expression*
12999Struct_construction_expression::do_copy()
13000{
13001 Struct_construction_expression* ret =
13002 new Struct_construction_expression(this->type_->copy_expressions(),
13003 (this->vals() == NULL
13004 ? NULL
13005 : this->vals()->copy()),
13006 this->location());
13007 if (this->traverse_order() != NULL)
13008 ret->set_traverse_order(this->traverse_order());
13009 return ret;
13010}
13011
8ba8cc87 13012// Flatten a struct construction expression. Store the values into
13013// temporaries in case they need interface conversion.
13014
13015Expression*
13016Struct_construction_expression::do_flatten(Gogo*, Named_object*,
13017 Statement_inserter* inserter)
13018{
e32de7ba 13019 if (this->vals() == NULL)
8ba8cc87 13020 return this;
13021
13022 // If this is a constant struct, we don't need temporaries.
de048538 13023 if (this->is_constant_struct() || this->is_static_initializer())
8ba8cc87 13024 return this;
13025
13026 Location loc = this->location();
e32de7ba 13027 for (Expression_list::iterator pv = this->vals()->begin();
13028 pv != this->vals()->end();
8ba8cc87 13029 ++pv)
13030 {
13031 if (*pv != NULL)
13032 {
5bf8be8b 13033 if ((*pv)->is_error_expression() || (*pv)->type()->is_error_type())
13034 {
13035 go_assert(saw_errors());
13036 return Expression::make_error(loc);
13037 }
8ba8cc87 13038 if (!(*pv)->is_variable())
13039 {
13040 Temporary_statement* temp =
13041 Statement::make_temporary(NULL, *pv, loc);
13042 inserter->insert(temp);
13043 *pv = Expression::make_temporary_reference(temp, loc);
13044 }
13045 }
13046 }
13047 return this;
13048}
13049
ea664253 13050// Return the backend representation for constructing a struct.
e440a328 13051
ea664253 13052Bexpression*
13053Struct_construction_expression::do_get_backend(Translate_context* context)
e440a328 13054{
13055 Gogo* gogo = context->gogo();
13056
2c809f8f 13057 Btype* btype = this->type_->get_backend(gogo);
e32de7ba 13058 if (this->vals() == NULL)
ea664253 13059 return gogo->backend()->zero_expression(btype);
e440a328 13060
e440a328 13061 const Struct_field_list* fields = this->type_->struct_type()->fields();
e32de7ba 13062 Expression_list::const_iterator pv = this->vals()->begin();
2c809f8f 13063 std::vector<Bexpression*> init;
13064 for (Struct_field_list::const_iterator pf = fields->begin();
13065 pf != fields->end();
13066 ++pf)
e440a328 13067 {
63697958 13068 Btype* fbtype = pf->type()->get_backend(gogo);
e32de7ba 13069 if (pv == this->vals()->end())
2c809f8f 13070 init.push_back(gogo->backend()->zero_expression(fbtype));
e440a328 13071 else if (*pv == NULL)
13072 {
2c809f8f 13073 init.push_back(gogo->backend()->zero_expression(fbtype));
e440a328 13074 ++pv;
13075 }
13076 else
13077 {
2c809f8f 13078 Expression* val =
13079 Expression::convert_for_assignment(gogo, pf->type(),
13080 *pv, this->location());
ea664253 13081 init.push_back(val->get_backend(context));
e440a328 13082 ++pv;
13083 }
e440a328 13084 }
0fdf8340 13085 if (this->type_->struct_type()->has_padding())
13086 {
13087 // Feed an extra value if there is a padding field.
13088 Btype *fbtype = Type::lookup_integer_type("uint8")->get_backend(gogo);
13089 init.push_back(gogo->backend()->zero_expression(fbtype));
13090 }
ea664253 13091 return gogo->backend()->constructor_expression(btype, init, this->location());
e440a328 13092}
13093
13094// Export a struct construction.
13095
13096void
548be246 13097Struct_construction_expression::do_export(Export_function_body* efb) const
e440a328 13098{
204d4af4 13099 efb->write_c_string("$convert(");
548be246 13100 efb->write_type(this->type_);
e32de7ba 13101 for (Expression_list::const_iterator pv = this->vals()->begin();
13102 pv != this->vals()->end();
e440a328 13103 ++pv)
13104 {
548be246 13105 efb->write_c_string(", ");
e440a328 13106 if (*pv != NULL)
548be246 13107 (*pv)->export_expression(efb);
e440a328 13108 }
548be246 13109 efb->write_c_string(")");
e440a328 13110}
13111
d751bb78 13112// Dump ast representation of a struct construction expression.
13113
13114void
13115Struct_construction_expression::do_dump_expression(
13116 Ast_dump_context* ast_dump_context) const
13117{
d751bb78 13118 ast_dump_context->dump_type(this->type_);
13119 ast_dump_context->ostream() << "{";
e32de7ba 13120 ast_dump_context->dump_expression_list(this->vals());
d751bb78 13121 ast_dump_context->ostream() << "}";
13122}
13123
e440a328 13124// Make a struct composite literal. This used by the thunk code.
13125
13126Expression*
13127Expression::make_struct_composite_literal(Type* type, Expression_list* vals,
b13c66cd 13128 Location location)
e440a328 13129{
c484d925 13130 go_assert(type->struct_type() != NULL);
e440a328 13131 return new Struct_construction_expression(type, vals, location);
13132}
13133
da244e59 13134// Class Array_construction_expression.
e440a328 13135
13136// Traversal.
13137
13138int
13139Array_construction_expression::do_traverse(Traverse* traverse)
13140{
e32de7ba 13141 if (this->traverse_vals(traverse) == TRAVERSE_EXIT)
e440a328 13142 return TRAVERSE_EXIT;
13143 if (Type::traverse(this->type_, traverse) == TRAVERSE_EXIT)
13144 return TRAVERSE_EXIT;
13145 return TRAVERSE_CONTINUE;
13146}
13147
13148// Return whether this is a constant initializer.
13149
13150bool
13151Array_construction_expression::is_constant_array() const
13152{
e32de7ba 13153 if (this->vals() == NULL)
e440a328 13154 return true;
13155
13156 // There are no constant constructors for interfaces.
13157 if (this->type_->array_type()->element_type()->interface_type() != NULL)
13158 return false;
13159
e32de7ba 13160 for (Expression_list::const_iterator pv = this->vals()->begin();
13161 pv != this->vals()->end();
e440a328 13162 ++pv)
13163 {
13164 if (*pv != NULL
13165 && !(*pv)->is_constant()
13166 && (!(*pv)->is_composite_literal()
13167 || (*pv)->is_nonconstant_composite_literal()))
13168 return false;
13169 }
13170 return true;
13171}
13172
3ae06f68 13173// Return whether this can be used a constant initializer.
f9ca30f9 13174
13175bool
3ae06f68 13176Array_construction_expression::do_is_static_initializer() const
f9ca30f9 13177{
e32de7ba 13178 if (this->vals() == NULL)
f9ca30f9 13179 return true;
de048538 13180
13181 // There are no constant constructors for interfaces.
13182 if (this->type_->array_type()->element_type()->interface_type() != NULL)
13183 return false;
13184
e32de7ba 13185 for (Expression_list::const_iterator pv = this->vals()->begin();
13186 pv != this->vals()->end();
f9ca30f9 13187 ++pv)
13188 {
3ae06f68 13189 if (*pv != NULL && !(*pv)->is_static_initializer())
f9ca30f9 13190 return false;
13191 }
13192 return true;
13193}
13194
e440a328 13195// Final type determination.
13196
13197void
13198Array_construction_expression::do_determine_type(const Type_context*)
13199{
e32de7ba 13200 if (this->vals() == NULL)
e440a328 13201 return;
13202 Type_context subcontext(this->type_->array_type()->element_type(), false);
e32de7ba 13203 for (Expression_list::const_iterator pv = this->vals()->begin();
13204 pv != this->vals()->end();
e440a328 13205 ++pv)
13206 {
13207 if (*pv != NULL)
13208 (*pv)->determine_type(&subcontext);
13209 }
13210}
13211
13212// Check types.
13213
13214void
13215Array_construction_expression::do_check_types(Gogo*)
13216{
e32de7ba 13217 if (this->vals() == NULL)
e440a328 13218 return;
13219
13220 Array_type* at = this->type_->array_type();
13221 int i = 0;
13222 Type* element_type = at->element_type();
e32de7ba 13223 for (Expression_list::const_iterator pv = this->vals()->begin();
13224 pv != this->vals()->end();
e440a328 13225 ++pv, ++i)
13226 {
13227 if (*pv != NULL
13228 && !Type::are_assignable(element_type, (*pv)->type(), NULL))
13229 {
631d5788 13230 go_error_at((*pv)->location(),
13231 "incompatible type for element %d in composite literal",
13232 i + 1);
e440a328 13233 this->set_is_error();
13234 }
13235 }
e440a328 13236}
13237
8ba8cc87 13238// Flatten an array construction expression. Store the values into
13239// temporaries in case they need interface conversion.
13240
13241Expression*
13242Array_construction_expression::do_flatten(Gogo*, Named_object*,
13243 Statement_inserter* inserter)
13244{
e32de7ba 13245 if (this->vals() == NULL)
8ba8cc87 13246 return this;
13247
13248 // If this is a constant array, we don't need temporaries.
de048538 13249 if (this->is_constant_array() || this->is_static_initializer())
8ba8cc87 13250 return this;
13251
13252 Location loc = this->location();
e32de7ba 13253 for (Expression_list::iterator pv = this->vals()->begin();
13254 pv != this->vals()->end();
8ba8cc87 13255 ++pv)
13256 {
13257 if (*pv != NULL)
13258 {
5bf8be8b 13259 if ((*pv)->is_error_expression() || (*pv)->type()->is_error_type())
13260 {
13261 go_assert(saw_errors());
13262 return Expression::make_error(loc);
13263 }
8ba8cc87 13264 if (!(*pv)->is_variable())
13265 {
13266 Temporary_statement* temp =
13267 Statement::make_temporary(NULL, *pv, loc);
13268 inserter->insert(temp);
13269 *pv = Expression::make_temporary_reference(temp, loc);
13270 }
13271 }
13272 }
13273 return this;
13274}
13275
2c809f8f 13276// Get a constructor expression for the array values.
e440a328 13277
2c809f8f 13278Bexpression*
13279Array_construction_expression::get_constructor(Translate_context* context,
13280 Btype* array_btype)
e440a328 13281{
e440a328 13282 Type* element_type = this->type_->array_type()->element_type();
2c809f8f 13283
13284 std::vector<unsigned long> indexes;
13285 std::vector<Bexpression*> vals;
13286 Gogo* gogo = context->gogo();
e32de7ba 13287 if (this->vals() != NULL)
e440a328 13288 {
13289 size_t i = 0;
ffe743ca 13290 std::vector<unsigned long>::const_iterator pi;
13291 if (this->indexes_ != NULL)
13292 pi = this->indexes_->begin();
e32de7ba 13293 for (Expression_list::const_iterator pv = this->vals()->begin();
13294 pv != this->vals()->end();
e440a328 13295 ++pv, ++i)
13296 {
ffe743ca 13297 if (this->indexes_ != NULL)
13298 go_assert(pi != this->indexes_->end());
ffe743ca 13299
13300 if (this->indexes_ == NULL)
2c809f8f 13301 indexes.push_back(i);
ffe743ca 13302 else
2c809f8f 13303 indexes.push_back(*pi);
e440a328 13304 if (*pv == NULL)
63697958 13305 {
63697958 13306 Btype* ebtype = element_type->get_backend(gogo);
13307 Bexpression *zv = gogo->backend()->zero_expression(ebtype);
2c809f8f 13308 vals.push_back(zv);
63697958 13309 }
e440a328 13310 else
13311 {
2c809f8f 13312 Expression* val_expr =
13313 Expression::convert_for_assignment(gogo, element_type, *pv,
13314 this->location());
ea664253 13315 vals.push_back(val_expr->get_backend(context));
e440a328 13316 }
ffe743ca 13317 if (this->indexes_ != NULL)
13318 ++pi;
e440a328 13319 }
ffe743ca 13320 if (this->indexes_ != NULL)
13321 go_assert(pi == this->indexes_->end());
e440a328 13322 }
2c809f8f 13323 return gogo->backend()->array_constructor_expression(array_btype, indexes,
13324 vals, this->location());
e440a328 13325}
13326
13327// Export an array construction.
13328
13329void
548be246 13330Array_construction_expression::do_export(Export_function_body* efb) const
e440a328 13331{
204d4af4 13332 efb->write_c_string("$convert(");
548be246 13333 efb->write_type(this->type_);
e32de7ba 13334 if (this->vals() != NULL)
e440a328 13335 {
ffe743ca 13336 std::vector<unsigned long>::const_iterator pi;
13337 if (this->indexes_ != NULL)
13338 pi = this->indexes_->begin();
e32de7ba 13339 for (Expression_list::const_iterator pv = this->vals()->begin();
13340 pv != this->vals()->end();
e440a328 13341 ++pv)
13342 {
548be246 13343 efb->write_c_string(", ");
ffe743ca 13344
13345 if (this->indexes_ != NULL)
13346 {
13347 char buf[100];
13348 snprintf(buf, sizeof buf, "%lu", *pi);
548be246 13349 efb->write_c_string(buf);
13350 efb->write_c_string(":");
ffe743ca 13351 }
13352
e440a328 13353 if (*pv != NULL)
548be246 13354 (*pv)->export_expression(efb);
ffe743ca 13355
13356 if (this->indexes_ != NULL)
13357 ++pi;
e440a328 13358 }
13359 }
548be246 13360 efb->write_c_string(")");
e440a328 13361}
13362
0e9a2e72 13363// Dump ast representation of an array construction expression.
d751bb78 13364
13365void
13366Array_construction_expression::do_dump_expression(
13367 Ast_dump_context* ast_dump_context) const
13368{
ffe743ca 13369 Expression* length = this->type_->array_type()->length();
8b1c301d 13370
13371 ast_dump_context->ostream() << "[" ;
13372 if (length != NULL)
13373 {
13374 ast_dump_context->dump_expression(length);
13375 }
13376 ast_dump_context->ostream() << "]" ;
d751bb78 13377 ast_dump_context->dump_type(this->type_);
0e9a2e72 13378 this->dump_slice_storage_expression(ast_dump_context);
d751bb78 13379 ast_dump_context->ostream() << "{" ;
ffe743ca 13380 if (this->indexes_ == NULL)
e32de7ba 13381 ast_dump_context->dump_expression_list(this->vals());
ffe743ca 13382 else
13383 {
e32de7ba 13384 Expression_list::const_iterator pv = this->vals()->begin();
ffe743ca 13385 for (std::vector<unsigned long>::const_iterator pi =
13386 this->indexes_->begin();
13387 pi != this->indexes_->end();
13388 ++pi, ++pv)
13389 {
13390 if (pi != this->indexes_->begin())
13391 ast_dump_context->ostream() << ", ";
13392 ast_dump_context->ostream() << *pi << ':';
13393 ast_dump_context->dump_expression(*pv);
13394 }
13395 }
d751bb78 13396 ast_dump_context->ostream() << "}" ;
13397
13398}
13399
da244e59 13400// Class Fixed_array_construction_expression.
e440a328 13401
da244e59 13402Fixed_array_construction_expression::Fixed_array_construction_expression(
13403 Type* type, const std::vector<unsigned long>* indexes,
13404 Expression_list* vals, Location location)
13405 : Array_construction_expression(EXPRESSION_FIXED_ARRAY_CONSTRUCTION,
13406 type, indexes, vals, location)
13407{ go_assert(type->array_type() != NULL && !type->is_slice_type()); }
e440a328 13408
de590a61 13409
13410// Copy.
13411
13412Expression*
13413Fixed_array_construction_expression::do_copy()
13414{
13415 Type* t = this->type()->copy_expressions();
13416 return new Fixed_array_construction_expression(t, this->indexes(),
13417 (this->vals() == NULL
13418 ? NULL
13419 : this->vals()->copy()),
13420 this->location());
13421}
13422
ea664253 13423// Return the backend representation for constructing a fixed array.
e440a328 13424
ea664253 13425Bexpression*
13426Fixed_array_construction_expression::do_get_backend(Translate_context* context)
e440a328 13427{
9f0e0513 13428 Type* type = this->type();
13429 Btype* btype = type->get_backend(context->gogo());
ea664253 13430 return this->get_constructor(context, btype);
e440a328 13431}
13432
76f85fd6 13433Expression*
13434Expression::make_array_composite_literal(Type* type, Expression_list* vals,
13435 Location location)
13436{
13437 go_assert(type->array_type() != NULL && !type->is_slice_type());
13438 return new Fixed_array_construction_expression(type, NULL, vals, location);
13439}
13440
da244e59 13441// Class Slice_construction_expression.
e440a328 13442
da244e59 13443Slice_construction_expression::Slice_construction_expression(
13444 Type* type, const std::vector<unsigned long>* indexes,
13445 Expression_list* vals, Location location)
13446 : Array_construction_expression(EXPRESSION_SLICE_CONSTRUCTION,
13447 type, indexes, vals, location),
0e9a2e72 13448 valtype_(NULL), array_val_(NULL), slice_storage_(NULL),
13449 storage_escapes_(true)
e440a328 13450{
da244e59 13451 go_assert(type->is_slice_type());
23d77f91 13452
da244e59 13453 unsigned long lenval;
13454 Expression* length;
13455 if (vals == NULL || vals->empty())
13456 lenval = 0;
13457 else
13458 {
13459 if (this->indexes() == NULL)
13460 lenval = vals->size();
13461 else
13462 lenval = indexes->back() + 1;
13463 }
13464 Type* int_type = Type::lookup_integer_type("int");
13465 length = Expression::make_integer_ul(lenval, int_type, location);
13466 Type* element_type = type->array_type()->element_type();
6bf4793c 13467 Array_type* array_type = Type::make_array_type(element_type, length);
13468 array_type->set_is_array_incomparable();
13469 this->valtype_ = array_type;
da244e59 13470}
e440a328 13471
23d77f91 13472// Traversal.
13473
13474int
13475Slice_construction_expression::do_traverse(Traverse* traverse)
13476{
13477 if (this->Array_construction_expression::do_traverse(traverse)
13478 == TRAVERSE_EXIT)
13479 return TRAVERSE_EXIT;
13480 if (Type::traverse(this->valtype_, traverse) == TRAVERSE_EXIT)
13481 return TRAVERSE_EXIT;
0e9a2e72 13482 if (this->array_val_ != NULL
13483 && Expression::traverse(&this->array_val_, traverse) == TRAVERSE_EXIT)
13484 return TRAVERSE_EXIT;
13485 if (this->slice_storage_ != NULL
13486 && Expression::traverse(&this->slice_storage_, traverse) == TRAVERSE_EXIT)
13487 return TRAVERSE_EXIT;
23d77f91 13488 return TRAVERSE_CONTINUE;
13489}
13490
0e9a2e72 13491// Helper routine to create fixed array value underlying the slice literal.
13492// May be called during flattening, or later during do_get_backend().
e440a328 13493
0e9a2e72 13494Expression*
13495Slice_construction_expression::create_array_val()
e440a328 13496{
f9c68f17 13497 Array_type* array_type = this->type()->array_type();
13498 if (array_type == NULL)
13499 {
c484d925 13500 go_assert(this->type()->is_error());
0e9a2e72 13501 return NULL;
f9c68f17 13502 }
13503
f23d7786 13504 Location loc = this->location();
23d77f91 13505 go_assert(this->valtype_ != NULL);
3d60812e 13506
f23d7786 13507 Expression_list* vals = this->vals();
0e9a2e72 13508 return new Fixed_array_construction_expression(
13509 this->valtype_, this->indexes(), vals, loc);
13510}
13511
13512// If we're previous established that the slice storage does not
13513// escape, then create a separate array temp val here for it. We
13514// need to do this as part of flattening so as to be able to insert
13515// the new temp statement.
13516
13517Expression*
13518Slice_construction_expression::do_flatten(Gogo* gogo, Named_object* no,
13519 Statement_inserter* inserter)
13520{
13521 if (this->type()->array_type() == NULL)
13522 return NULL;
13523
13524 // Base class flattening first
13525 this->Array_construction_expression::do_flatten(gogo, no, inserter);
13526
a1bbc2c3 13527 // Create a stack-allocated storage temp if storage won't escape
03118c21 13528 if (!this->storage_escapes_
13529 && this->slice_storage_ == NULL
13530 && this->element_count() > 0)
0e9a2e72 13531 {
13532 Location loc = this->location();
03118c21 13533 this->array_val_ = this->create_array_val();
0e9a2e72 13534 go_assert(this->array_val_);
13535 Temporary_statement* temp =
13536 Statement::make_temporary(this->valtype_, this->array_val_, loc);
13537 inserter->insert(temp);
13538 this->slice_storage_ = Expression::make_temporary_reference(temp, loc);
13539 }
13540 return this;
13541}
13542
13543// When dumping a slice construction expression that has an explicit
13544// storeage temp, emit the temp here (if we don't do this the storage
13545// temp appears unused in the AST dump).
13546
13547void
13548Slice_construction_expression::
13549dump_slice_storage_expression(Ast_dump_context* ast_dump_context) const
13550{
13551 if (this->slice_storage_ == NULL)
13552 return;
13553 ast_dump_context->ostream() << "storage=" ;
13554 ast_dump_context->dump_expression(this->slice_storage_);
13555}
13556
de590a61 13557// Copy.
13558
13559Expression*
13560Slice_construction_expression::do_copy()
13561{
13562 return new Slice_construction_expression(this->type()->copy_expressions(),
13563 this->indexes(),
13564 (this->vals() == NULL
13565 ? NULL
13566 : this->vals()->copy()),
13567 this->location());
13568}
13569
0e9a2e72 13570// Return the backend representation for constructing a slice.
13571
13572Bexpression*
13573Slice_construction_expression::do_get_backend(Translate_context* context)
13574{
13575 if (this->array_val_ == NULL)
03118c21 13576 this->array_val_ = this->create_array_val();
0e9a2e72 13577 if (this->array_val_ == NULL)
13578 {
13579 go_assert(this->type()->is_error());
13580 return context->backend()->error_expression();
13581 }
13582
13583 Location loc = this->location();
e440a328 13584
3ae06f68 13585 bool is_static_initializer = this->array_val_->is_static_initializer();
d8829beb 13586
13587 // We have to copy the initial values into heap memory if we are in
3ae06f68 13588 // a function or if the values are not constants.
13589 bool copy_to_heap = context->function() != NULL || !is_static_initializer;
e440a328 13590
f23d7786 13591 Expression* space;
0e9a2e72 13592
13593 if (this->slice_storage_ != NULL)
13594 {
13595 go_assert(!this->storage_escapes_);
13596 space = Expression::make_unary(OPERATOR_AND, this->slice_storage_, loc);
13597 }
13598 else if (!copy_to_heap)
e440a328 13599 {
f23d7786 13600 // The initializer will only run once.
0e9a2e72 13601 space = Expression::make_unary(OPERATOR_AND, this->array_val_, loc);
f23d7786 13602 space->unary_expression()->set_is_slice_init();
e440a328 13603 }
13604 else
45ff893b 13605 {
5973ede0 13606 go_assert(this->storage_escapes_ || this->element_count() == 0);
0e9a2e72 13607 space = Expression::make_heap_expression(this->array_val_, loc);
45ff893b 13608 }
d633d0fb 13609 Array_type* at = this->valtype_->array_type();
13610 Type* et = at->element_type();
13611 space = Expression::make_unsafe_cast(Type::make_pointer_type(et),
13612 space, loc);
e440a328 13613
2c809f8f 13614 // Build a constructor for the slice.
d633d0fb 13615 Expression* len = at->length();
f23d7786 13616 Expression* slice_val =
13617 Expression::make_slice_value(this->type(), space, len, len, loc);
ea664253 13618 return slice_val->get_backend(context);
e440a328 13619}
13620
13621// Make a slice composite literal. This is used by the type
13622// descriptor code.
13623
0e9a2e72 13624Slice_construction_expression*
e440a328 13625Expression::make_slice_composite_literal(Type* type, Expression_list* vals,
b13c66cd 13626 Location location)
e440a328 13627{
411eb89e 13628 go_assert(type->is_slice_type());
2c809f8f 13629 return new Slice_construction_expression(type, NULL, vals, location);
e440a328 13630}
13631
da244e59 13632// Class Map_construction_expression.
e440a328 13633
13634// Traversal.
13635
13636int
13637Map_construction_expression::do_traverse(Traverse* traverse)
13638{
13639 if (this->vals_ != NULL
13640 && this->vals_->traverse(traverse) == TRAVERSE_EXIT)
13641 return TRAVERSE_EXIT;
13642 if (Type::traverse(this->type_, traverse) == TRAVERSE_EXIT)
13643 return TRAVERSE_EXIT;
13644 return TRAVERSE_CONTINUE;
13645}
13646
2c809f8f 13647// Flatten constructor initializer into a temporary variable since
13648// we need to take its address for __go_construct_map.
13649
13650Expression*
13651Map_construction_expression::do_flatten(Gogo* gogo, Named_object*,
13652 Statement_inserter* inserter)
13653{
13654 if (!this->is_error_expression()
13655 && this->vals_ != NULL
13656 && !this->vals_->empty()
13657 && this->constructor_temp_ == NULL)
13658 {
13659 Map_type* mt = this->type_->map_type();
13660 Type* key_type = mt->key_type();
13661 Type* val_type = mt->val_type();
13662 this->element_type_ = Type::make_builtin_struct_type(2,
13663 "__key", key_type,
13664 "__val", val_type);
13665
13666 Expression_list* value_pairs = new Expression_list();
13667 Location loc = this->location();
13668
13669 size_t i = 0;
13670 for (Expression_list::const_iterator pv = this->vals_->begin();
13671 pv != this->vals_->end();
13672 ++pv, ++i)
13673 {
13674 Expression_list* key_value_pair = new Expression_list();
91c0fd76 13675 Expression* key = *pv;
5bf8be8b 13676 if (key->is_error_expression() || key->type()->is_error_type())
13677 {
13678 go_assert(saw_errors());
13679 return Expression::make_error(loc);
13680 }
91c0fd76 13681 if (key->type()->interface_type() != NULL && !key->is_variable())
13682 {
13683 Temporary_statement* temp =
13684 Statement::make_temporary(NULL, key, loc);
13685 inserter->insert(temp);
13686 key = Expression::make_temporary_reference(temp, loc);
13687 }
13688 key = Expression::convert_for_assignment(gogo, key_type, key, loc);
2c809f8f 13689
13690 ++pv;
91c0fd76 13691 Expression* val = *pv;
5bf8be8b 13692 if (val->is_error_expression() || val->type()->is_error_type())
13693 {
13694 go_assert(saw_errors());
13695 return Expression::make_error(loc);
13696 }
91c0fd76 13697 if (val->type()->interface_type() != NULL && !val->is_variable())
13698 {
13699 Temporary_statement* temp =
13700 Statement::make_temporary(NULL, val, loc);
13701 inserter->insert(temp);
13702 val = Expression::make_temporary_reference(temp, loc);
13703 }
13704 val = Expression::convert_for_assignment(gogo, val_type, val, loc);
2c809f8f 13705
13706 key_value_pair->push_back(key);
13707 key_value_pair->push_back(val);
13708 value_pairs->push_back(
13709 Expression::make_struct_composite_literal(this->element_type_,
13710 key_value_pair, loc));
13711 }
13712
e67508fa 13713 Expression* element_count = Expression::make_integer_ul(i, NULL, loc);
6bf4793c 13714 Array_type* ctor_type =
2c809f8f 13715 Type::make_array_type(this->element_type_, element_count);
6bf4793c 13716 ctor_type->set_is_array_incomparable();
2c809f8f 13717 Expression* constructor =
13718 new Fixed_array_construction_expression(ctor_type, NULL,
13719 value_pairs, loc);
13720
13721 this->constructor_temp_ =
13722 Statement::make_temporary(NULL, constructor, loc);
13723 constructor->issue_nil_check();
13724 this->constructor_temp_->set_is_address_taken();
13725 inserter->insert(this->constructor_temp_);
13726 }
13727
13728 return this;
13729}
13730
e440a328 13731// Final type determination.
13732
13733void
13734Map_construction_expression::do_determine_type(const Type_context*)
13735{
13736 if (this->vals_ == NULL)
13737 return;
13738
13739 Map_type* mt = this->type_->map_type();
13740 Type_context key_context(mt->key_type(), false);
13741 Type_context val_context(mt->val_type(), false);
13742 for (Expression_list::const_iterator pv = this->vals_->begin();
13743 pv != this->vals_->end();
13744 ++pv)
13745 {
13746 (*pv)->determine_type(&key_context);
13747 ++pv;
13748 (*pv)->determine_type(&val_context);
13749 }
13750}
13751
13752// Check types.
13753
13754void
13755Map_construction_expression::do_check_types(Gogo*)
13756{
13757 if (this->vals_ == NULL)
13758 return;
13759
13760 Map_type* mt = this->type_->map_type();
13761 int i = 0;
13762 Type* key_type = mt->key_type();
13763 Type* val_type = mt->val_type();
13764 for (Expression_list::const_iterator pv = this->vals_->begin();
13765 pv != this->vals_->end();
13766 ++pv, ++i)
13767 {
13768 if (!Type::are_assignable(key_type, (*pv)->type(), NULL))
13769 {
631d5788 13770 go_error_at((*pv)->location(),
13771 "incompatible type for element %d key in map construction",
13772 i + 1);
e440a328 13773 this->set_is_error();
13774 }
13775 ++pv;
13776 if (!Type::are_assignable(val_type, (*pv)->type(), NULL))
13777 {
631d5788 13778 go_error_at((*pv)->location(),
13779 ("incompatible type for element %d value "
13780 "in map construction"),
e440a328 13781 i + 1);
13782 this->set_is_error();
13783 }
13784 }
13785}
13786
de590a61 13787// Copy.
13788
13789Expression*
13790Map_construction_expression::do_copy()
13791{
13792 return new Map_construction_expression(this->type_->copy_expressions(),
13793 (this->vals_ == NULL
13794 ? NULL
13795 : this->vals_->copy()),
13796 this->location());
13797}
13798
ea664253 13799// Return the backend representation for constructing a map.
e440a328 13800
ea664253 13801Bexpression*
13802Map_construction_expression::do_get_backend(Translate_context* context)
e440a328 13803{
2c809f8f 13804 if (this->is_error_expression())
ea664253 13805 return context->backend()->error_expression();
2c809f8f 13806 Location loc = this->location();
e440a328 13807
e440a328 13808 size_t i = 0;
2c809f8f 13809 Expression* ventries;
e440a328 13810 if (this->vals_ == NULL || this->vals_->empty())
2c809f8f 13811 ventries = Expression::make_nil(loc);
e440a328 13812 else
13813 {
2c809f8f 13814 go_assert(this->constructor_temp_ != NULL);
13815 i = this->vals_->size() / 2;
e440a328 13816
2c809f8f 13817 Expression* ctor_ref =
13818 Expression::make_temporary_reference(this->constructor_temp_, loc);
13819 ventries = Expression::make_unary(OPERATOR_AND, ctor_ref, loc);
13820 }
e440a328 13821
2c809f8f 13822 Map_type* mt = this->type_->map_type();
13823 if (this->element_type_ == NULL)
13824 this->element_type_ =
13825 Type::make_builtin_struct_type(2,
13826 "__key", mt->key_type(),
13827 "__val", mt->val_type());
0d5530d9 13828 Expression* descriptor = Expression::make_type_descriptor(mt, loc);
2c809f8f 13829
13830 Type* uintptr_t = Type::lookup_integer_type("uintptr");
e67508fa 13831 Expression* count = Expression::make_integer_ul(i, uintptr_t, loc);
2c809f8f 13832
13833 Expression* entry_size =
13834 Expression::make_type_info(this->element_type_, TYPE_INFO_SIZE);
13835
13836 unsigned int field_index;
13837 const Struct_field* valfield =
13838 this->element_type_->find_local_field("__val", &field_index);
13839 Expression* val_offset =
13840 Expression::make_struct_field_offset(this->element_type_, valfield);
2c809f8f 13841
13842 Expression* map_ctor =
0d5530d9 13843 Runtime::make_call(Runtime::CONSTRUCT_MAP, loc, 5, descriptor, count,
13844 entry_size, val_offset, ventries);
ea664253 13845 return map_ctor->get_backend(context);
2c809f8f 13846}
e440a328 13847
2c809f8f 13848// Export an array construction.
e440a328 13849
2c809f8f 13850void
548be246 13851Map_construction_expression::do_export(Export_function_body* efb) const
2c809f8f 13852{
204d4af4 13853 efb->write_c_string("$convert(");
548be246 13854 efb->write_type(this->type_);
2c809f8f 13855 for (Expression_list::const_iterator pv = this->vals_->begin();
13856 pv != this->vals_->end();
13857 ++pv)
13858 {
548be246 13859 efb->write_c_string(", ");
13860 (*pv)->export_expression(efb);
2c809f8f 13861 }
548be246 13862 efb->write_c_string(")");
2c809f8f 13863}
e440a328 13864
2c809f8f 13865// Dump ast representation for a map construction expression.
d751bb78 13866
13867void
13868Map_construction_expression::do_dump_expression(
13869 Ast_dump_context* ast_dump_context) const
13870{
d751bb78 13871 ast_dump_context->ostream() << "{" ;
8b1c301d 13872 ast_dump_context->dump_expression_list(this->vals_, true);
d751bb78 13873 ast_dump_context->ostream() << "}";
13874}
13875
7795ac51 13876// Class Composite_literal_expression.
e440a328 13877
13878// Traversal.
13879
13880int
13881Composite_literal_expression::do_traverse(Traverse* traverse)
13882{
dbffccfc 13883 if (Type::traverse(this->type_, traverse) == TRAVERSE_EXIT)
e440a328 13884 return TRAVERSE_EXIT;
dbffccfc 13885
13886 // If this is a struct composite literal with keys, then the keys
13887 // are field names, not expressions. We don't want to traverse them
13888 // in that case. If we do, we can give an erroneous error "variable
13889 // initializer refers to itself." See bug482.go in the testsuite.
13890 if (this->has_keys_ && this->vals_ != NULL)
13891 {
13892 // The type may not be resolvable at this point.
13893 Type* type = this->type_;
a01f2481 13894
7795ac51 13895 for (int depth = 0; depth < this->depth_; ++depth)
a01f2481 13896 {
13897 if (type->array_type() != NULL)
13898 type = type->array_type()->element_type();
13899 else if (type->map_type() != NULL)
7795ac51 13900 {
13901 if (this->key_path_[depth])
13902 type = type->map_type()->key_type();
13903 else
13904 type = type->map_type()->val_type();
13905 }
a01f2481 13906 else
13907 {
13908 // This error will be reported during lowering.
13909 return TRAVERSE_CONTINUE;
13910 }
13911 }
13912
dbffccfc 13913 while (true)
13914 {
13915 if (type->classification() == Type::TYPE_NAMED)
13916 type = type->named_type()->real_type();
13917 else if (type->classification() == Type::TYPE_FORWARD)
13918 {
13919 Type* t = type->forwarded();
13920 if (t == type)
13921 break;
13922 type = t;
13923 }
13924 else
13925 break;
13926 }
13927
13928 if (type->classification() == Type::TYPE_STRUCT)
13929 {
13930 Expression_list::iterator p = this->vals_->begin();
13931 while (p != this->vals_->end())
13932 {
13933 // Skip key.
13934 ++p;
13935 go_assert(p != this->vals_->end());
13936 if (Expression::traverse(&*p, traverse) == TRAVERSE_EXIT)
13937 return TRAVERSE_EXIT;
13938 ++p;
13939 }
13940 return TRAVERSE_CONTINUE;
13941 }
13942 }
13943
13944 if (this->vals_ != NULL)
13945 return this->vals_->traverse(traverse);
13946
13947 return TRAVERSE_CONTINUE;
e440a328 13948}
13949
13950// Lower a generic composite literal into a specific version based on
13951// the type.
13952
13953Expression*
ceeb4318 13954Composite_literal_expression::do_lower(Gogo* gogo, Named_object* function,
13955 Statement_inserter* inserter, int)
e440a328 13956{
13957 Type* type = this->type_;
13958
7795ac51 13959 for (int depth = 0; depth < this->depth_; ++depth)
e440a328 13960 {
67a2ed75 13961 type = type->deref();
e440a328 13962 if (type->array_type() != NULL)
13963 type = type->array_type()->element_type();
13964 else if (type->map_type() != NULL)
7795ac51 13965 {
13966 if (this->key_path_[depth])
13967 type = type->map_type()->key_type();
13968 else
13969 type = type->map_type()->val_type();
13970 }
e440a328 13971 else
13972 {
5c13bd80 13973 if (!type->is_error())
631d5788 13974 go_error_at(this->location(),
13975 ("may only omit types within composite literals "
13976 "of slice, array, or map type"));
e440a328 13977 return Expression::make_error(this->location());
13978 }
13979 }
13980
e00772b3 13981 Type *pt = type->points_to();
13982 bool is_pointer = false;
13983 if (pt != NULL)
13984 {
13985 is_pointer = true;
13986 type = pt;
13987 }
13988
13989 Expression* ret;
5c13bd80 13990 if (type->is_error())
e440a328 13991 return Expression::make_error(this->location());
13992 else if (type->struct_type() != NULL)
e00772b3 13993 ret = this->lower_struct(gogo, type);
e440a328 13994 else if (type->array_type() != NULL)
113ef6a5 13995 ret = this->lower_array(type);
e440a328 13996 else if (type->map_type() != NULL)
e00772b3 13997 ret = this->lower_map(gogo, function, inserter, type);
e440a328 13998 else
13999 {
631d5788 14000 go_error_at(this->location(),
14001 ("expected struct, slice, array, or map type "
14002 "for composite literal"));
e440a328 14003 return Expression::make_error(this->location());
14004 }
e00772b3 14005
14006 if (is_pointer)
2c809f8f 14007 ret = Expression::make_heap_expression(ret, this->location());
e00772b3 14008
14009 return ret;
e440a328 14010}
14011
14012// Lower a struct composite literal.
14013
14014Expression*
81c4b26b 14015Composite_literal_expression::lower_struct(Gogo* gogo, Type* type)
e440a328 14016{
b13c66cd 14017 Location location = this->location();
e440a328 14018 Struct_type* st = type->struct_type();
14019 if (this->vals_ == NULL || !this->has_keys_)
07daa4e7 14020 {
e6013c28 14021 if (this->vals_ != NULL
14022 && !this->vals_->empty()
14023 && type->named_type() != NULL
14024 && type->named_type()->named_object()->package() != NULL)
14025 {
14026 for (Struct_field_list::const_iterator pf = st->fields()->begin();
14027 pf != st->fields()->end();
14028 ++pf)
07daa4e7 14029 {
07ba7f26 14030 if (Gogo::is_hidden_name(pf->field_name())
14031 || pf->is_embedded_builtin(gogo))
631d5788 14032 go_error_at(this->location(),
14033 "assignment of unexported field %qs in %qs literal",
14034 Gogo::message_name(pf->field_name()).c_str(),
14035 type->named_type()->message_name().c_str());
07daa4e7 14036 }
14037 }
14038
14039 return new Struct_construction_expression(type, this->vals_, location);
14040 }
e440a328 14041
14042 size_t field_count = st->field_count();
14043 std::vector<Expression*> vals(field_count);
e32de7ba 14044 std::vector<unsigned long>* traverse_order = new(std::vector<unsigned long>);
e440a328 14045 Expression_list::const_iterator p = this->vals_->begin();
62750cd5 14046 Expression* external_expr = NULL;
14047 const Named_object* external_no = NULL;
e440a328 14048 while (p != this->vals_->end())
14049 {
14050 Expression* name_expr = *p;
14051
14052 ++p;
c484d925 14053 go_assert(p != this->vals_->end());
e440a328 14054 Expression* val = *p;
14055
14056 ++p;
14057
14058 if (name_expr == NULL)
14059 {
631d5788 14060 go_error_at(val->location(),
14061 "mixture of field and value initializers");
e440a328 14062 return Expression::make_error(location);
14063 }
14064
14065 bool bad_key = false;
14066 std::string name;
81c4b26b 14067 const Named_object* no = NULL;
e440a328 14068 switch (name_expr->classification())
14069 {
14070 case EXPRESSION_UNKNOWN_REFERENCE:
14071 name = name_expr->unknown_expression()->name();
7f7ce694 14072 if (type->named_type() != NULL)
14073 {
14074 // If the named object found for this field name comes from a
14075 // different package than the struct it is a part of, do not count
14076 // this incorrect lookup as a usage of the object's package.
14077 no = name_expr->unknown_expression()->named_object();
14078 if (no->package() != NULL
14079 && no->package() != type->named_type()->named_object()->package())
14080 no->package()->forget_usage(name_expr);
14081 }
e440a328 14082 break;
14083
14084 case EXPRESSION_CONST_REFERENCE:
81c4b26b 14085 no = static_cast<Const_expression*>(name_expr)->named_object();
e440a328 14086 break;
14087
14088 case EXPRESSION_TYPE:
14089 {
14090 Type* t = name_expr->type();
14091 Named_type* nt = t->named_type();
14092 if (nt == NULL)
14093 bad_key = true;
14094 else
81c4b26b 14095 no = nt->named_object();
e440a328 14096 }
14097 break;
14098
14099 case EXPRESSION_VAR_REFERENCE:
81c4b26b 14100 no = name_expr->var_expression()->named_object();
e440a328 14101 break;
14102
b0c09712 14103 case EXPRESSION_ENCLOSED_VAR_REFERENCE:
14104 no = name_expr->enclosed_var_expression()->variable();
e440a328 14105 break;
14106
b0c09712 14107 case EXPRESSION_FUNC_REFERENCE:
14108 no = name_expr->func_expression()->named_object();
e440a328 14109 break;
14110
14111 default:
14112 bad_key = true;
14113 break;
14114 }
14115 if (bad_key)
14116 {
631d5788 14117 go_error_at(name_expr->location(), "expected struct field name");
e440a328 14118 return Expression::make_error(location);
14119 }
14120
81c4b26b 14121 if (no != NULL)
14122 {
62750cd5 14123 if (no->package() != NULL && external_expr == NULL)
14124 {
14125 external_expr = name_expr;
14126 external_no = no;
14127 }
14128
81c4b26b 14129 name = no->name();
14130
14131 // A predefined name won't be packed. If it starts with a
14132 // lower case letter we need to check for that case, because
2d29d278 14133 // the field name will be packed. FIXME.
81c4b26b 14134 if (!Gogo::is_hidden_name(name)
14135 && name[0] >= 'a'
14136 && name[0] <= 'z')
14137 {
14138 Named_object* gno = gogo->lookup_global(name.c_str());
14139 if (gno == no)
14140 name = gogo->pack_hidden_name(name, false);
14141 }
14142 }
14143
e440a328 14144 unsigned int index;
14145 const Struct_field* sf = st->find_local_field(name, &index);
14146 if (sf == NULL)
14147 {
631d5788 14148 go_error_at(name_expr->location(), "unknown field %qs in %qs",
14149 Gogo::message_name(name).c_str(),
14150 (type->named_type() != NULL
14151 ? type->named_type()->message_name().c_str()
14152 : "unnamed struct"));
e440a328 14153 return Expression::make_error(location);
14154 }
14155 if (vals[index] != NULL)
14156 {
631d5788 14157 go_error_at(name_expr->location(),
14158 "duplicate value for field %qs in %qs",
14159 Gogo::message_name(name).c_str(),
14160 (type->named_type() != NULL
14161 ? type->named_type()->message_name().c_str()
14162 : "unnamed struct"));
e440a328 14163 return Expression::make_error(location);
14164 }
14165
07daa4e7 14166 if (type->named_type() != NULL
14167 && type->named_type()->named_object()->package() != NULL
07ba7f26 14168 && (Gogo::is_hidden_name(sf->field_name())
14169 || sf->is_embedded_builtin(gogo)))
631d5788 14170 go_error_at(name_expr->location(),
14171 "assignment of unexported field %qs in %qs literal",
14172 Gogo::message_name(sf->field_name()).c_str(),
14173 type->named_type()->message_name().c_str());
07daa4e7 14174
e440a328 14175 vals[index] = val;
e32de7ba 14176 traverse_order->push_back(static_cast<unsigned long>(index));
e440a328 14177 }
14178
62750cd5 14179 if (!this->all_are_names_)
14180 {
14181 // This is a weird case like bug462 in the testsuite.
14182 if (external_expr == NULL)
631d5788 14183 go_error_at(this->location(), "unknown field in %qs literal",
14184 (type->named_type() != NULL
14185 ? type->named_type()->message_name().c_str()
14186 : "unnamed struct"));
62750cd5 14187 else
631d5788 14188 go_error_at(external_expr->location(), "unknown field %qs in %qs",
14189 external_no->message_name().c_str(),
14190 (type->named_type() != NULL
14191 ? type->named_type()->message_name().c_str()
14192 : "unnamed struct"));
62750cd5 14193 return Expression::make_error(location);
14194 }
14195
e440a328 14196 Expression_list* list = new Expression_list;
14197 list->reserve(field_count);
14198 for (size_t i = 0; i < field_count; ++i)
14199 list->push_back(vals[i]);
14200
0c4f5a19 14201 Struct_construction_expression* ret =
14202 new Struct_construction_expression(type, list, location);
14203 ret->set_traverse_order(traverse_order);
14204 return ret;
e440a328 14205}
14206
e32de7ba 14207// Index/value/traversal-order triple.
00773463 14208
e32de7ba 14209struct IVT_triple {
14210 unsigned long index;
14211 unsigned long traversal_order;
14212 Expression* expr;
14213 IVT_triple(unsigned long i, unsigned long to, Expression *e)
14214 : index(i), traversal_order(to), expr(e) { }
14215 bool operator<(const IVT_triple& other) const
14216 { return this->index < other.index; }
00773463 14217};
14218
e440a328 14219// Lower an array composite literal.
14220
14221Expression*
113ef6a5 14222Composite_literal_expression::lower_array(Type* type)
e440a328 14223{
b13c66cd 14224 Location location = this->location();
e440a328 14225 if (this->vals_ == NULL || !this->has_keys_)
ffe743ca 14226 return this->make_array(type, NULL, this->vals_);
e440a328 14227
ffe743ca 14228 std::vector<unsigned long>* indexes = new std::vector<unsigned long>;
14229 indexes->reserve(this->vals_->size());
00773463 14230 bool indexes_out_of_order = false;
ffe743ca 14231 Expression_list* vals = new Expression_list();
14232 vals->reserve(this->vals_->size());
e440a328 14233 unsigned long index = 0;
14234 Expression_list::const_iterator p = this->vals_->begin();
14235 while (p != this->vals_->end())
14236 {
14237 Expression* index_expr = *p;
14238
14239 ++p;
c484d925 14240 go_assert(p != this->vals_->end());
e440a328 14241 Expression* val = *p;
14242
14243 ++p;
14244
ffe743ca 14245 if (index_expr == NULL)
14246 {
8f2ebee5 14247 if (std::find(indexes->begin(), indexes->end(), index)
14248 != indexes->end())
14249 {
14250 go_error_at(val->location(),
14251 "duplicate value for index %lu", index);
14252 return Expression::make_error(location);
14253 }
ffe743ca 14254 if (!indexes->empty())
14255 indexes->push_back(index);
14256 }
14257 else
e440a328 14258 {
ffe743ca 14259 if (indexes->empty() && !vals->empty())
14260 {
14261 for (size_t i = 0; i < vals->size(); ++i)
14262 indexes->push_back(i);
14263 }
14264
0c77715b 14265 Numeric_constant nc;
14266 if (!index_expr->numeric_constant_value(&nc))
e440a328 14267 {
631d5788 14268 go_error_at(index_expr->location(),
14269 "index expression is not integer constant");
e440a328 14270 return Expression::make_error(location);
14271 }
6f6d9955 14272
0c77715b 14273 switch (nc.to_unsigned_long(&index))
e440a328 14274 {
0c77715b 14275 case Numeric_constant::NC_UL_VALID:
14276 break;
14277 case Numeric_constant::NC_UL_NOTINT:
631d5788 14278 go_error_at(index_expr->location(),
14279 "index expression is not integer constant");
0c77715b 14280 return Expression::make_error(location);
14281 case Numeric_constant::NC_UL_NEGATIVE:
631d5788 14282 go_error_at(index_expr->location(),
14283 "index expression is negative");
e440a328 14284 return Expression::make_error(location);
0c77715b 14285 case Numeric_constant::NC_UL_BIG:
631d5788 14286 go_error_at(index_expr->location(), "index value overflow");
e440a328 14287 return Expression::make_error(location);
0c77715b 14288 default:
14289 go_unreachable();
e440a328 14290 }
6f6d9955 14291
14292 Named_type* ntype = Type::lookup_integer_type("int");
14293 Integer_type* inttype = ntype->integer_type();
0c77715b 14294 if (sizeof(index) <= static_cast<size_t>(inttype->bits() * 8)
14295 && index >> (inttype->bits() - 1) != 0)
6f6d9955 14296 {
631d5788 14297 go_error_at(index_expr->location(), "index value overflow");
6f6d9955 14298 return Expression::make_error(location);
14299 }
14300
ffe743ca 14301 if (std::find(indexes->begin(), indexes->end(), index)
14302 != indexes->end())
e440a328 14303 {
631d5788 14304 go_error_at(index_expr->location(),
14305 "duplicate value for index %lu",
14306 index);
e440a328 14307 return Expression::make_error(location);
14308 }
ffe743ca 14309
00773463 14310 if (!indexes->empty() && index < indexes->back())
14311 indexes_out_of_order = true;
14312
ffe743ca 14313 indexes->push_back(index);
e440a328 14314 }
14315
ffe743ca 14316 vals->push_back(val);
14317
e440a328 14318 ++index;
14319 }
14320
ffe743ca 14321 if (indexes->empty())
14322 {
14323 delete indexes;
14324 indexes = NULL;
14325 }
e440a328 14326
e32de7ba 14327 std::vector<unsigned long>* traverse_order = NULL;
00773463 14328 if (indexes_out_of_order)
14329 {
e32de7ba 14330 typedef std::vector<IVT_triple> V;
00773463 14331
14332 V v;
14333 v.reserve(indexes->size());
14334 std::vector<unsigned long>::const_iterator pi = indexes->begin();
e32de7ba 14335 unsigned long torder = 0;
00773463 14336 for (Expression_list::const_iterator pe = vals->begin();
14337 pe != vals->end();
e32de7ba 14338 ++pe, ++pi, ++torder)
14339 v.push_back(IVT_triple(*pi, torder, *pe));
00773463 14340
e32de7ba 14341 std::sort(v.begin(), v.end());
00773463 14342
14343 delete indexes;
14344 delete vals;
e32de7ba 14345
00773463 14346 indexes = new std::vector<unsigned long>();
14347 indexes->reserve(v.size());
14348 vals = new Expression_list();
14349 vals->reserve(v.size());
e32de7ba 14350 traverse_order = new std::vector<unsigned long>();
14351 traverse_order->reserve(v.size());
00773463 14352
14353 for (V::const_iterator p = v.begin(); p != v.end(); ++p)
14354 {
e32de7ba 14355 indexes->push_back(p->index);
14356 vals->push_back(p->expr);
14357 traverse_order->push_back(p->traversal_order);
00773463 14358 }
14359 }
14360
e32de7ba 14361 Expression* ret = this->make_array(type, indexes, vals);
14362 Array_construction_expression* ace = ret->array_literal();
14363 if (ace != NULL && traverse_order != NULL)
14364 ace->set_traverse_order(traverse_order);
14365 return ret;
e440a328 14366}
14367
14368// Actually build the array composite literal. This handles
14369// [...]{...}.
14370
14371Expression*
ffe743ca 14372Composite_literal_expression::make_array(
14373 Type* type,
14374 const std::vector<unsigned long>* indexes,
14375 Expression_list* vals)
e440a328 14376{
b13c66cd 14377 Location location = this->location();
e440a328 14378 Array_type* at = type->array_type();
ffe743ca 14379
e440a328 14380 if (at->length() != NULL && at->length()->is_nil_expression())
14381 {
ffe743ca 14382 size_t size;
14383 if (vals == NULL)
14384 size = 0;
00773463 14385 else if (indexes != NULL)
14386 size = indexes->back() + 1;
14387 else
ffe743ca 14388 {
14389 size = vals->size();
14390 Integer_type* it = Type::lookup_integer_type("int")->integer_type();
14391 if (sizeof(size) <= static_cast<size_t>(it->bits() * 8)
14392 && size >> (it->bits() - 1) != 0)
14393 {
631d5788 14394 go_error_at(location, "too many elements in composite literal");
ffe743ca 14395 return Expression::make_error(location);
14396 }
14397 }
ffe743ca 14398
e67508fa 14399 Expression* elen = Expression::make_integer_ul(size, NULL, location);
e440a328 14400 at = Type::make_array_type(at->element_type(), elen);
14401 type = at;
14402 }
ffe743ca 14403 else if (at->length() != NULL
14404 && !at->length()->is_error_expression()
14405 && this->vals_ != NULL)
14406 {
14407 Numeric_constant nc;
14408 unsigned long val;
14409 if (at->length()->numeric_constant_value(&nc)
14410 && nc.to_unsigned_long(&val) == Numeric_constant::NC_UL_VALID)
14411 {
14412 if (indexes == NULL)
14413 {
14414 if (this->vals_->size() > val)
14415 {
631d5788 14416 go_error_at(location,
14417 "too many elements in composite literal");
ffe743ca 14418 return Expression::make_error(location);
14419 }
14420 }
14421 else
14422 {
00773463 14423 unsigned long max = indexes->back();
ffe743ca 14424 if (max >= val)
14425 {
631d5788 14426 go_error_at(location,
14427 ("some element keys in composite literal "
14428 "are out of range"));
ffe743ca 14429 return Expression::make_error(location);
14430 }
14431 }
14432 }
14433 }
14434
e440a328 14435 if (at->length() != NULL)
ffe743ca 14436 return new Fixed_array_construction_expression(type, indexes, vals,
14437 location);
e440a328 14438 else
2c809f8f 14439 return new Slice_construction_expression(type, indexes, vals, location);
e440a328 14440}
14441
14442// Lower a map composite literal.
14443
14444Expression*
a287720d 14445Composite_literal_expression::lower_map(Gogo* gogo, Named_object* function,
ceeb4318 14446 Statement_inserter* inserter,
a287720d 14447 Type* type)
e440a328 14448{
b13c66cd 14449 Location location = this->location();
e440a328 14450 if (this->vals_ != NULL)
14451 {
14452 if (!this->has_keys_)
14453 {
631d5788 14454 go_error_at(location, "map composite literal must have keys");
e440a328 14455 return Expression::make_error(location);
14456 }
14457
a287720d 14458 for (Expression_list::iterator p = this->vals_->begin();
e440a328 14459 p != this->vals_->end();
14460 p += 2)
14461 {
14462 if (*p == NULL)
14463 {
14464 ++p;
631d5788 14465 go_error_at((*p)->location(),
14466 ("map composite literal must "
14467 "have keys for every value"));
e440a328 14468 return Expression::make_error(location);
14469 }
a287720d 14470 // Make sure we have lowered the key; it may not have been
14471 // lowered in order to handle keys for struct composite
14472 // literals. Lower it now to get the right error message.
14473 if ((*p)->unknown_expression() != NULL)
14474 {
14475 (*p)->unknown_expression()->clear_is_composite_literal_key();
ceeb4318 14476 gogo->lower_expression(function, inserter, &*p);
c484d925 14477 go_assert((*p)->is_error_expression());
a287720d 14478 return Expression::make_error(location);
14479 }
e440a328 14480 }
14481 }
14482
14483 return new Map_construction_expression(type, this->vals_, location);
14484}
14485
de590a61 14486// Copy.
14487
14488Expression*
14489Composite_literal_expression::do_copy()
14490{
14491 Composite_literal_expression* ret =
14492 new Composite_literal_expression(this->type_->copy_expressions(),
14493 this->depth_, this->has_keys_,
14494 (this->vals_ == NULL
14495 ? NULL
14496 : this->vals_->copy()),
14497 this->all_are_names_,
14498 this->location());
14499 ret->key_path_ = this->key_path_;
14500 return ret;
14501}
14502
d751bb78 14503// Dump ast representation for a composite literal expression.
14504
14505void
14506Composite_literal_expression::do_dump_expression(
14507 Ast_dump_context* ast_dump_context) const
14508{
8b1c301d 14509 ast_dump_context->ostream() << "composite(";
d751bb78 14510 ast_dump_context->dump_type(this->type_);
14511 ast_dump_context->ostream() << ", {";
8b1c301d 14512 ast_dump_context->dump_expression_list(this->vals_, this->has_keys_);
d751bb78 14513 ast_dump_context->ostream() << "})";
14514}
14515
e440a328 14516// Make a composite literal expression.
14517
14518Expression*
14519Expression::make_composite_literal(Type* type, int depth, bool has_keys,
62750cd5 14520 Expression_list* vals, bool all_are_names,
b13c66cd 14521 Location location)
e440a328 14522{
14523 return new Composite_literal_expression(type, depth, has_keys, vals,
62750cd5 14524 all_are_names, location);
e440a328 14525}
14526
14527// Return whether this expression is a composite literal.
14528
14529bool
14530Expression::is_composite_literal() const
14531{
14532 switch (this->classification_)
14533 {
14534 case EXPRESSION_COMPOSITE_LITERAL:
14535 case EXPRESSION_STRUCT_CONSTRUCTION:
14536 case EXPRESSION_FIXED_ARRAY_CONSTRUCTION:
2c809f8f 14537 case EXPRESSION_SLICE_CONSTRUCTION:
e440a328 14538 case EXPRESSION_MAP_CONSTRUCTION:
14539 return true;
14540 default:
14541 return false;
14542 }
14543}
14544
14545// Return whether this expression is a composite literal which is not
14546// constant.
14547
14548bool
14549Expression::is_nonconstant_composite_literal() const
14550{
14551 switch (this->classification_)
14552 {
14553 case EXPRESSION_STRUCT_CONSTRUCTION:
14554 {
14555 const Struct_construction_expression *psce =
14556 static_cast<const Struct_construction_expression*>(this);
14557 return !psce->is_constant_struct();
14558 }
14559 case EXPRESSION_FIXED_ARRAY_CONSTRUCTION:
14560 {
14561 const Fixed_array_construction_expression *pace =
14562 static_cast<const Fixed_array_construction_expression*>(this);
14563 return !pace->is_constant_array();
14564 }
2c809f8f 14565 case EXPRESSION_SLICE_CONSTRUCTION:
e440a328 14566 {
2c809f8f 14567 const Slice_construction_expression *pace =
14568 static_cast<const Slice_construction_expression*>(this);
e440a328 14569 return !pace->is_constant_array();
14570 }
14571 case EXPRESSION_MAP_CONSTRUCTION:
14572 return true;
14573 default:
14574 return false;
14575 }
14576}
14577
35a54f17 14578// Return true if this is a variable or temporary_variable.
14579
14580bool
14581Expression::is_variable() const
14582{
14583 switch (this->classification_)
14584 {
14585 case EXPRESSION_VAR_REFERENCE:
14586 case EXPRESSION_TEMPORARY_REFERENCE:
14587 case EXPRESSION_SET_AND_USE_TEMPORARY:
b0c09712 14588 case EXPRESSION_ENCLOSED_VAR_REFERENCE:
35a54f17 14589 return true;
14590 default:
14591 return false;
14592 }
14593}
14594
e440a328 14595// Return true if this is a reference to a local variable.
14596
14597bool
14598Expression::is_local_variable() const
14599{
14600 const Var_expression* ve = this->var_expression();
14601 if (ve == NULL)
14602 return false;
14603 const Named_object* no = ve->named_object();
14604 return (no->is_result_variable()
14605 || (no->is_variable() && !no->var_value()->is_global()));
14606}
14607
14608// Class Type_guard_expression.
14609
14610// Traversal.
14611
14612int
14613Type_guard_expression::do_traverse(Traverse* traverse)
14614{
14615 if (Expression::traverse(&this->expr_, traverse) == TRAVERSE_EXIT
14616 || Type::traverse(this->type_, traverse) == TRAVERSE_EXIT)
14617 return TRAVERSE_EXIT;
14618 return TRAVERSE_CONTINUE;
14619}
14620
2c809f8f 14621Expression*
14622Type_guard_expression::do_flatten(Gogo*, Named_object*,
14623 Statement_inserter* inserter)
14624{
5bf8be8b 14625 if (this->expr_->is_error_expression()
14626 || this->expr_->type()->is_error_type())
14627 {
14628 go_assert(saw_errors());
14629 return Expression::make_error(this->location());
14630 }
14631
2c809f8f 14632 if (!this->expr_->is_variable())
14633 {
14634 Temporary_statement* temp = Statement::make_temporary(NULL, this->expr_,
14635 this->location());
14636 inserter->insert(temp);
14637 this->expr_ =
14638 Expression::make_temporary_reference(temp, this->location());
14639 }
14640 return this;
14641}
14642
e440a328 14643// Check types of a type guard expression. The expression must have
14644// an interface type, but the actual type conversion is checked at run
14645// time.
14646
14647void
14648Type_guard_expression::do_check_types(Gogo*)
14649{
e440a328 14650 Type* expr_type = this->expr_->type();
7e9da23f 14651 if (expr_type->interface_type() == NULL)
f725ade8 14652 {
5c13bd80 14653 if (!expr_type->is_error() && !this->type_->is_error())
f725ade8 14654 this->report_error(_("type assertion only valid for interface types"));
14655 this->set_is_error();
14656 }
e440a328 14657 else if (this->type_->interface_type() == NULL)
14658 {
14659 std::string reason;
14660 if (!expr_type->interface_type()->implements_interface(this->type_,
14661 &reason))
14662 {
5c13bd80 14663 if (!this->type_->is_error())
e440a328 14664 {
f725ade8 14665 if (reason.empty())
14666 this->report_error(_("impossible type assertion: "
14667 "type does not implement interface"));
14668 else
631d5788 14669 go_error_at(this->location(),
14670 ("impossible type assertion: "
14671 "type does not implement interface (%s)"),
14672 reason.c_str());
e440a328 14673 }
f725ade8 14674 this->set_is_error();
e440a328 14675 }
14676 }
14677}
14678
de590a61 14679// Copy.
14680
14681Expression*
14682Type_guard_expression::do_copy()
14683{
14684 return new Type_guard_expression(this->expr_->copy(),
14685 this->type_->copy_expressions(),
14686 this->location());
14687}
14688
ea664253 14689// Return the backend representation for a type guard expression.
e440a328 14690
ea664253 14691Bexpression*
14692Type_guard_expression::do_get_backend(Translate_context* context)
e440a328 14693{
2c809f8f 14694 Expression* conversion;
7e9da23f 14695 if (this->type_->interface_type() != NULL)
2c809f8f 14696 conversion =
14697 Expression::convert_interface_to_interface(this->type_, this->expr_,
14698 true, this->location());
e440a328 14699 else
2c809f8f 14700 conversion =
14701 Expression::convert_for_assignment(context->gogo(), this->type_,
14702 this->expr_, this->location());
14703
21b70e8f 14704 Gogo* gogo = context->gogo();
14705 Btype* bt = this->type_->get_backend(gogo);
14706 Bexpression* bexpr = conversion->get_backend(context);
14707 return gogo->backend()->convert_expression(bt, bexpr, this->location());
e440a328 14708}
14709
d751bb78 14710// Dump ast representation for a type guard expression.
14711
14712void
2c809f8f 14713Type_guard_expression::do_dump_expression(Ast_dump_context* ast_dump_context)
d751bb78 14714 const
14715{
14716 this->expr_->dump_expression(ast_dump_context);
14717 ast_dump_context->ostream() << ".";
14718 ast_dump_context->dump_type(this->type_);
14719}
14720
e440a328 14721// Make a type guard expression.
14722
14723Expression*
14724Expression::make_type_guard(Expression* expr, Type* type,
b13c66cd 14725 Location location)
e440a328 14726{
14727 return new Type_guard_expression(expr, type, location);
14728}
14729
2c809f8f 14730// Class Heap_expression.
e440a328 14731
da244e59 14732// Return the type of the expression stored on the heap.
e440a328 14733
da244e59 14734Type*
14735Heap_expression::do_type()
14736{ return Type::make_pointer_type(this->expr_->type()); }
e440a328 14737
ea664253 14738// Return the backend representation for allocating an expression on the heap.
e440a328 14739
ea664253 14740Bexpression*
14741Heap_expression::do_get_backend(Translate_context* context)
e440a328 14742{
03118c21 14743 Type* etype = this->expr_->type();
14744 if (this->expr_->is_error_expression() || etype->is_error())
ea664253 14745 return context->backend()->error_expression();
2c809f8f 14746
02c19a1a 14747 Location loc = this->location();
2c809f8f 14748 Gogo* gogo = context->gogo();
02c19a1a 14749 Btype* btype = this->type()->get_backend(gogo);
45ff893b 14750
03118c21 14751 Expression* alloc = Expression::make_allocation(etype, loc);
5973ede0 14752 if (this->allocate_on_stack_)
45ff893b 14753 alloc->allocation_expression()->set_allocate_on_stack();
14754 Bexpression* space = alloc->get_backend(context);
02c19a1a 14755
14756 Bstatement* decl;
14757 Named_object* fn = context->function();
14758 go_assert(fn != NULL);
14759 Bfunction* fndecl = fn->func_value()->get_or_make_decl(gogo, fn);
14760 Bvariable* space_temp =
14761 gogo->backend()->temporary_variable(fndecl, context->bblock(), btype,
14762 space, true, loc, &decl);
03118c21 14763 Btype* expr_btype = etype->get_backend(gogo);
02c19a1a 14764
ea664253 14765 Bexpression* bexpr = this->expr_->get_backend(context);
03118c21 14766
14767 // If this assignment needs a write barrier, call typedmemmove. We
14768 // don't do this in the write barrier pass because in some cases
14769 // backend conversion can introduce new Heap_expression values.
14770 Bstatement* assn;
06e83d10 14771 if (!etype->has_pointer() || this->allocate_on_stack_)
03118c21 14772 {
7af8e400 14773 space = gogo->backend()->var_expression(space_temp, loc);
03118c21 14774 Bexpression* ref =
14775 gogo->backend()->indirect_expression(expr_btype, space, true, loc);
14776 assn = gogo->backend()->assignment_statement(fndecl, ref, bexpr, loc);
14777 }
14778 else
14779 {
14780 Bstatement* edecl;
14781 Bvariable* btemp =
14782 gogo->backend()->temporary_variable(fndecl, context->bblock(),
14783 expr_btype, bexpr, true, loc,
14784 &edecl);
14785 Bexpression* btempref = gogo->backend()->var_expression(btemp,
7af8e400 14786 loc);
03118c21 14787 Bexpression* addr = gogo->backend()->address_expression(btempref, loc);
14788
14789 Expression* td = Expression::make_type_descriptor(etype, loc);
14790 Type* etype_ptr = Type::make_pointer_type(etype);
7af8e400 14791 space = gogo->backend()->var_expression(space_temp, loc);
03118c21 14792 Expression* elhs = Expression::make_backend(space, etype_ptr, loc);
14793 Expression* erhs = Expression::make_backend(addr, etype_ptr, loc);
14794 Expression* call = Runtime::make_call(Runtime::TYPEDMEMMOVE, loc, 3,
14795 td, elhs, erhs);
14796 Bexpression* bcall = call->get_backend(context);
14797 Bstatement* s = gogo->backend()->expression_statement(fndecl, bcall);
14798 assn = gogo->backend()->compound_statement(edecl, s);
14799 }
02c19a1a 14800 decl = gogo->backend()->compound_statement(decl, assn);
7af8e400 14801 space = gogo->backend()->var_expression(space_temp, loc);
ea664253 14802 return gogo->backend()->compound_expression(decl, space, loc);
e440a328 14803}
14804
2c809f8f 14805// Dump ast representation for a heap expression.
d751bb78 14806
14807void
2c809f8f 14808Heap_expression::do_dump_expression(
d751bb78 14809 Ast_dump_context* ast_dump_context) const
14810{
14811 ast_dump_context->ostream() << "&(";
14812 ast_dump_context->dump_expression(this->expr_);
14813 ast_dump_context->ostream() << ")";
14814}
14815
2c809f8f 14816// Allocate an expression on the heap.
e440a328 14817
14818Expression*
2c809f8f 14819Expression::make_heap_expression(Expression* expr, Location location)
e440a328 14820{
2c809f8f 14821 return new Heap_expression(expr, location);
e440a328 14822}
14823
14824// Class Receive_expression.
14825
14826// Return the type of a receive expression.
14827
14828Type*
14829Receive_expression::do_type()
14830{
e429e3bd 14831 if (this->is_error_expression())
14832 return Type::make_error_type();
e440a328 14833 Channel_type* channel_type = this->channel_->type()->channel_type();
14834 if (channel_type == NULL)
e429e3bd 14835 {
14836 this->report_error(_("expected channel"));
14837 return Type::make_error_type();
14838 }
e440a328 14839 return channel_type->element_type();
14840}
14841
14842// Check types for a receive expression.
14843
14844void
14845Receive_expression::do_check_types(Gogo*)
14846{
14847 Type* type = this->channel_->type();
5c13bd80 14848 if (type->is_error())
e440a328 14849 {
e429e3bd 14850 go_assert(saw_errors());
e440a328 14851 this->set_is_error();
14852 return;
14853 }
14854 if (type->channel_type() == NULL)
14855 {
14856 this->report_error(_("expected channel"));
14857 return;
14858 }
14859 if (!type->channel_type()->may_receive())
14860 {
14861 this->report_error(_("invalid receive on send-only channel"));
14862 return;
14863 }
14864}
14865
2c809f8f 14866// Flattening for receive expressions creates a temporary variable to store
14867// received data in for receives.
14868
14869Expression*
14870Receive_expression::do_flatten(Gogo*, Named_object*,
14871 Statement_inserter* inserter)
14872{
14873 Channel_type* channel_type = this->channel_->type()->channel_type();
14874 if (channel_type == NULL)
14875 {
14876 go_assert(saw_errors());
14877 return this;
14878 }
5bf8be8b 14879 else if (this->channel_->is_error_expression())
14880 {
14881 go_assert(saw_errors());
14882 return Expression::make_error(this->location());
14883 }
2c809f8f 14884
14885 Type* element_type = channel_type->element_type();
14886 if (this->temp_receiver_ == NULL)
14887 {
14888 this->temp_receiver_ = Statement::make_temporary(element_type, NULL,
14889 this->location());
14890 this->temp_receiver_->set_is_address_taken();
14891 inserter->insert(this->temp_receiver_);
14892 }
14893
14894 return this;
14895}
14896
ea664253 14897// Get the backend representation for a receive expression.
e440a328 14898
ea664253 14899Bexpression*
14900Receive_expression::do_get_backend(Translate_context* context)
e440a328 14901{
f24f10bb 14902 Location loc = this->location();
14903
e440a328 14904 Channel_type* channel_type = this->channel_->type()->channel_type();
5b8368f4 14905 if (channel_type == NULL)
14906 {
c484d925 14907 go_assert(this->channel_->type()->is_error());
ea664253 14908 return context->backend()->error_expression();
5b8368f4 14909 }
e440a328 14910
2c809f8f 14911 Expression* recv_ref =
14912 Expression::make_temporary_reference(this->temp_receiver_, loc);
14913 Expression* recv_addr =
14914 Expression::make_temporary_reference(this->temp_receiver_, loc);
14915 recv_addr = Expression::make_unary(OPERATOR_AND, recv_addr, loc);
e36a5ff5 14916 Expression* recv = Runtime::make_call(Runtime::CHANRECV1, loc, 2,
14917 this->channel_, recv_addr);
ea664253 14918 return Expression::make_compound(recv, recv_ref, loc)->get_backend(context);
e440a328 14919}
14920
d751bb78 14921// Dump ast representation for a receive expression.
14922
14923void
14924Receive_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
14925{
14926 ast_dump_context->ostream() << " <- " ;
14927 ast_dump_context->dump_expression(channel_);
14928}
14929
e440a328 14930// Make a receive expression.
14931
14932Receive_expression*
b13c66cd 14933Expression::make_receive(Expression* channel, Location location)
e440a328 14934{
14935 return new Receive_expression(channel, location);
14936}
14937
e440a328 14938// An expression which evaluates to a pointer to the type descriptor
14939// of a type.
14940
14941class Type_descriptor_expression : public Expression
14942{
14943 public:
b13c66cd 14944 Type_descriptor_expression(Type* type, Location location)
e440a328 14945 : Expression(EXPRESSION_TYPE_DESCRIPTOR, location),
14946 type_(type)
14947 { }
14948
14949 protected:
4b686186 14950 int
14951 do_traverse(Traverse*);
14952
e440a328 14953 Type*
14954 do_type()
14955 { return Type::make_type_descriptor_ptr_type(); }
14956
f9ca30f9 14957 bool
3ae06f68 14958 do_is_static_initializer() const
f9ca30f9 14959 { return true; }
14960
e440a328 14961 void
14962 do_determine_type(const Type_context*)
14963 { }
14964
14965 Expression*
14966 do_copy()
14967 { return this; }
14968
ea664253 14969 Bexpression*
14970 do_get_backend(Translate_context* context)
a1d23b41 14971 {
ea664253 14972 return this->type_->type_descriptor_pointer(context->gogo(),
14973 this->location());
a1d23b41 14974 }
e440a328 14975
d751bb78 14976 void
14977 do_dump_expression(Ast_dump_context*) const;
14978
e440a328 14979 private:
14980 // The type for which this is the descriptor.
14981 Type* type_;
14982};
14983
4b686186 14984int
14985Type_descriptor_expression::do_traverse(Traverse* traverse)
14986{
14987 if (Type::traverse(this->type_, traverse) == TRAVERSE_EXIT)
14988 return TRAVERSE_EXIT;
14989 return TRAVERSE_CONTINUE;
14990}
14991
d751bb78 14992// Dump ast representation for a type descriptor expression.
14993
14994void
14995Type_descriptor_expression::do_dump_expression(
14996 Ast_dump_context* ast_dump_context) const
14997{
14998 ast_dump_context->dump_type(this->type_);
14999}
15000
e440a328 15001// Make a type descriptor expression.
15002
15003Expression*
b13c66cd 15004Expression::make_type_descriptor(Type* type, Location location)
e440a328 15005{
15006 return new Type_descriptor_expression(type, location);
15007}
15008
aa5ae575 15009// An expression which evaluates to a pointer to the Garbage Collection symbol
15010// of a type.
15011
15012class GC_symbol_expression : public Expression
15013{
15014 public:
15015 GC_symbol_expression(Type* type)
15016 : Expression(EXPRESSION_GC_SYMBOL, Linemap::predeclared_location()),
15017 type_(type)
15018 {}
15019
15020 protected:
15021 Type*
15022 do_type()
03118c21 15023 { return Type::make_pointer_type(Type::lookup_integer_type("uint8")); }
aa5ae575 15024
15025 bool
3ae06f68 15026 do_is_static_initializer() const
aa5ae575 15027 { return true; }
15028
15029 void
15030 do_determine_type(const Type_context*)
15031 { }
15032
15033 Expression*
15034 do_copy()
15035 { return this; }
15036
15037 Bexpression*
15038 do_get_backend(Translate_context* context)
15039 { return this->type_->gc_symbol_pointer(context->gogo()); }
15040
15041 void
15042 do_dump_expression(Ast_dump_context*) const;
15043
15044 private:
15045 // The type which this gc symbol describes.
15046 Type* type_;
15047};
15048
15049// Dump ast representation for a gc symbol expression.
15050
15051void
15052GC_symbol_expression::do_dump_expression(
15053 Ast_dump_context* ast_dump_context) const
15054{
15055 ast_dump_context->ostream() << "gcdata(";
15056 ast_dump_context->dump_type(this->type_);
15057 ast_dump_context->ostream() << ")";
15058}
15059
15060// Make a gc symbol expression.
15061
15062Expression*
15063Expression::make_gc_symbol(Type* type)
15064{
15065 return new GC_symbol_expression(type);
15066}
15067
03118c21 15068// An expression that evaluates to a pointer to a symbol holding the
15069// ptrmask data of a type.
15070
15071class Ptrmask_symbol_expression : public Expression
15072{
15073 public:
15074 Ptrmask_symbol_expression(Type* type)
15075 : Expression(EXPRESSION_PTRMASK_SYMBOL, Linemap::predeclared_location()),
15076 type_(type)
15077 {}
15078
15079 protected:
15080 Type*
15081 do_type()
15082 { return Type::make_pointer_type(Type::lookup_integer_type("uint8")); }
15083
15084 bool
15085 do_is_static_initializer() const
15086 { return true; }
15087
15088 void
15089 do_determine_type(const Type_context*)
15090 { }
15091
15092 Expression*
15093 do_copy()
15094 { return this; }
15095
15096 Bexpression*
15097 do_get_backend(Translate_context*);
15098
15099 void
15100 do_dump_expression(Ast_dump_context*) const;
15101
15102 private:
15103 // The type that this ptrmask symbol describes.
15104 Type* type_;
15105};
15106
15107// Return the ptrmask variable.
15108
15109Bexpression*
15110Ptrmask_symbol_expression::do_get_backend(Translate_context* context)
15111{
15112 Gogo* gogo = context->gogo();
15113
15114 // If this type does not need a gcprog, then we can use the standard
15115 // GC symbol.
15116 int64_t ptrsize, ptrdata;
15117 if (!this->type_->needs_gcprog(gogo, &ptrsize, &ptrdata))
15118 return this->type_->gc_symbol_pointer(gogo);
15119
15120 // Otherwise we have to build a ptrmask variable, and return a
15121 // pointer to it.
15122
15123 Bvariable* bvar = this->type_->gc_ptrmask_var(gogo, ptrsize, ptrdata);
15124 Location bloc = Linemap::predeclared_location();
7af8e400 15125 Bexpression* bref = gogo->backend()->var_expression(bvar, bloc);
03118c21 15126 Bexpression* baddr = gogo->backend()->address_expression(bref, bloc);
15127
15128 Type* uint8_type = Type::lookup_integer_type("uint8");
15129 Type* pointer_uint8_type = Type::make_pointer_type(uint8_type);
15130 Btype* ubtype = pointer_uint8_type->get_backend(gogo);
15131 return gogo->backend()->convert_expression(ubtype, baddr, bloc);
15132}
15133
15134// Dump AST for a ptrmask symbol expression.
15135
15136void
15137Ptrmask_symbol_expression::do_dump_expression(
15138 Ast_dump_context* ast_dump_context) const
15139{
15140 ast_dump_context->ostream() << "ptrmask(";
15141 ast_dump_context->dump_type(this->type_);
15142 ast_dump_context->ostream() << ")";
15143}
15144
15145// Make a ptrmask symbol expression.
15146
15147Expression*
15148Expression::make_ptrmask_symbol(Type* type)
15149{
15150 return new Ptrmask_symbol_expression(type);
15151}
15152
e440a328 15153// An expression which evaluates to some characteristic of a type.
15154// This is only used to initialize fields of a type descriptor. Using
15155// a new expression class is slightly inefficient but gives us a good
15156// separation between the frontend and the middle-end with regard to
15157// how types are laid out.
15158
15159class Type_info_expression : public Expression
15160{
15161 public:
15162 Type_info_expression(Type* type, Type_info type_info)
b13c66cd 15163 : Expression(EXPRESSION_TYPE_INFO, Linemap::predeclared_location()),
e440a328 15164 type_(type), type_info_(type_info)
15165 { }
15166
15167 protected:
0e168074 15168 bool
3ae06f68 15169 do_is_static_initializer() const
0e168074 15170 { return true; }
15171
e440a328 15172 Type*
15173 do_type();
15174
15175 void
15176 do_determine_type(const Type_context*)
15177 { }
15178
15179 Expression*
15180 do_copy()
15181 { return this; }
15182
ea664253 15183 Bexpression*
15184 do_get_backend(Translate_context* context);
e440a328 15185
d751bb78 15186 void
15187 do_dump_expression(Ast_dump_context*) const;
15188
e440a328 15189 private:
15190 // The type for which we are getting information.
15191 Type* type_;
15192 // What information we want.
15193 Type_info type_info_;
15194};
15195
15196// The type is chosen to match what the type descriptor struct
15197// expects.
15198
15199Type*
15200Type_info_expression::do_type()
15201{
15202 switch (this->type_info_)
15203 {
15204 case TYPE_INFO_SIZE:
03118c21 15205 case TYPE_INFO_BACKEND_PTRDATA:
15206 case TYPE_INFO_DESCRIPTOR_PTRDATA:
e440a328 15207 return Type::lookup_integer_type("uintptr");
15208 case TYPE_INFO_ALIGNMENT:
15209 case TYPE_INFO_FIELD_ALIGNMENT:
15210 return Type::lookup_integer_type("uint8");
15211 default:
c3e6f413 15212 go_unreachable();
e440a328 15213 }
15214}
15215
ea664253 15216// Return the backend representation for type information.
e440a328 15217
ea664253 15218Bexpression*
15219Type_info_expression::do_get_backend(Translate_context* context)
e440a328 15220{
927a01eb 15221 Gogo* gogo = context->gogo();
2a305b85 15222 bool ok = true;
3f378015 15223 int64_t val;
927a01eb 15224 switch (this->type_info_)
e440a328 15225 {
927a01eb 15226 case TYPE_INFO_SIZE:
2a305b85 15227 ok = this->type_->backend_type_size(gogo, &val);
927a01eb 15228 break;
15229 case TYPE_INFO_ALIGNMENT:
2a305b85 15230 ok = this->type_->backend_type_align(gogo, &val);
927a01eb 15231 break;
15232 case TYPE_INFO_FIELD_ALIGNMENT:
2a305b85 15233 ok = this->type_->backend_type_field_align(gogo, &val);
927a01eb 15234 break;
03118c21 15235 case TYPE_INFO_BACKEND_PTRDATA:
15236 ok = this->type_->backend_type_ptrdata(gogo, &val);
15237 break;
15238 case TYPE_INFO_DESCRIPTOR_PTRDATA:
15239 ok = this->type_->descriptor_ptrdata(gogo, &val);
15240 break;
927a01eb 15241 default:
15242 go_unreachable();
e440a328 15243 }
2a305b85 15244 if (!ok)
15245 {
15246 go_assert(saw_errors());
15247 return gogo->backend()->error_expression();
15248 }
3f378015 15249 Expression* e = Expression::make_integer_int64(val, this->type(),
15250 this->location());
15251 return e->get_backend(context);
e440a328 15252}
15253
d751bb78 15254// Dump ast representation for a type info expression.
15255
15256void
15257Type_info_expression::do_dump_expression(
15258 Ast_dump_context* ast_dump_context) const
15259{
15260 ast_dump_context->ostream() << "typeinfo(";
15261 ast_dump_context->dump_type(this->type_);
15262 ast_dump_context->ostream() << ",";
15263 ast_dump_context->ostream() <<
15264 (this->type_info_ == TYPE_INFO_ALIGNMENT ? "alignment"
15265 : this->type_info_ == TYPE_INFO_FIELD_ALIGNMENT ? "field alignment"
03118c21 15266 : this->type_info_ == TYPE_INFO_SIZE ? "size"
15267 : this->type_info_ == TYPE_INFO_BACKEND_PTRDATA ? "backend_ptrdata"
15268 : this->type_info_ == TYPE_INFO_DESCRIPTOR_PTRDATA ? "descriptor_ptrdata"
d751bb78 15269 : "unknown");
15270 ast_dump_context->ostream() << ")";
15271}
15272
e440a328 15273// Make a type info expression.
15274
15275Expression*
15276Expression::make_type_info(Type* type, Type_info type_info)
15277{
15278 return new Type_info_expression(type, type_info);
15279}
15280
35a54f17 15281// An expression that evaluates to some characteristic of a slice.
15282// This is used when indexing, bound-checking, or nil checking a slice.
15283
15284class Slice_info_expression : public Expression
15285{
15286 public:
15287 Slice_info_expression(Expression* slice, Slice_info slice_info,
15288 Location location)
15289 : Expression(EXPRESSION_SLICE_INFO, location),
15290 slice_(slice), slice_info_(slice_info)
15291 { }
15292
15293 protected:
15294 Type*
15295 do_type();
15296
15297 void
15298 do_determine_type(const Type_context*)
15299 { }
15300
15301 Expression*
15302 do_copy()
15303 {
15304 return new Slice_info_expression(this->slice_->copy(), this->slice_info_,
15305 this->location());
15306 }
15307
ea664253 15308 Bexpression*
15309 do_get_backend(Translate_context* context);
35a54f17 15310
15311 void
15312 do_dump_expression(Ast_dump_context*) const;
15313
15314 void
15315 do_issue_nil_check()
15316 { this->slice_->issue_nil_check(); }
15317
15318 private:
15319 // The slice for which we are getting information.
15320 Expression* slice_;
15321 // What information we want.
15322 Slice_info slice_info_;
15323};
15324
15325// Return the type of the slice info.
15326
15327Type*
15328Slice_info_expression::do_type()
15329{
15330 switch (this->slice_info_)
15331 {
15332 case SLICE_INFO_VALUE_POINTER:
15333 return Type::make_pointer_type(
15334 this->slice_->type()->array_type()->element_type());
15335 case SLICE_INFO_LENGTH:
15336 case SLICE_INFO_CAPACITY:
15337 return Type::lookup_integer_type("int");
15338 default:
15339 go_unreachable();
15340 }
15341}
15342
ea664253 15343// Return the backend information for slice information.
35a54f17 15344
ea664253 15345Bexpression*
15346Slice_info_expression::do_get_backend(Translate_context* context)
35a54f17 15347{
15348 Gogo* gogo = context->gogo();
ea664253 15349 Bexpression* bslice = this->slice_->get_backend(context);
35a54f17 15350 switch (this->slice_info_)
15351 {
15352 case SLICE_INFO_VALUE_POINTER:
15353 case SLICE_INFO_LENGTH:
15354 case SLICE_INFO_CAPACITY:
ea664253 15355 return gogo->backend()->struct_field_expression(bslice, this->slice_info_,
15356 this->location());
35a54f17 15357 break;
15358 default:
15359 go_unreachable();
15360 }
35a54f17 15361}
15362
15363// Dump ast representation for a type info expression.
15364
15365void
15366Slice_info_expression::do_dump_expression(
15367 Ast_dump_context* ast_dump_context) const
15368{
15369 ast_dump_context->ostream() << "sliceinfo(";
15370 this->slice_->dump_expression(ast_dump_context);
15371 ast_dump_context->ostream() << ",";
15372 ast_dump_context->ostream() <<
15373 (this->slice_info_ == SLICE_INFO_VALUE_POINTER ? "values"
15374 : this->slice_info_ == SLICE_INFO_LENGTH ? "length"
15375 : this->slice_info_ == SLICE_INFO_CAPACITY ? "capacity "
15376 : "unknown");
15377 ast_dump_context->ostream() << ")";
15378}
15379
15380// Make a slice info expression.
15381
15382Expression*
15383Expression::make_slice_info(Expression* slice, Slice_info slice_info,
15384 Location location)
15385{
15386 return new Slice_info_expression(slice, slice_info, location);
15387}
15388
d633d0fb 15389// Class Slice_value_expression.
2c809f8f 15390
15391int
15392Slice_value_expression::do_traverse(Traverse* traverse)
15393{
55e8ba6a 15394 if (Type::traverse(this->type_, traverse) == TRAVERSE_EXIT
d633d0fb 15395 || Expression::traverse(&this->valmem_, traverse) == TRAVERSE_EXIT
2c809f8f 15396 || Expression::traverse(&this->len_, traverse) == TRAVERSE_EXIT
15397 || Expression::traverse(&this->cap_, traverse) == TRAVERSE_EXIT)
15398 return TRAVERSE_EXIT;
15399 return TRAVERSE_CONTINUE;
15400}
15401
d633d0fb 15402Expression*
15403Slice_value_expression::do_copy()
15404{
15405 return new Slice_value_expression(this->type_->copy_expressions(),
15406 this->valmem_->copy(),
15407 this->len_->copy(), this->cap_->copy(),
15408 this->location());
15409}
15410
ea664253 15411Bexpression*
15412Slice_value_expression::do_get_backend(Translate_context* context)
2c809f8f 15413{
15414 std::vector<Bexpression*> vals(3);
d633d0fb 15415 vals[0] = this->valmem_->get_backend(context);
ea664253 15416 vals[1] = this->len_->get_backend(context);
15417 vals[2] = this->cap_->get_backend(context);
2c809f8f 15418
15419 Gogo* gogo = context->gogo();
15420 Btype* btype = this->type_->get_backend(gogo);
ea664253 15421 return gogo->backend()->constructor_expression(btype, vals, this->location());
2c809f8f 15422}
15423
15424void
15425Slice_value_expression::do_dump_expression(
15426 Ast_dump_context* ast_dump_context) const
15427{
15428 ast_dump_context->ostream() << "slicevalue(";
15429 ast_dump_context->ostream() << "values: ";
d633d0fb 15430 this->valmem_->dump_expression(ast_dump_context);
2c809f8f 15431 ast_dump_context->ostream() << ", length: ";
15432 this->len_->dump_expression(ast_dump_context);
15433 ast_dump_context->ostream() << ", capacity: ";
15434 this->cap_->dump_expression(ast_dump_context);
15435 ast_dump_context->ostream() << ")";
15436}
15437
15438Expression*
d633d0fb 15439Expression::make_slice_value(Type* at, Expression* valmem, Expression* len,
2c809f8f 15440 Expression* cap, Location location)
15441{
15442 go_assert(at->is_slice_type());
d633d0fb 15443 go_assert(valmem->is_nil_expression()
15444 || (at->array_type()->element_type()
15445 == valmem->type()->points_to()));
15446 return new Slice_value_expression(at, valmem, len, cap, location);
2c809f8f 15447}
2387f644 15448
15449// An expression that evaluates to some characteristic of a non-empty interface.
15450// This is used to access the method table or underlying object of an interface.
15451
15452class Interface_info_expression : public Expression
15453{
15454 public:
15455 Interface_info_expression(Expression* iface, Interface_info iface_info,
2c809f8f 15456 Location location)
2387f644 15457 : Expression(EXPRESSION_INTERFACE_INFO, location),
15458 iface_(iface), iface_info_(iface_info)
15459 { }
15460
15461 protected:
15462 Type*
15463 do_type();
15464
15465 void
15466 do_determine_type(const Type_context*)
15467 { }
15468
15469 Expression*
15470 do_copy()
15471 {
15472 return new Interface_info_expression(this->iface_->copy(),
15473 this->iface_info_, this->location());
15474 }
15475
ea664253 15476 Bexpression*
15477 do_get_backend(Translate_context* context);
2387f644 15478
15479 void
15480 do_dump_expression(Ast_dump_context*) const;
15481
15482 void
15483 do_issue_nil_check()
15484 { this->iface_->issue_nil_check(); }
15485
15486 private:
15487 // The interface for which we are getting information.
15488 Expression* iface_;
15489 // What information we want.
15490 Interface_info iface_info_;
15491};
15492
15493// Return the type of the interface info.
15494
15495Type*
15496Interface_info_expression::do_type()
15497{
15498 switch (this->iface_info_)
15499 {
15500 case INTERFACE_INFO_METHODS:
15501 {
625d3118 15502 typedef Unordered_map(Interface_type*, Type*) Hashtable;
15503 static Hashtable result_types;
15504
15505 Interface_type* itype = this->iface_->type()->interface_type();
15506
15507 Hashtable::const_iterator p = result_types.find(itype);
15508 if (p != result_types.end())
15509 return p->second;
15510
2c809f8f 15511 Type* pdt = Type::make_type_descriptor_ptr_type();
625d3118 15512 if (itype->is_empty())
15513 {
15514 result_types[itype] = pdt;
15515 return pdt;
15516 }
2c809f8f 15517
2387f644 15518 Location loc = this->location();
15519 Struct_field_list* sfl = new Struct_field_list();
2387f644 15520 sfl->push_back(
15521 Struct_field(Typed_identifier("__type_descriptor", pdt, loc)));
15522
2387f644 15523 for (Typed_identifier_list::const_iterator p = itype->methods()->begin();
15524 p != itype->methods()->end();
15525 ++p)
15526 {
15527 Function_type* ft = p->type()->function_type();
15528 go_assert(ft->receiver() == NULL);
15529
15530 const Typed_identifier_list* params = ft->parameters();
15531 Typed_identifier_list* mparams = new Typed_identifier_list();
15532 if (params != NULL)
15533 mparams->reserve(params->size() + 1);
15534 Type* vt = Type::make_pointer_type(Type::make_void_type());
15535 mparams->push_back(Typed_identifier("", vt, ft->location()));
15536 if (params != NULL)
15537 {
15538 for (Typed_identifier_list::const_iterator pp = params->begin();
15539 pp != params->end();
15540 ++pp)
15541 mparams->push_back(*pp);
15542 }
15543
15544 Typed_identifier_list* mresults = (ft->results() == NULL
15545 ? NULL
15546 : ft->results()->copy());
15547 Backend_function_type* mft =
15548 Type::make_backend_function_type(NULL, mparams, mresults,
15549 ft->location());
15550
15551 std::string fname = Gogo::unpack_hidden_name(p->name());
15552 sfl->push_back(Struct_field(Typed_identifier(fname, mft, loc)));
15553 }
15554
6bf4793c 15555 Struct_type* st = Type::make_struct_type(sfl, loc);
15556 st->set_is_struct_incomparable();
15557 Pointer_type *pt = Type::make_pointer_type(st);
625d3118 15558 result_types[itype] = pt;
15559 return pt;
2387f644 15560 }
15561 case INTERFACE_INFO_OBJECT:
15562 return Type::make_pointer_type(Type::make_void_type());
15563 default:
15564 go_unreachable();
15565 }
15566}
15567
ea664253 15568// Return the backend representation for interface information.
2387f644 15569
ea664253 15570Bexpression*
15571Interface_info_expression::do_get_backend(Translate_context* context)
2387f644 15572{
15573 Gogo* gogo = context->gogo();
ea664253 15574 Bexpression* biface = this->iface_->get_backend(context);
2387f644 15575 switch (this->iface_info_)
15576 {
15577 case INTERFACE_INFO_METHODS:
15578 case INTERFACE_INFO_OBJECT:
ea664253 15579 return gogo->backend()->struct_field_expression(biface, this->iface_info_,
15580 this->location());
2387f644 15581 break;
15582 default:
15583 go_unreachable();
15584 }
2387f644 15585}
15586
15587// Dump ast representation for an interface info expression.
15588
15589void
15590Interface_info_expression::do_dump_expression(
15591 Ast_dump_context* ast_dump_context) const
15592{
2c809f8f 15593 bool is_empty = this->iface_->type()->interface_type()->is_empty();
2387f644 15594 ast_dump_context->ostream() << "interfaceinfo(";
15595 this->iface_->dump_expression(ast_dump_context);
15596 ast_dump_context->ostream() << ",";
15597 ast_dump_context->ostream() <<
2c809f8f 15598 (this->iface_info_ == INTERFACE_INFO_METHODS && !is_empty ? "methods"
15599 : this->iface_info_ == INTERFACE_INFO_TYPE_DESCRIPTOR ? "type_descriptor"
2387f644 15600 : this->iface_info_ == INTERFACE_INFO_OBJECT ? "object"
15601 : "unknown");
15602 ast_dump_context->ostream() << ")";
15603}
15604
15605// Make an interface info expression.
15606
15607Expression*
15608Expression::make_interface_info(Expression* iface, Interface_info iface_info,
15609 Location location)
15610{
15611 return new Interface_info_expression(iface, iface_info, location);
15612}
15613
2c809f8f 15614// An expression that represents an interface value. The first field is either
15615// a type descriptor for an empty interface or a pointer to the interface method
15616// table for a non-empty interface. The second field is always the object.
15617
15618class Interface_value_expression : public Expression
15619{
15620 public:
15621 Interface_value_expression(Type* type, Expression* first_field,
15622 Expression* obj, Location location)
15623 : Expression(EXPRESSION_INTERFACE_VALUE, location),
15624 type_(type), first_field_(first_field), obj_(obj)
15625 { }
15626
15627 protected:
15628 int
15629 do_traverse(Traverse*);
15630
15631 Type*
15632 do_type()
15633 { return this->type_; }
15634
15635 void
15636 do_determine_type(const Type_context*)
15637 { go_unreachable(); }
15638
15639 Expression*
15640 do_copy()
15641 {
de590a61 15642 return new Interface_value_expression(this->type_->copy_expressions(),
2c809f8f 15643 this->first_field_->copy(),
15644 this->obj_->copy(), this->location());
15645 }
15646
ea664253 15647 Bexpression*
15648 do_get_backend(Translate_context* context);
2c809f8f 15649
15650 void
15651 do_dump_expression(Ast_dump_context*) const;
15652
15653 private:
15654 // The type of the interface value.
15655 Type* type_;
15656 // The first field of the interface (either a type descriptor or a pointer
15657 // to the method table.
15658 Expression* first_field_;
15659 // The underlying object of the interface.
15660 Expression* obj_;
15661};
15662
15663int
15664Interface_value_expression::do_traverse(Traverse* traverse)
15665{
15666 if (Expression::traverse(&this->first_field_, traverse) == TRAVERSE_EXIT
15667 || Expression::traverse(&this->obj_, traverse) == TRAVERSE_EXIT)
15668 return TRAVERSE_EXIT;
15669 return TRAVERSE_CONTINUE;
15670}
15671
ea664253 15672Bexpression*
15673Interface_value_expression::do_get_backend(Translate_context* context)
2c809f8f 15674{
15675 std::vector<Bexpression*> vals(2);
ea664253 15676 vals[0] = this->first_field_->get_backend(context);
15677 vals[1] = this->obj_->get_backend(context);
2c809f8f 15678
15679 Gogo* gogo = context->gogo();
15680 Btype* btype = this->type_->get_backend(gogo);
ea664253 15681 return gogo->backend()->constructor_expression(btype, vals, this->location());
2c809f8f 15682}
15683
15684void
15685Interface_value_expression::do_dump_expression(
15686 Ast_dump_context* ast_dump_context) const
15687{
15688 ast_dump_context->ostream() << "interfacevalue(";
15689 ast_dump_context->ostream() <<
15690 (this->type_->interface_type()->is_empty()
15691 ? "type_descriptor: "
15692 : "methods: ");
15693 this->first_field_->dump_expression(ast_dump_context);
15694 ast_dump_context->ostream() << ", object: ";
15695 this->obj_->dump_expression(ast_dump_context);
15696 ast_dump_context->ostream() << ")";
15697}
15698
15699Expression*
15700Expression::make_interface_value(Type* type, Expression* first_value,
15701 Expression* object, Location location)
15702{
15703 return new Interface_value_expression(type, first_value, object, location);
15704}
15705
15706// An interface method table for a pair of types: an interface type and a type
15707// that implements that interface.
15708
15709class Interface_mtable_expression : public Expression
15710{
15711 public:
15712 Interface_mtable_expression(Interface_type* itype, Type* type,
15713 bool is_pointer, Location location)
15714 : Expression(EXPRESSION_INTERFACE_MTABLE, location),
15715 itype_(itype), type_(type), is_pointer_(is_pointer),
15716 method_table_type_(NULL), bvar_(NULL)
15717 { }
15718
15719 protected:
15720 int
15721 do_traverse(Traverse*);
15722
15723 Type*
15724 do_type();
15725
15726 bool
3ae06f68 15727 do_is_static_initializer() const
2c809f8f 15728 { return true; }
15729
15730 void
15731 do_determine_type(const Type_context*)
15732 { go_unreachable(); }
15733
15734 Expression*
15735 do_copy()
15736 {
de590a61 15737 Interface_type* itype = this->itype_->copy_expressions()->interface_type();
15738 return new Interface_mtable_expression(itype,
15739 this->type_->copy_expressions(),
2c809f8f 15740 this->is_pointer_, this->location());
15741 }
15742
15743 bool
15744 do_is_addressable() const
15745 { return true; }
15746
ea664253 15747 Bexpression*
15748 do_get_backend(Translate_context* context);
2c809f8f 15749
15750 void
15751 do_dump_expression(Ast_dump_context*) const;
15752
15753 private:
15754 // The interface type for which the methods are defined.
15755 Interface_type* itype_;
15756 // The type to construct the interface method table for.
15757 Type* type_;
15758 // Whether this table contains the method set for the receiver type or the
15759 // pointer receiver type.
15760 bool is_pointer_;
15761 // The type of the method table.
15762 Type* method_table_type_;
15763 // The backend variable that refers to the interface method table.
15764 Bvariable* bvar_;
15765};
15766
15767int
15768Interface_mtable_expression::do_traverse(Traverse* traverse)
15769{
15770 if (Type::traverse(this->itype_, traverse) == TRAVERSE_EXIT
15771 || Type::traverse(this->type_, traverse) == TRAVERSE_EXIT)
15772 return TRAVERSE_EXIT;
15773 return TRAVERSE_CONTINUE;
15774}
15775
15776Type*
15777Interface_mtable_expression::do_type()
15778{
15779 if (this->method_table_type_ != NULL)
15780 return this->method_table_type_;
15781
15782 const Typed_identifier_list* interface_methods = this->itype_->methods();
15783 go_assert(!interface_methods->empty());
15784
15785 Struct_field_list* sfl = new Struct_field_list;
15786 Typed_identifier tid("__type_descriptor", Type::make_type_descriptor_ptr_type(),
15787 this->location());
15788 sfl->push_back(Struct_field(tid));
db122cb9 15789 Type* unsafe_ptr_type = Type::make_pointer_type(Type::make_void_type());
2c809f8f 15790 for (Typed_identifier_list::const_iterator p = interface_methods->begin();
15791 p != interface_methods->end();
15792 ++p)
db122cb9 15793 {
15794 // We want C function pointers here, not func descriptors; model
15795 // using void* pointers.
15796 Typed_identifier method(p->name(), unsafe_ptr_type, p->location());
15797 sfl->push_back(Struct_field(method));
15798 }
6bf4793c 15799 Struct_type* st = Type::make_struct_type(sfl, this->location());
15800 st->set_is_struct_incomparable();
15801 this->method_table_type_ = st;
2c809f8f 15802 return this->method_table_type_;
15803}
15804
ea664253 15805Bexpression*
15806Interface_mtable_expression::do_get_backend(Translate_context* context)
2c809f8f 15807{
15808 Gogo* gogo = context->gogo();
2c809f8f 15809 Location loc = Linemap::predeclared_location();
15810 if (this->bvar_ != NULL)
7af8e400 15811 return gogo->backend()->var_expression(this->bvar_, this->location());
2c809f8f 15812
15813 const Typed_identifier_list* interface_methods = this->itype_->methods();
15814 go_assert(!interface_methods->empty());
15815
19272321 15816 std::string mangled_name =
15817 gogo->interface_method_table_name(this->itype_, this->type_,
15818 this->is_pointer_);
2c809f8f 15819
1530c754 15820 // Set is_public if we are converting a named type to an interface
15821 // type that is defined in the same package as the named type, and
15822 // the interface has hidden methods. In that case the interface
15823 // method table will be defined by the package that defines the
15824 // types.
15825 bool is_public = false;
15826 if (this->type_->named_type() != NULL
15827 && (this->type_->named_type()->named_object()->package()
15828 == this->itype_->package()))
15829 {
15830 for (Typed_identifier_list::const_iterator p = interface_methods->begin();
15831 p != interface_methods->end();
15832 ++p)
2c809f8f 15833 {
1530c754 15834 if (Gogo::is_hidden_name(p->name()))
15835 {
15836 is_public = true;
15837 break;
15838 }
2c809f8f 15839 }
15840 }
15841
1530c754 15842 if (is_public
2c809f8f 15843 && this->type_->named_type()->named_object()->package() != NULL)
15844 {
1530c754 15845 // The interface conversion table is defined elsewhere.
2c809f8f 15846 Btype* btype = this->type()->get_backend(gogo);
438b4bec 15847 std::string asm_name(go_selectively_encode_id(mangled_name));
2c809f8f 15848 this->bvar_ =
438b4bec 15849 gogo->backend()->immutable_struct_reference(mangled_name, asm_name,
15850 btype, loc);
7af8e400 15851 return gogo->backend()->var_expression(this->bvar_, this->location());
2c809f8f 15852 }
15853
15854 // The first element is the type descriptor.
15855 Type* td_type;
15856 if (!this->is_pointer_)
15857 td_type = this->type_;
15858 else
15859 td_type = Type::make_pointer_type(this->type_);
15860
db122cb9 15861 std::vector<Backend::Btyped_identifier> bstructfields;
15862
2c809f8f 15863 // Build an interface method table for a type: a type descriptor followed by a
15864 // list of function pointers, one for each interface method. This is used for
15865 // interfaces.
15866 Expression_list* svals = new Expression_list();
db122cb9 15867 Expression* tdescriptor = Expression::make_type_descriptor(td_type, loc);
15868 svals->push_back(tdescriptor);
15869
15870 Btype* tdesc_btype = tdescriptor->type()->get_backend(gogo);
15871 Backend::Btyped_identifier btd("_type", tdesc_btype, loc);
15872 bstructfields.push_back(btd);
2c809f8f 15873
15874 Named_type* nt = this->type_->named_type();
15875 Struct_type* st = this->type_->struct_type();
15876 go_assert(nt != NULL || st != NULL);
15877
15878 for (Typed_identifier_list::const_iterator p = interface_methods->begin();
15879 p != interface_methods->end();
15880 ++p)
15881 {
15882 bool is_ambiguous;
15883 Method* m;
15884 if (nt != NULL)
15885 m = nt->method_function(p->name(), &is_ambiguous);
15886 else
15887 m = st->method_function(p->name(), &is_ambiguous);
15888 go_assert(m != NULL);
15889 Named_object* no = m->named_object();
15890
15891 go_assert(no->is_function() || no->is_function_declaration());
db122cb9 15892
15893 Btype* fcn_btype = m->type()->get_backend_fntype(gogo);
15894 Backend::Btyped_identifier bmtype(p->name(), fcn_btype, loc);
15895 bstructfields.push_back(bmtype);
15896
2c809f8f 15897 svals->push_back(Expression::make_func_code_reference(no, loc));
15898 }
15899
db122cb9 15900 Btype *btype = gogo->backend()->struct_type(bstructfields);
15901 std::vector<Bexpression*> ctor_bexprs;
15902 for (Expression_list::const_iterator pe = svals->begin();
15903 pe != svals->end();
15904 ++pe)
15905 {
15906 ctor_bexprs.push_back((*pe)->get_backend(context));
15907 }
15908 Bexpression* ctor =
15909 gogo->backend()->constructor_expression(btype, ctor_bexprs, loc);
2c809f8f 15910
438b4bec 15911 std::string asm_name(go_selectively_encode_id(mangled_name));
15912 this->bvar_ = gogo->backend()->immutable_struct(mangled_name, asm_name, false,
2c809f8f 15913 !is_public, btype, loc);
15914 gogo->backend()->immutable_struct_set_init(this->bvar_, mangled_name, false,
15915 !is_public, btype, loc, ctor);
7af8e400 15916 return gogo->backend()->var_expression(this->bvar_, loc);
2c809f8f 15917}
15918
15919void
15920Interface_mtable_expression::do_dump_expression(
15921 Ast_dump_context* ast_dump_context) const
15922{
15923 ast_dump_context->ostream() << "__go_"
15924 << (this->is_pointer_ ? "pimt__" : "imt_");
15925 ast_dump_context->dump_type(this->itype_);
15926 ast_dump_context->ostream() << "__";
15927 ast_dump_context->dump_type(this->type_);
15928}
15929
15930Expression*
15931Expression::make_interface_mtable_ref(Interface_type* itype, Type* type,
15932 bool is_pointer, Location location)
15933{
15934 return new Interface_mtable_expression(itype, type, is_pointer, location);
15935}
15936
e440a328 15937// An expression which evaluates to the offset of a field within a
15938// struct. This, like Type_info_expression, q.v., is only used to
15939// initialize fields of a type descriptor.
15940
15941class Struct_field_offset_expression : public Expression
15942{
15943 public:
15944 Struct_field_offset_expression(Struct_type* type, const Struct_field* field)
b13c66cd 15945 : Expression(EXPRESSION_STRUCT_FIELD_OFFSET,
15946 Linemap::predeclared_location()),
e440a328 15947 type_(type), field_(field)
15948 { }
15949
15950 protected:
f23d7786 15951 bool
3ae06f68 15952 do_is_static_initializer() const
f23d7786 15953 { return true; }
15954
e440a328 15955 Type*
15956 do_type()
15957 { return Type::lookup_integer_type("uintptr"); }
15958
15959 void
15960 do_determine_type(const Type_context*)
15961 { }
15962
15963 Expression*
15964 do_copy()
15965 { return this; }
15966
ea664253 15967 Bexpression*
15968 do_get_backend(Translate_context* context);
e440a328 15969
d751bb78 15970 void
15971 do_dump_expression(Ast_dump_context*) const;
15972
e440a328 15973 private:
15974 // The type of the struct.
15975 Struct_type* type_;
15976 // The field.
15977 const Struct_field* field_;
15978};
15979
ea664253 15980// Return the backend representation for a struct field offset.
e440a328 15981
ea664253 15982Bexpression*
15983Struct_field_offset_expression::do_get_backend(Translate_context* context)
e440a328 15984{
e440a328 15985 const Struct_field_list* fields = this->type_->fields();
e440a328 15986 Struct_field_list::const_iterator p;
2c8bda43 15987 unsigned i = 0;
e440a328 15988 for (p = fields->begin();
15989 p != fields->end();
2c8bda43 15990 ++p, ++i)
15991 if (&*p == this->field_)
15992 break;
c484d925 15993 go_assert(&*p == this->field_);
e440a328 15994
2c8bda43 15995 Gogo* gogo = context->gogo();
15996 Btype* btype = this->type_->get_backend(gogo);
15997
3f378015 15998 int64_t offset = gogo->backend()->type_field_offset(btype, i);
2c8bda43 15999 Type* uptr_type = Type::lookup_integer_type("uintptr");
e67508fa 16000 Expression* ret =
3f378015 16001 Expression::make_integer_int64(offset, uptr_type,
16002 Linemap::predeclared_location());
ea664253 16003 return ret->get_backend(context);
e440a328 16004}
16005
d751bb78 16006// Dump ast representation for a struct field offset expression.
16007
16008void
16009Struct_field_offset_expression::do_dump_expression(
16010 Ast_dump_context* ast_dump_context) const
16011{
16012 ast_dump_context->ostream() << "unsafe.Offsetof(";
2d29d278 16013 ast_dump_context->dump_type(this->type_);
16014 ast_dump_context->ostream() << '.';
16015 ast_dump_context->ostream() <<
16016 Gogo::message_name(this->field_->field_name());
d751bb78 16017 ast_dump_context->ostream() << ")";
16018}
16019
e440a328 16020// Make an expression for a struct field offset.
16021
16022Expression*
16023Expression::make_struct_field_offset(Struct_type* type,
16024 const Struct_field* field)
16025{
16026 return new Struct_field_offset_expression(type, field);
16027}
16028
16029// An expression which evaluates to the address of an unnamed label.
16030
16031class Label_addr_expression : public Expression
16032{
16033 public:
b13c66cd 16034 Label_addr_expression(Label* label, Location location)
e440a328 16035 : Expression(EXPRESSION_LABEL_ADDR, location),
16036 label_(label)
16037 { }
16038
16039 protected:
16040 Type*
16041 do_type()
16042 { return Type::make_pointer_type(Type::make_void_type()); }
16043
16044 void
16045 do_determine_type(const Type_context*)
16046 { }
16047
16048 Expression*
16049 do_copy()
16050 { return new Label_addr_expression(this->label_, this->location()); }
16051
ea664253 16052 Bexpression*
16053 do_get_backend(Translate_context* context)
16054 { return this->label_->get_addr(context, this->location()); }
e440a328 16055
d751bb78 16056 void
16057 do_dump_expression(Ast_dump_context* ast_dump_context) const
16058 { ast_dump_context->ostream() << this->label_->name(); }
16059
e440a328 16060 private:
16061 // The label whose address we are taking.
16062 Label* label_;
16063};
16064
16065// Make an expression for the address of an unnamed label.
16066
16067Expression*
b13c66cd 16068Expression::make_label_addr(Label* label, Location location)
e440a328 16069{
16070 return new Label_addr_expression(label, location);
16071}
16072
da244e59 16073// Class Conditional_expression.
283a177b 16074
2c809f8f 16075// Traversal.
16076
16077int
16078Conditional_expression::do_traverse(Traverse* traverse)
16079{
16080 if (Expression::traverse(&this->cond_, traverse) == TRAVERSE_EXIT
16081 || Expression::traverse(&this->then_, traverse) == TRAVERSE_EXIT
16082 || Expression::traverse(&this->else_, traverse) == TRAVERSE_EXIT)
16083 return TRAVERSE_EXIT;
16084 return TRAVERSE_CONTINUE;
16085}
16086
283a177b 16087// Return the type of the conditional expression.
16088
16089Type*
16090Conditional_expression::do_type()
16091{
16092 Type* result_type = Type::make_void_type();
3a522dcc 16093 if (Type::are_identical(this->then_->type(), this->else_->type(),
16094 Type::COMPARE_ERRORS | Type::COMPARE_TAGS,
2c809f8f 16095 NULL))
283a177b 16096 result_type = this->then_->type();
16097 else if (this->then_->is_nil_expression()
16098 || this->else_->is_nil_expression())
16099 result_type = (!this->then_->is_nil_expression()
16100 ? this->then_->type()
16101 : this->else_->type());
16102 return result_type;
16103}
16104
2c809f8f 16105// Determine type for a conditional expression.
16106
16107void
16108Conditional_expression::do_determine_type(const Type_context* context)
16109{
16110 this->cond_->determine_type_no_context();
16111 this->then_->determine_type(context);
16112 this->else_->determine_type(context);
16113}
16114
283a177b 16115// Get the backend representation of a conditional expression.
16116
ea664253 16117Bexpression*
16118Conditional_expression::do_get_backend(Translate_context* context)
283a177b 16119{
16120 Gogo* gogo = context->gogo();
16121 Btype* result_btype = this->type()->get_backend(gogo);
ea664253 16122 Bexpression* cond = this->cond_->get_backend(context);
16123 Bexpression* then = this->then_->get_backend(context);
16124 Bexpression* belse = this->else_->get_backend(context);
93715b75 16125 Bfunction* bfn = context->function()->func_value()->get_decl();
16126 return gogo->backend()->conditional_expression(bfn, result_btype, cond, then,
ea664253 16127 belse, this->location());
283a177b 16128}
16129
16130// Dump ast representation of a conditional expression.
16131
16132void
16133Conditional_expression::do_dump_expression(
16134 Ast_dump_context* ast_dump_context) const
16135{
16136 ast_dump_context->ostream() << "(";
16137 ast_dump_context->dump_expression(this->cond_);
16138 ast_dump_context->ostream() << " ? ";
16139 ast_dump_context->dump_expression(this->then_);
16140 ast_dump_context->ostream() << " : ";
16141 ast_dump_context->dump_expression(this->else_);
16142 ast_dump_context->ostream() << ") ";
16143}
16144
16145// Make a conditional expression.
16146
16147Expression*
16148Expression::make_conditional(Expression* cond, Expression* then,
16149 Expression* else_expr, Location location)
16150{
16151 return new Conditional_expression(cond, then, else_expr, location);
16152}
16153
da244e59 16154// Class Compound_expression.
2c809f8f 16155
16156// Traversal.
16157
16158int
16159Compound_expression::do_traverse(Traverse* traverse)
16160{
16161 if (Expression::traverse(&this->init_, traverse) == TRAVERSE_EXIT
16162 || Expression::traverse(&this->expr_, traverse) == TRAVERSE_EXIT)
16163 return TRAVERSE_EXIT;
16164 return TRAVERSE_CONTINUE;
16165}
16166
16167// Return the type of the compound expression.
16168
16169Type*
16170Compound_expression::do_type()
16171{
16172 return this->expr_->type();
16173}
16174
16175// Determine type for a compound expression.
16176
16177void
16178Compound_expression::do_determine_type(const Type_context* context)
16179{
16180 this->init_->determine_type_no_context();
16181 this->expr_->determine_type(context);
16182}
16183
16184// Get the backend representation of a compound expression.
16185
ea664253 16186Bexpression*
16187Compound_expression::do_get_backend(Translate_context* context)
2c809f8f 16188{
16189 Gogo* gogo = context->gogo();
ea664253 16190 Bexpression* binit = this->init_->get_backend(context);
0ab48656 16191 Bfunction* bfunction = context->function()->func_value()->get_decl();
16192 Bstatement* init_stmt = gogo->backend()->expression_statement(bfunction,
16193 binit);
ea664253 16194 Bexpression* bexpr = this->expr_->get_backend(context);
16195 return gogo->backend()->compound_expression(init_stmt, bexpr,
16196 this->location());
2c809f8f 16197}
16198
16199// Dump ast representation of a conditional expression.
16200
16201void
16202Compound_expression::do_dump_expression(
16203 Ast_dump_context* ast_dump_context) const
16204{
16205 ast_dump_context->ostream() << "(";
16206 ast_dump_context->dump_expression(this->init_);
16207 ast_dump_context->ostream() << ",";
16208 ast_dump_context->dump_expression(this->expr_);
16209 ast_dump_context->ostream() << ") ";
16210}
16211
16212// Make a compound expression.
16213
16214Expression*
16215Expression::make_compound(Expression* init, Expression* expr, Location location)
16216{
16217 return new Compound_expression(init, expr, location);
16218}
16219
1b4fb1e0 16220// Class Backend_expression.
16221
16222int
16223Backend_expression::do_traverse(Traverse*)
16224{
16225 return TRAVERSE_CONTINUE;
16226}
16227
de590a61 16228Expression*
16229Backend_expression::do_copy()
16230{
16231 return new Backend_expression(this->bexpr_, this->type_->copy_expressions(),
16232 this->location());
16233}
16234
1b4fb1e0 16235void
16236Backend_expression::do_dump_expression(Ast_dump_context* ast_dump_context) const
16237{
16238 ast_dump_context->ostream() << "backend_expression<";
16239 ast_dump_context->dump_type(this->type_);
16240 ast_dump_context->ostream() << ">";
16241}
16242
16243Expression*
16244Expression::make_backend(Bexpression* bexpr, Type* type, Location location)
16245{
16246 return new Backend_expression(bexpr, type, location);
16247}
16248
e440a328 16249// Import an expression. This comes at the end in order to see the
16250// various class definitions.
16251
16252Expression*
bc8e2ef4 16253Expression::import_expression(Import_expression* imp, Location loc)
e440a328 16254{
16255 int c = imp->peek_char();
5f6f5357 16256 if (c == '+' || c == '-' || c == '!' || c == '^' || c == '&' || c == '*')
9b92780c 16257 return Unary_expression::do_import(imp, loc);
e440a328 16258 else if (c == '(')
9b92780c 16259 return Binary_expression::do_import(imp, loc);
204d4af4 16260 else if (imp->match_c_string("$true")
16261 || imp->match_c_string("$false")
16262 || (imp->version() < EXPORT_FORMAT_V3
16263 && (imp->match_c_string("true")
16264 || imp->match_c_string("false"))))
9b92780c 16265 return Boolean_expression::do_import(imp, loc);
e440a328 16266 else if (c == '"')
9b92780c 16267 return String_expression::do_import(imp, loc);
e440a328 16268 else if (c == '-' || (c >= '0' && c <= '9'))
16269 {
16270 // This handles integers, floats and complex constants.
9b92780c 16271 return Integer_expression::do_import(imp, loc);
e440a328 16272 }
204d4af4 16273 else if (imp->match_c_string("$nil")
16274 || (imp->version() < EXPORT_FORMAT_V3
16275 && imp->match_c_string("nil")))
9b92780c 16276 return Nil_expression::do_import(imp, loc);
204d4af4 16277 else if (imp->match_c_string("$convert")
16278 || (imp->version() < EXPORT_FORMAT_V3
16279 && imp->match_c_string("convert")))
9b92780c 16280 return Type_conversion_expression::do_import(imp, loc);
5f6f5357 16281
16282 Import_function_body* ifb = imp->ifb();
16283 if (ifb == NULL)
e440a328 16284 {
631d5788 16285 go_error_at(imp->location(), "import error: expected expression");
9b92780c 16286 return Expression::make_error(loc);
e440a328 16287 }
5f6f5357 16288 if (ifb->saw_error())
16289 return Expression::make_error(loc);
16290 std::string id = ifb->read_identifier();
16291 if (id.empty())
16292 {
16293 if (!ifb->saw_error())
16294 go_error_at(imp->location(),
16295 "import error: expected identifier at %lu",
16296 static_cast<unsigned long>(ifb->off()));
16297 ifb->set_saw_error();
16298 return Expression::make_error(loc);
16299 }
16300 Named_object* var = ifb->block()->bindings()->lookup(id);
16301 if (var == NULL)
16302 {
16303 if (!ifb->saw_error())
16304 go_error_at(imp->location(), "import error: lookup of %qs failed",
16305 id.c_str());
16306 ifb->set_saw_error();
16307 return Expression::make_error(loc);
16308 }
16309 return Expression::make_var_reference(var, loc);
e440a328 16310}
16311
16312// Class Expression_list.
16313
16314// Traverse the list.
16315
16316int
16317Expression_list::traverse(Traverse* traverse)
16318{
16319 for (Expression_list::iterator p = this->begin();
16320 p != this->end();
16321 ++p)
16322 {
16323 if (*p != NULL)
16324 {
16325 if (Expression::traverse(&*p, traverse) == TRAVERSE_EXIT)
16326 return TRAVERSE_EXIT;
16327 }
16328 }
16329 return TRAVERSE_CONTINUE;
16330}
16331
16332// Copy the list.
16333
16334Expression_list*
16335Expression_list::copy()
16336{
16337 Expression_list* ret = new Expression_list();
16338 for (Expression_list::iterator p = this->begin();
16339 p != this->end();
16340 ++p)
16341 {
16342 if (*p == NULL)
16343 ret->push_back(NULL);
16344 else
16345 ret->push_back((*p)->copy());
16346 }
16347 return ret;
16348}
16349
16350// Return whether an expression list has an error expression.
16351
16352bool
16353Expression_list::contains_error() const
16354{
16355 for (Expression_list::const_iterator p = this->begin();
16356 p != this->end();
16357 ++p)
16358 if (*p != NULL && (*p)->is_error_expression())
16359 return true;
16360 return false;
16361}
0c77715b 16362
16363// Class Numeric_constant.
16364
16365// Destructor.
16366
16367Numeric_constant::~Numeric_constant()
16368{
16369 this->clear();
16370}
16371
16372// Copy constructor.
16373
16374Numeric_constant::Numeric_constant(const Numeric_constant& a)
16375 : classification_(a.classification_), type_(a.type_)
16376{
16377 switch (a.classification_)
16378 {
16379 case NC_INVALID:
16380 break;
16381 case NC_INT:
16382 case NC_RUNE:
16383 mpz_init_set(this->u_.int_val, a.u_.int_val);
16384 break;
16385 case NC_FLOAT:
16386 mpfr_init_set(this->u_.float_val, a.u_.float_val, GMP_RNDN);
16387 break;
16388 case NC_COMPLEX:
fcbea5e4 16389 mpc_init2(this->u_.complex_val, mpc_precision);
16390 mpc_set(this->u_.complex_val, a.u_.complex_val, MPC_RNDNN);
0c77715b 16391 break;
16392 default:
16393 go_unreachable();
16394 }
16395}
16396
16397// Assignment operator.
16398
16399Numeric_constant&
16400Numeric_constant::operator=(const Numeric_constant& a)
16401{
16402 this->clear();
16403 this->classification_ = a.classification_;
16404 this->type_ = a.type_;
16405 switch (a.classification_)
16406 {
16407 case NC_INVALID:
16408 break;
16409 case NC_INT:
16410 case NC_RUNE:
16411 mpz_init_set(this->u_.int_val, a.u_.int_val);
16412 break;
16413 case NC_FLOAT:
16414 mpfr_init_set(this->u_.float_val, a.u_.float_val, GMP_RNDN);
16415 break;
16416 case NC_COMPLEX:
fcbea5e4 16417 mpc_init2(this->u_.complex_val, mpc_precision);
16418 mpc_set(this->u_.complex_val, a.u_.complex_val, MPC_RNDNN);
0c77715b 16419 break;
16420 default:
16421 go_unreachable();
16422 }
16423 return *this;
16424}
16425
16426// Clear the contents.
16427
16428void
16429Numeric_constant::clear()
16430{
16431 switch (this->classification_)
16432 {
16433 case NC_INVALID:
16434 break;
16435 case NC_INT:
16436 case NC_RUNE:
16437 mpz_clear(this->u_.int_val);
16438 break;
16439 case NC_FLOAT:
16440 mpfr_clear(this->u_.float_val);
16441 break;
16442 case NC_COMPLEX:
fcbea5e4 16443 mpc_clear(this->u_.complex_val);
0c77715b 16444 break;
16445 default:
16446 go_unreachable();
16447 }
16448 this->classification_ = NC_INVALID;
16449}
16450
16451// Set to an unsigned long value.
16452
16453void
16454Numeric_constant::set_unsigned_long(Type* type, unsigned long val)
16455{
16456 this->clear();
16457 this->classification_ = NC_INT;
16458 this->type_ = type;
16459 mpz_init_set_ui(this->u_.int_val, val);
16460}
16461
16462// Set to an integer value.
16463
16464void
16465Numeric_constant::set_int(Type* type, const mpz_t val)
16466{
16467 this->clear();
16468 this->classification_ = NC_INT;
16469 this->type_ = type;
16470 mpz_init_set(this->u_.int_val, val);
16471}
16472
16473// Set to a rune value.
16474
16475void
16476Numeric_constant::set_rune(Type* type, const mpz_t val)
16477{
16478 this->clear();
16479 this->classification_ = NC_RUNE;
16480 this->type_ = type;
16481 mpz_init_set(this->u_.int_val, val);
16482}
16483
16484// Set to a floating point value.
16485
16486void
16487Numeric_constant::set_float(Type* type, const mpfr_t val)
16488{
16489 this->clear();
16490 this->classification_ = NC_FLOAT;
16491 this->type_ = type;
d1d4ace3 16492
833b523c 16493 // Numeric constants do not have negative zero values, so remove
16494 // them here. They also don't have infinity or NaN values, but we
16495 // should never see them here.
d1d4ace3 16496 int bits = 0;
16497 if (type != NULL
16498 && type->float_type() != NULL
16499 && !type->float_type()->is_abstract())
16500 bits = type->float_type()->bits();
16501 if (Numeric_constant::is_float_neg_zero(val, bits))
833b523c 16502 mpfr_init_set_ui(this->u_.float_val, 0, GMP_RNDN);
16503 else
16504 mpfr_init_set(this->u_.float_val, val, GMP_RNDN);
0c77715b 16505}
16506
16507// Set to a complex value.
16508
16509void
fcbea5e4 16510Numeric_constant::set_complex(Type* type, const mpc_t val)
0c77715b 16511{
16512 this->clear();
16513 this->classification_ = NC_COMPLEX;
16514 this->type_ = type;
d1d4ace3 16515
16516 // Avoid negative zero as in set_float.
16517 int bits = 0;
16518 if (type != NULL
16519 && type->complex_type() != NULL
16520 && !type->complex_type()->is_abstract())
16521 bits = type->complex_type()->bits() / 2;
16522
16523 mpfr_t real;
16524 mpfr_init_set(real, mpc_realref(val), GMP_RNDN);
16525 if (Numeric_constant::is_float_neg_zero(real, bits))
16526 mpfr_set_ui(real, 0, GMP_RNDN);
16527
16528 mpfr_t imag;
16529 mpfr_init_set(imag, mpc_imagref(val), GMP_RNDN);
16530 if (Numeric_constant::is_float_neg_zero(imag, bits))
16531 mpfr_set_ui(imag, 0, GMP_RNDN);
16532
fcbea5e4 16533 mpc_init2(this->u_.complex_val, mpc_precision);
d1d4ace3 16534 mpc_set_fr_fr(this->u_.complex_val, real, imag, MPC_RNDNN);
16535
16536 mpfr_clear(real);
16537 mpfr_clear(imag);
16538}
16539
16540// Return whether VAL, at a precision of BITS, is a negative zero.
16541// BITS may be zero in which case it is ignored.
16542
16543bool
16544Numeric_constant::is_float_neg_zero(const mpfr_t val, int bits)
16545{
16546 if (!mpfr_signbit(val))
16547 return false;
16548 if (mpfr_zero_p(val))
16549 return true;
16550 mp_exp_t min_exp;
16551 switch (bits)
16552 {
16553 case 0:
16554 return false;
16555 case 32:
16556 // In a denormalized float32 the exponent is -126, and there are
16557 // 24 bits of which at least the last must be 1, so the smallest
16558 // representable non-zero exponent is -126 - (24 - 1) == -149.
16559 min_exp = -149;
16560 break;
16561 case 64:
16562 // Minimum exponent is -1022, there are 53 bits.
16563 min_exp = -1074;
16564 break;
16565 default:
16566 go_unreachable();
16567 }
16568 return mpfr_get_exp(val) < min_exp;
0c77715b 16569}
16570
16571// Get an int value.
16572
16573void
16574Numeric_constant::get_int(mpz_t* val) const
16575{
16576 go_assert(this->is_int());
16577 mpz_init_set(*val, this->u_.int_val);
16578}
16579
16580// Get a rune value.
16581
16582void
16583Numeric_constant::get_rune(mpz_t* val) const
16584{
16585 go_assert(this->is_rune());
16586 mpz_init_set(*val, this->u_.int_val);
16587}
16588
16589// Get a floating point value.
16590
16591void
16592Numeric_constant::get_float(mpfr_t* val) const
16593{
16594 go_assert(this->is_float());
16595 mpfr_init_set(*val, this->u_.float_val, GMP_RNDN);
16596}
16597
16598// Get a complex value.
16599
16600void
fcbea5e4 16601Numeric_constant::get_complex(mpc_t* val) const
0c77715b 16602{
16603 go_assert(this->is_complex());
fcbea5e4 16604 mpc_init2(*val, mpc_precision);
16605 mpc_set(*val, this->u_.complex_val, MPC_RNDNN);
0c77715b 16606}
16607
16608// Express value as unsigned long if possible.
16609
16610Numeric_constant::To_unsigned_long
16611Numeric_constant::to_unsigned_long(unsigned long* val) const
16612{
16613 switch (this->classification_)
16614 {
16615 case NC_INT:
16616 case NC_RUNE:
16617 return this->mpz_to_unsigned_long(this->u_.int_val, val);
16618 case NC_FLOAT:
16619 return this->mpfr_to_unsigned_long(this->u_.float_val, val);
16620 case NC_COMPLEX:
fcbea5e4 16621 if (!mpfr_zero_p(mpc_imagref(this->u_.complex_val)))
0c77715b 16622 return NC_UL_NOTINT;
fcbea5e4 16623 return this->mpfr_to_unsigned_long(mpc_realref(this->u_.complex_val),
16624 val);
0c77715b 16625 default:
16626 go_unreachable();
16627 }
16628}
16629
16630// Express integer value as unsigned long if possible.
16631
16632Numeric_constant::To_unsigned_long
16633Numeric_constant::mpz_to_unsigned_long(const mpz_t ival,
16634 unsigned long *val) const
16635{
16636 if (mpz_sgn(ival) < 0)
16637 return NC_UL_NEGATIVE;
16638 unsigned long ui = mpz_get_ui(ival);
16639 if (mpz_cmp_ui(ival, ui) != 0)
16640 return NC_UL_BIG;
16641 *val = ui;
16642 return NC_UL_VALID;
16643}
16644
16645// Express floating point value as unsigned long if possible.
16646
16647Numeric_constant::To_unsigned_long
16648Numeric_constant::mpfr_to_unsigned_long(const mpfr_t fval,
16649 unsigned long *val) const
16650{
16651 if (!mpfr_integer_p(fval))
16652 return NC_UL_NOTINT;
16653 mpz_t ival;
16654 mpz_init(ival);
16655 mpfr_get_z(ival, fval, GMP_RNDN);
16656 To_unsigned_long ret = this->mpz_to_unsigned_long(ival, val);
16657 mpz_clear(ival);
16658 return ret;
16659}
16660
03118c21 16661// Express value as memory size if possible.
16662
16663bool
16664Numeric_constant::to_memory_size(int64_t* val) const
16665{
16666 switch (this->classification_)
16667 {
16668 case NC_INT:
16669 case NC_RUNE:
16670 return this->mpz_to_memory_size(this->u_.int_val, val);
16671 case NC_FLOAT:
16672 return this->mpfr_to_memory_size(this->u_.float_val, val);
16673 case NC_COMPLEX:
16674 if (!mpfr_zero_p(mpc_imagref(this->u_.complex_val)))
16675 return false;
16676 return this->mpfr_to_memory_size(mpc_realref(this->u_.complex_val), val);
16677 default:
16678 go_unreachable();
16679 }
16680}
16681
16682// Express integer as memory size if possible.
16683
16684bool
16685Numeric_constant::mpz_to_memory_size(const mpz_t ival, int64_t* val) const
16686{
16687 if (mpz_sgn(ival) < 0)
16688 return false;
16689 if (mpz_fits_slong_p(ival))
16690 {
16691 *val = static_cast<int64_t>(mpz_get_si(ival));
16692 return true;
16693 }
16694
16695 // Test >= 64, not > 64, because an int64_t can hold 63 bits of a
16696 // positive value.
16697 if (mpz_sizeinbase(ival, 2) >= 64)
16698 return false;
16699
16700 mpz_t q, r;
16701 mpz_init(q);
16702 mpz_init(r);
16703 mpz_tdiv_q_2exp(q, ival, 32);
16704 mpz_tdiv_r_2exp(r, ival, 32);
16705 go_assert(mpz_fits_ulong_p(q) && mpz_fits_ulong_p(r));
16706 *val = ((static_cast<int64_t>(mpz_get_ui(q)) << 32)
16707 + static_cast<int64_t>(mpz_get_ui(r)));
16708 mpz_clear(r);
16709 mpz_clear(q);
16710 return true;
16711}
16712
16713// Express floating point value as memory size if possible.
16714
16715bool
16716Numeric_constant::mpfr_to_memory_size(const mpfr_t fval, int64_t* val) const
16717{
16718 if (!mpfr_integer_p(fval))
16719 return false;
16720 mpz_t ival;
16721 mpz_init(ival);
16722 mpfr_get_z(ival, fval, GMP_RNDN);
16723 bool ret = this->mpz_to_memory_size(ival, val);
16724 mpz_clear(ival);
16725 return ret;
16726}
16727
0c77715b 16728// Convert value to integer if possible.
16729
16730bool
16731Numeric_constant::to_int(mpz_t* val) const
16732{
16733 switch (this->classification_)
16734 {
16735 case NC_INT:
16736 case NC_RUNE:
16737 mpz_init_set(*val, this->u_.int_val);
16738 return true;
16739 case NC_FLOAT:
16740 if (!mpfr_integer_p(this->u_.float_val))
16741 return false;
16742 mpz_init(*val);
16743 mpfr_get_z(*val, this->u_.float_val, GMP_RNDN);
16744 return true;
16745 case NC_COMPLEX:
fcbea5e4 16746 if (!mpfr_zero_p(mpc_imagref(this->u_.complex_val))
16747 || !mpfr_integer_p(mpc_realref(this->u_.complex_val)))
0c77715b 16748 return false;
16749 mpz_init(*val);
fcbea5e4 16750 mpfr_get_z(*val, mpc_realref(this->u_.complex_val), GMP_RNDN);
0c77715b 16751 return true;
16752 default:
16753 go_unreachable();
16754 }
16755}
16756
16757// Convert value to floating point if possible.
16758
16759bool
16760Numeric_constant::to_float(mpfr_t* val) const
16761{
16762 switch (this->classification_)
16763 {
16764 case NC_INT:
16765 case NC_RUNE:
16766 mpfr_init_set_z(*val, this->u_.int_val, GMP_RNDN);
16767 return true;
16768 case NC_FLOAT:
16769 mpfr_init_set(*val, this->u_.float_val, GMP_RNDN);
16770 return true;
16771 case NC_COMPLEX:
fcbea5e4 16772 if (!mpfr_zero_p(mpc_imagref(this->u_.complex_val)))
0c77715b 16773 return false;
fcbea5e4 16774 mpfr_init_set(*val, mpc_realref(this->u_.complex_val), GMP_RNDN);
0c77715b 16775 return true;
16776 default:
16777 go_unreachable();
16778 }
16779}
16780
16781// Convert value to complex.
16782
16783bool
fcbea5e4 16784Numeric_constant::to_complex(mpc_t* val) const
0c77715b 16785{
fcbea5e4 16786 mpc_init2(*val, mpc_precision);
0c77715b 16787 switch (this->classification_)
16788 {
16789 case NC_INT:
16790 case NC_RUNE:
fcbea5e4 16791 mpc_set_z(*val, this->u_.int_val, MPC_RNDNN);
0c77715b 16792 return true;
16793 case NC_FLOAT:
fcbea5e4 16794 mpc_set_fr(*val, this->u_.float_val, MPC_RNDNN);
0c77715b 16795 return true;
16796 case NC_COMPLEX:
fcbea5e4 16797 mpc_set(*val, this->u_.complex_val, MPC_RNDNN);
0c77715b 16798 return true;
16799 default:
16800 go_unreachable();
16801 }
16802}
16803
16804// Get the type.
16805
16806Type*
16807Numeric_constant::type() const
16808{
16809 if (this->type_ != NULL)
16810 return this->type_;
16811 switch (this->classification_)
16812 {
16813 case NC_INT:
16814 return Type::make_abstract_integer_type();
16815 case NC_RUNE:
16816 return Type::make_abstract_character_type();
16817 case NC_FLOAT:
16818 return Type::make_abstract_float_type();
16819 case NC_COMPLEX:
16820 return Type::make_abstract_complex_type();
16821 default:
16822 go_unreachable();
16823 }
16824}
16825
16826// If the constant can be expressed in TYPE, then set the type of the
16827// constant to TYPE and return true. Otherwise return false, and, if
16828// ISSUE_ERROR is true, report an appropriate error message.
16829
16830bool
16831Numeric_constant::set_type(Type* type, bool issue_error, Location loc)
16832{
16833 bool ret;
f11c2155 16834 if (type == NULL || type->is_error())
0c77715b 16835 ret = true;
16836 else if (type->integer_type() != NULL)
16837 ret = this->check_int_type(type->integer_type(), issue_error, loc);
16838 else if (type->float_type() != NULL)
16839 ret = this->check_float_type(type->float_type(), issue_error, loc);
16840 else if (type->complex_type() != NULL)
16841 ret = this->check_complex_type(type->complex_type(), issue_error, loc);
16842 else
5706ab68 16843 {
16844 ret = false;
16845 if (issue_error)
16846 go_assert(saw_errors());
16847 }
0c77715b 16848 if (ret)
16849 this->type_ = type;
16850 return ret;
16851}
16852
16853// Check whether the constant can be expressed in an integer type.
16854
16855bool
16856Numeric_constant::check_int_type(Integer_type* type, bool issue_error,
71a45216 16857 Location location)
0c77715b 16858{
16859 mpz_t val;
16860 switch (this->classification_)
16861 {
16862 case NC_INT:
16863 case NC_RUNE:
16864 mpz_init_set(val, this->u_.int_val);
16865 break;
16866
16867 case NC_FLOAT:
16868 if (!mpfr_integer_p(this->u_.float_val))
16869 {
16870 if (issue_error)
71a45216 16871 {
631d5788 16872 go_error_at(location,
16873 "floating point constant truncated to integer");
71a45216 16874 this->set_invalid();
16875 }
0c77715b 16876 return false;
16877 }
16878 mpz_init(val);
16879 mpfr_get_z(val, this->u_.float_val, GMP_RNDN);
16880 break;
16881
16882 case NC_COMPLEX:
fcbea5e4 16883 if (!mpfr_integer_p(mpc_realref(this->u_.complex_val))
16884 || !mpfr_zero_p(mpc_imagref(this->u_.complex_val)))
0c77715b 16885 {
16886 if (issue_error)
71a45216 16887 {
631d5788 16888 go_error_at(location, "complex constant truncated to integer");
71a45216 16889 this->set_invalid();
16890 }
0c77715b 16891 return false;
16892 }
16893 mpz_init(val);
fcbea5e4 16894 mpfr_get_z(val, mpc_realref(this->u_.complex_val), GMP_RNDN);
0c77715b 16895 break;
16896
16897 default:
16898 go_unreachable();
16899 }
16900
16901 bool ret;
16902 if (type->is_abstract())
16903 ret = true;
16904 else
16905 {
16906 int bits = mpz_sizeinbase(val, 2);
16907 if (type->is_unsigned())
16908 {
16909 // For an unsigned type we can only accept a nonnegative
16910 // number, and we must be able to represents at least BITS.
16911 ret = mpz_sgn(val) >= 0 && bits <= type->bits();
16912 }
16913 else
16914 {
16915 // For a signed type we need an extra bit to indicate the
16916 // sign. We have to handle the most negative integer
16917 // specially.
16918 ret = (bits + 1 <= type->bits()
16919 || (bits <= type->bits()
16920 && mpz_sgn(val) < 0
16921 && (mpz_scan1(val, 0)
16922 == static_cast<unsigned long>(type->bits() - 1))
16923 && mpz_scan0(val, type->bits()) == ULONG_MAX));
16924 }
16925 }
16926
16927 if (!ret && issue_error)
71a45216 16928 {
631d5788 16929 go_error_at(location, "integer constant overflow");
71a45216 16930 this->set_invalid();
16931 }
0c77715b 16932
16933 return ret;
16934}
16935
16936// Check whether the constant can be expressed in a floating point
16937// type.
16938
16939bool
16940Numeric_constant::check_float_type(Float_type* type, bool issue_error,
d0bcce51 16941 Location location)
0c77715b 16942{
16943 mpfr_t val;
16944 switch (this->classification_)
16945 {
16946 case NC_INT:
16947 case NC_RUNE:
16948 mpfr_init_set_z(val, this->u_.int_val, GMP_RNDN);
16949 break;
16950
16951 case NC_FLOAT:
16952 mpfr_init_set(val, this->u_.float_val, GMP_RNDN);
16953 break;
16954
16955 case NC_COMPLEX:
fcbea5e4 16956 if (!mpfr_zero_p(mpc_imagref(this->u_.complex_val)))
0c77715b 16957 {
16958 if (issue_error)
71a45216 16959 {
16960 this->set_invalid();
631d5788 16961 go_error_at(location, "complex constant truncated to float");
71a45216 16962 }
0c77715b 16963 return false;
16964 }
fcbea5e4 16965 mpfr_init_set(val, mpc_realref(this->u_.complex_val), GMP_RNDN);
0c77715b 16966 break;
16967
16968 default:
16969 go_unreachable();
16970 }
16971
16972 bool ret;
16973 if (type->is_abstract())
16974 ret = true;
16975 else if (mpfr_nan_p(val) || mpfr_inf_p(val) || mpfr_zero_p(val))
16976 {
16977 // A NaN or Infinity always fits in the range of the type.
16978 ret = true;
16979 }
16980 else
16981 {
16982 mp_exp_t exp = mpfr_get_exp(val);
16983 mp_exp_t max_exp;
16984 switch (type->bits())
16985 {
16986 case 32:
16987 max_exp = 128;
16988 break;
16989 case 64:
16990 max_exp = 1024;
16991 break;
16992 default:
16993 go_unreachable();
16994 }
16995
16996 ret = exp <= max_exp;
d0bcce51 16997
16998 if (ret)
16999 {
17000 // Round the constant to the desired type.
17001 mpfr_t t;
17002 mpfr_init(t);
17003 switch (type->bits())
17004 {
17005 case 32:
17006 mpfr_set_prec(t, 24);
17007 break;
17008 case 64:
17009 mpfr_set_prec(t, 53);
17010 break;
17011 default:
17012 go_unreachable();
17013 }
17014 mpfr_set(t, val, GMP_RNDN);
17015 mpfr_set(val, t, GMP_RNDN);
17016 mpfr_clear(t);
17017
17018 this->set_float(type, val);
17019 }
0c77715b 17020 }
17021
17022 mpfr_clear(val);
17023
17024 if (!ret && issue_error)
71a45216 17025 {
631d5788 17026 go_error_at(location, "floating point constant overflow");
71a45216 17027 this->set_invalid();
17028 }
0c77715b 17029
17030 return ret;
17031}
17032
17033// Check whether the constant can be expressed in a complex type.
17034
17035bool
17036Numeric_constant::check_complex_type(Complex_type* type, bool issue_error,
d0bcce51 17037 Location location)
0c77715b 17038{
17039 if (type->is_abstract())
17040 return true;
17041
17042 mp_exp_t max_exp;
17043 switch (type->bits())
17044 {
17045 case 64:
17046 max_exp = 128;
17047 break;
17048 case 128:
17049 max_exp = 1024;
17050 break;
17051 default:
17052 go_unreachable();
17053 }
17054
fcbea5e4 17055 mpc_t val;
17056 mpc_init2(val, mpc_precision);
0c77715b 17057 switch (this->classification_)
17058 {
17059 case NC_INT:
17060 case NC_RUNE:
fcbea5e4 17061 mpc_set_z(val, this->u_.int_val, MPC_RNDNN);
0c77715b 17062 break;
17063
17064 case NC_FLOAT:
fcbea5e4 17065 mpc_set_fr(val, this->u_.float_val, MPC_RNDNN);
0c77715b 17066 break;
17067
17068 case NC_COMPLEX:
fcbea5e4 17069 mpc_set(val, this->u_.complex_val, MPC_RNDNN);
0c77715b 17070 break;
17071
17072 default:
17073 go_unreachable();
17074 }
17075
d0bcce51 17076 bool ret = true;
fcbea5e4 17077 if (!mpfr_nan_p(mpc_realref(val))
17078 && !mpfr_inf_p(mpc_realref(val))
17079 && !mpfr_zero_p(mpc_realref(val))
17080 && mpfr_get_exp(mpc_realref(val)) > max_exp)
d0bcce51 17081 {
17082 if (issue_error)
71a45216 17083 {
631d5788 17084 go_error_at(location, "complex real part overflow");
71a45216 17085 this->set_invalid();
17086 }
d0bcce51 17087 ret = false;
17088 }
0c77715b 17089
fcbea5e4 17090 if (!mpfr_nan_p(mpc_imagref(val))
17091 && !mpfr_inf_p(mpc_imagref(val))
17092 && !mpfr_zero_p(mpc_imagref(val))
17093 && mpfr_get_exp(mpc_imagref(val)) > max_exp)
d0bcce51 17094 {
17095 if (issue_error)
71a45216 17096 {
631d5788 17097 go_error_at(location, "complex imaginary part overflow");
71a45216 17098 this->set_invalid();
17099 }
d0bcce51 17100 ret = false;
17101 }
0c77715b 17102
d0bcce51 17103 if (ret)
17104 {
17105 // Round the constant to the desired type.
fcbea5e4 17106 mpc_t t;
d0bcce51 17107 switch (type->bits())
17108 {
17109 case 64:
fcbea5e4 17110 mpc_init2(t, 24);
d0bcce51 17111 break;
17112 case 128:
fcbea5e4 17113 mpc_init2(t, 53);
d0bcce51 17114 break;
17115 default:
17116 go_unreachable();
17117 }
fcbea5e4 17118 mpc_set(t, val, MPC_RNDNN);
17119 mpc_set(val, t, MPC_RNDNN);
17120 mpc_clear(t);
d0bcce51 17121
fcbea5e4 17122 this->set_complex(type, val);
d0bcce51 17123 }
17124
fcbea5e4 17125 mpc_clear(val);
0c77715b 17126
17127 return ret;
17128}
17129
17130// Return an Expression for this value.
17131
17132Expression*
17133Numeric_constant::expression(Location loc) const
17134{
17135 switch (this->classification_)
17136 {
17137 case NC_INT:
e67508fa 17138 return Expression::make_integer_z(&this->u_.int_val, this->type_, loc);
0c77715b 17139 case NC_RUNE:
17140 return Expression::make_character(&this->u_.int_val, this->type_, loc);
17141 case NC_FLOAT:
17142 return Expression::make_float(&this->u_.float_val, this->type_, loc);
17143 case NC_COMPLEX:
fcbea5e4 17144 return Expression::make_complex(&this->u_.complex_val, this->type_, loc);
71a45216 17145 case NC_INVALID:
17146 go_assert(saw_errors());
17147 return Expression::make_error(loc);
0c77715b 17148 default:
17149 go_unreachable();
17150 }
17151}