1
0
mirror of https://github.com/golang/go synced 2024-11-23 23:00:03 -07:00

go/types: check that typed constant shift expressions are representable

Fixes #12945.

Change-Id: I08b44795fcd7ec59371aea8111f7febead54720b
Reviewed-on: https://go-review.googlesource.com/15900
Reviewed-by: Robert Griesemer <gri@golang.org>
This commit is contained in:
Matthew Dempsky 2015-10-15 09:50:40 -07:00 committed by Robert Griesemer
parent e920f7d5c5
commit e538e1b627
2 changed files with 18 additions and 2 deletions

View File

@ -618,7 +618,7 @@ func (check *Checker) comparison(x, y *operand, op token.Token) {
x.typ = Typ[UntypedBool]
}
func (check *Checker) shift(x, y *operand, op token.Token) {
func (check *Checker) shift(x, y *operand, e *ast.BinaryExpr, op token.Token) {
untypedx := isUntyped(x.typ)
// The lhs must be of integer type or be representable
@ -671,6 +671,14 @@ func (check *Checker) shift(x, y *operand, op token.Token) {
x.typ = Typ[UntypedInt]
}
x.val = constant.Shift(x.val, op, uint(s))
// Typed constants must be representable in
// their type after each constant operation.
if isTyped(x.typ) {
if e != nil {
x.expr = e // for better error message
}
check.representable(x, x.typ.Underlying().(*Basic))
}
return
}
@ -753,7 +761,7 @@ func (check *Checker) binary(x *operand, e *ast.BinaryExpr, lhs, rhs ast.Expr, o
}
if isShift(op) {
check.shift(x, &y, op)
check.shift(x, &y, e, op)
return
}

View File

@ -312,3 +312,11 @@ const (
y64 = float64(f64)
_ = assert(x64 - y64 == 0)
)
const (
_ = int8(-1) << 7
_ = int8 /* ERROR "overflows" */ (-1) << 8
_ = uint32(1) << 31
_ = uint32 /* ERROR "overflows" */ (1) << 32
)