]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/asm: fix shifts again, this time for sure
authorRob Pike <r@golang.org>
Mon, 22 Jun 2015 22:40:40 +0000 (08:40 +1000)
committerRob Pike <r@golang.org>
Tue, 23 Jun 2015 06:44:54 +0000 (06:44 +0000)
There are two conditions to worry about:

1) The shift count cannot be negative. Since the evaluator uses unsigned
arithmetic throughout, this means checking that the high bit of
the shift count is always off, which is done by converting to int64
and seeing if the result is negative.

2) For right shifts, the value cannot be negative. We don't want a
high bit in the value because right shifting a value depends on the
sign, and for clarity we always want unsigned shifts.

Next step is to build some testing infrastructure for the parser.

Change-Id: I4c46c79989d02c107fc64954403fc18613763f1d
Reviewed-on: https://go-review.googlesource.com/11326
Reviewed-by: Russ Cox <rsc@golang.org>
src/cmd/asm/internal/asm/parse.go

index 18cc27fa83b4d90f8ad11b283ef24a8f37d77586..2533256f88210983b3f723f565cb97f9441c5ec8 100644 (file)
@@ -797,8 +797,8 @@ func (p *Parser) term() uint64 {
                        value *= p.factor()
                case '/':
                        p.next()
-                       if value&(1<<63) != 0 {
-                               p.errorf("divide with high bit set")
+                       if int64(value) < 0 {
+                               p.errorf("divide of value with high bit set")
                        }
                        value /= p.factor()
                case '%':
@@ -808,14 +808,17 @@ func (p *Parser) term() uint64 {
                        p.next()
                        shift := p.factor()
                        if int64(shift) < 0 {
-                               p.errorf("left shift with high bit set")
+                               p.errorf("negative left shift count")
                        }
                        return value << shift
                case lex.RSH:
                        p.next()
                        shift := p.term()
                        if int64(shift) < 0 {
-                               p.errorf("right shift with high bit set")
+                               p.errorf("negative right shift count")
+                       }
+                       if int64(value) < 0 {
+                               p.errorf("right shift of value with high bit set")
                        }
                        value >>= shift
                case '&':