ref: 242c473f7221643384498dd67ee2717f31482ffd
parent: 94fd29519bd9650953b1f9b67ae62c628678297d
author: Roberto E. Vargas Caballero <[email protected]>
date: Thu May 31 17:55:36 EDT 2012
Added support for qualifiers in pointer types
--- a/decl.c
+++ b/decl.c
@@ -198,32 +198,43 @@
void decl(void)
{
- unsigned char ns = 0;
- unsigned char qlf[PTRLEVEL_MAX];
+ unsigned char qlf[PTRLEVEL_MAX], *bp, *lim;
puts("decl");
- for (ns = 0; yytoken == '*'; ns++) {
- if (ns == PTRLEVEL_MAX)
- error("Too much indirection levels");
+ lim = qlf + PTRLEVEL_MAX;
+ for (bp = qlf; yytoken == '*' && bp != lim; ++bp) {
+ *bp = 0;
+ repeat_qlf:
switch (gettok()) {
case CONST:
- if (!(qlf[ns] ^= 2))
+ if (!(*bp ^= 1))
goto duplicated;
- continue;
+ goto repeat_qlf;
case RESTRICTED:
- if (!(qlf[ns] ^= 4))
+ if (!(*bp ^= 2))
goto duplicated;
- continue;
+ goto repeat_qlf;
case VOLATILE:
- if (!(qlf[ns] ^= 8))
+ if (!(*bp ^= 4))
goto duplicated;
- continue;
+ goto repeat_qlf;
+ default:
+ break;
}
}
+
+ if (bp == lim)
+ error("Too much indirection levels");
+
dirdcl();
- if (ns)
- push(PTR); /* TODO: pointer qualifiers */
+ while (bp-- != qlf) {
+ if (*bp & 1) push(CONST);
+ if (*bp & 2) push(RESTRICTED);
+ if (*bp & 4) push(VOLATILE);
+ push(PTR);
+ }
+
printf("leaving dcl %c\n", yytoken);
return;
--- a/types.c
+++ b/types.c
@@ -26,7 +26,8 @@
struct type *mktype(register struct type *base, unsigned char op)
{
register struct type **ptr, *nt;
- assert(op == PTR || op == ARY || op == FTN);
+ assert(op == PTR || op == ARY || op == FTN ||
+ op == VOLATILE || op == RESTRICTED || op == CONST);
switch (op) {
case PTR:
@@ -38,6 +39,15 @@
case FTN:
ptr = &base->ftn;
break;
+ case VOLATILE:
+ ptr = &base->vltl;
+ break;
+ case RESTRICTED:
+ ptr = &base->rstr;
+ break;
+ case CONST:
+ ptr = &base->cnst;
+ break;
}
if (*ptr) return *ptr;
@@ -68,6 +78,16 @@
break;
case FTN:
fputs("function that returns ", stdout);
+ break;
+ case VOLATILE:
+ fputs("volatile ", stdout);
+ break;
+ break;
+ case RESTRICTED:
+ fputs("restricted ", stdout);
+ break;
+ case CONST:
+ fputs("const ", stdout);
break;
default: {
static char *type, *sign;
--- a/types.h
+++ b/types.h
@@ -3,11 +3,15 @@
struct type {
- unsigned char op;
+ unsigned op : 5;
struct type *base;
- struct type *ary; /* array */
- struct type *ptr; /* pointer */
- struct type *ftn; /* function */
+ struct type *ary; /* array */
+ struct type *ptr; /* pointer */
+ struct type *ftn; /* function */
+ struct type *cnst; /* const */
+ struct type *vltl; /* volatile */
+ struct type *rstr; /* restricted */
+
union {
struct {
unsigned btype : 4;
@@ -37,13 +41,12 @@
#define T_ULLONG (&tullong)
#define T_VOID (&tvoid)
+#define ARY 1
+#define PTR 2
+#define FTN 3
-#define ARY 1
-#define PTR 2
-#define FTN 3
-#define T_CONST 8
-#define T_RESTRICTED 16
-#define T_VOLATILE 32
+#define QLF(x) (VOLATILE - x + 1)
+
struct type *mktype(register struct type *base, unsigned char op);