diff -r 39206a734718 sys/src/cmd/8c/txt.c --- a/sys/src/cmd/8c/txt.c Sat Aug 01 10:54:03 2020 -0700 +++ b/sys/src/cmd/8c/txt.c Sat Aug 01 13:59:38 2020 -0700 @@ -865,7 +865,7 @@ gmove(f, &fregnode0); gins(AFADDD, nodfconst(-2147483648.), &fregnode0); gins(AFMOVLP, f, &nod); - gins(ASUBL, nodconst(-2147483648), &nod); + gins(ASUBL, nodconst(-0x80000000), &nod); gmove(&nod, t); return; diff -r 39206a734718 sys/src/cmd/cc/lex.c --- a/sys/src/cmd/cc/lex.c Sat Aug 01 10:54:03 2020 -0700 +++ b/sys/src/cmd/cc/lex.c Sat Aug 01 13:59:38 2020 -0700 @@ -444,7 +444,7 @@ yylex(void) { vlong vv; - long c, c1, t; + long c, c1, t, w; char *cp; Rune rune; Sym *s; @@ -844,7 +844,22 @@ yyerror("overflow in constant"); vv = yylval.vval; - if(c1 & Numvlong) { + /* + * Implicit widening: if we have no type suffix, and we've + * overflowed the constant, we widen. C99 requires hex and + * octal constants widen to an unsigned type, and then to + * the next signed type that fits. Decimal constants go + * directly to signed. Do not pass go, do not collect 200 + * dollars. + * + * This is silly, but we do it anyways. + */ + w = 32; + if((c1 & (Numdec|Numuns)) == Numdec) + w = 31; + if(c1 & Numvlong || (c1 & Numlong) == 0 && (uvlong)vv >= 1ULL<