ref: 10faf603cace3ffda21153466dfbd9e672bcf656
parent: a48a176171b40b974a7c5a284c2356d26ffdf7ad
author: Roberto E. Vargas Caballero <k0ga@shike2.com>
date: Mon Sep 7 07:37:24 EDT 2015
Fix interger constants size These constant were incorrectly emitted, because the size of the target type was ignored, so negative number generated different quantities. There were also another problem related to the fact that comparisions were always done in the host type, that may be bigger than the target type..
--- a/cc1/cc1.h
+++ b/cc1/cc1.h
@@ -363,6 +363,7 @@
/* fold.c */
extern Node *simplify(int op, Type *tp, Node *lp, Node *rp);
extern Node *castcode(Node *np, Type *newtp);
+extern TUINT ones(int nbytes);
/* expr.c */
extern Node *expr(void), *negate(Node *np), *constexpr(void);
--- a/cc1/code.c
+++ b/cc1/code.c
@@ -192,7 +192,7 @@
case PTR:
case INT:
u = (tp->sign) ? (TUINT) sym->u.i : sym->u.u;
- printf("#%c%lX", np->type->letter, sym->u.i);
+ printf("#%c%lX", np->type->letter, sym->u.i & ones(tp->size));
break;
case ARY:
/*
--- a/cc1/expr.c
+++ b/cc1/expr.c
@@ -14,6 +14,7 @@
{
Symbol *sym;
Type *tp;
+ TUINT mask, nodeval;
if (!np || !np->constant)
return 0;
@@ -23,7 +24,9 @@
switch (tp->op) {
case PTR:
case INT:
- return ((tp->sign) ? sym->u.i : sym->u.u) == val;
+ mask = (val > 1) ? ones(np->type->size) : -1;
+ nodeval = (tp->sign) ? sym->u.i : sym->u.u;
+ return (nodeval & mask) == (val & mask);
case FLOAT:
return sym->u.f == val;
}
--- a/cc1/fold.c
+++ b/cc1/fold.c
@@ -4,6 +4,19 @@
#include "../inc/cc.h"
#include "cc1.h"
+
+/* TODO: Add ENUM in the cases */
+
+TUINT
+ones(int nbytes)
+{
+ TUINT v;
+
+ for (v = 0; nbytes--; v |= 255)
+ v <<= 8;
+ return v;
+}
+
static bool
addi(TINT l, TINT r, Type *tp)
{
@@ -135,16 +148,6 @@
return 1;
}
-static TUINT
-ones(int n)
-{
- TUINT v;
-
- for (v = 1; n--; v |= 1)
- v <<= 1;
- return v;
-}
-
static bool
foldint(int op, Symbol *res, TINT l, TINT r)
{
@@ -462,7 +465,7 @@
return NULL;
case OBAND:
/* i & ~0 => i */
- if (cmpnode(rp, ~0))
+ if (cmpnode(rp, -1))
goto free_right;
return NULL;
case OMOD:
--- a/cc1/tests/test019.c
+++ b/cc1/tests/test019.c
@@ -22,8 +22,8 @@
A2 #I4 :I
A2 #IC :I
A2 #I8 :I
- A2 #IFFFFFFFD :I
- A2 #IFFFFFFF3 :I
+ A2 #IFFFD :I
+ A2 #IFFF3 :I
A2 #I1 :I
A2 #I0 :I
A2 #I0 :I