static void doinclude(State *s, char *p) { File *f; int sysinc; char term, *q, *path; if(peek(s) & (Tdisable|Tinherit)) return; switch(*p){ case '"': p++; term = '"'; break; case '<': p++; term = '>'; break; default: cpperr(s, "%c - bad filename quote character\n", *p); return; } if((q = strchr(p, term)) == nil){ cpperr(s, "%s - unterminated filename\n", p); return; } *q = 0; if((path = findinc(p, term, s->langincdirs, &sysinc)) == nil){ if(Autoconf && strcmp(p, "config.h") != 0) cpperr(s, "%q - include file not found\n", p); } if(path == nil) path = estrdup(p); f = addfile(path, sysinc); f->ref++; free(path); scanfile(s->dep, f, s->file, s->line); }
static void dopragma(State *s, char *p) { int l; char *q, *t, *path, *m; static char *lib = "lib"; l = strlen(lib); if(strncmp(p, "lib", l) != 0) return; p += l; while(isspace(*p)) p++; if(*p++ != '"') cpperr(s, "#pragma lib - \" not found\n"); if((q = strrchr(p, '"')) == nil) cpperr(s, "#pragma lib - \" unmatched\n"); *q = 0; path = expand(p); if(addlist(&Pragmalib, path) == 1) parse_ar(path); free(path); }
static void doendif(State *s, char *) { switch(pop(s)){ case Tlost: case Tlost|Tinherit: cpperr(s, "#endif - not in a conditional clause\n"); break; } }
static void push(State *s, int state) { if(s->sp >= Ifstack){ cpperr(s, "#ifdef stack overflow\n"); return; } if(state == Tdisable) state = Tdisable|Tinherit; s->stk[s->sp++] = state | (peek(s) & Tinherit); }
static void doelse(State *s, char *) { switch(pop(s)){ case Tenable: case Tenable|Tinherit: push(s, Tdisable); break; case Tdisable: case Tdisable|Tinherit: push(s, Tenable); break; case Tlost: cpperr(s, "#else - not in a conditional clause\n"); break; } }
static void dodefine(State *s, char *p) { int brace; Symb *sym; char *name, *val; if(peek(s) & (Tdisable|Tinherit)) return; if(! Name1(*p)) cpperr(s, "%q - bad character in macro name\n", p); name = p; while(NameN(*p)) p++; val = nil; if(*p == '('){ *p++ = 0; brace = 1; while(*p){ switch(*p++){ case '(': brace++; break; case ')': brace--; break; default: break; } if(brace == 0) break; } val = p; } if(isspace(*p)){ *p++ = 0; while(isspace(*p)) p++; val = p; } if(val == nil || ! *val) val = "1"; setsym(name, val); }
static void doelif(State *s, char *p) { if(peek(s) & (Tdisable|Tinherit)) return; switch(pop(s)){ case Tenable: case Tenable|Tinherit: push(s, Tdisable); return; case Tlost: cpperr(s, "#elif - not in a conditional clause\n"); return; } if(expr(s, p)) push(s, Tenable); else push(s, Tdisable); }
static void doifndef(State *s, char *p) { char *name; if(peek(s) & (Tdisable|Tinherit)){ push(s, Tdisable); return; } if(! Name1(*p)) cpperr(s, "%q - bad character in macro name\n", p); name = p; while(NameN(*p)) p++; *p = 0; if(looksym(name, s->langincdirs) == nil) push(s, Tenable); else push(s, Tdisable); }
static void doundef(State *s, char *p) { char *name; if(peek(s) & (Tdisable|Tinherit)) return; if(! Name1(*p)) cpperr(s, "%q - bad character in macro name\n", p); name = p; while(NameN(*p)) p++; *p = 0; /* * Ignore any error, it appears to be legal to #undef * a name which has never been #define'ed */ rmsym(name); }
STATIC void cpp_basic_data_type(type *t) { char c; int i; //printf("cpp_basic_data_type(t)\n"); //type_print(t); switch (tybasic(t->Tty)) { case TYschar: c = 'C'; goto dochar; case TYchar: c = 'D'; goto dochar; case TYuchar: c = 'E'; goto dochar; case TYshort: c = 'F'; goto dochar; case TYushort: c = 'G'; goto dochar; case TYint: c = 'H'; goto dochar; case TYuint: c = 'I'; goto dochar; case TYlong: c = 'J'; goto dochar; case TYulong: c = 'K'; goto dochar; case TYfloat: c = 'M'; goto dochar; case TYdouble: c = 'N'; goto dochar; case TYdouble_alias: if (intsize == 4) { c = 'O'; goto dochar; } c = 'Z'; goto dochar2; case TYldouble: if (intsize == 2) { c = 'O'; goto dochar; } c = 'Z'; goto dochar2; dochar: CHAR(c); break; case TYllong: c = 'J'; goto dochar2; case TYullong: c = 'K'; goto dochar2; case TYbool: c = 'N'; goto dochar2; // was 'X' prior to 8.1b8 case TYwchar_t: if (config.flags4 & CFG4nowchar_t) { c = 'G'; goto dochar; // same as TYushort } else { pstate.STflags |= PFLmfc; c = 'Y'; goto dochar2; } // Digital Mars extensions case TYifloat: c = 'R'; goto dochar2; case TYidouble: c = 'S'; goto dochar2; case TYildouble: c = 'T'; goto dochar2; case TYcfloat: c = 'U'; goto dochar2; case TYcdouble: c = 'V'; goto dochar2; case TYcldouble: c = 'W'; goto dochar2; case TYchar16: c = 'X'; goto dochar2; case TYdchar: c = 'Y'; goto dochar2; case TYnullptr: c = 'Z'; goto dochar2; dochar2: CHAR('_'); goto dochar; #if TARGET_SEGMENTED case TYsptr: case TYcptr: case TYf16ptr: case TYfptr: case TYhptr: case TYvptr: #endif #if !MARS case TYmemptr: #endif case TYnptr: c = 'P' + cpp_cvidx(t->Tty); CHAR(c); if(I64) CHAR('E'); // __ptr64 modifier cpp_pointer_type(t); break; case TYstruct: case TYenum: cpp_ecsu_data_type(t); break; case TYarray: i = cpp_cvidx(t->Tty); i |= 1; // always const CHAR('P' + i); cpp_pointer_type(t); break; case TYvoid: c = 'X'; goto dochar; #if !MARS case TYident: if (pstate.STintemplate) { CHAR('V'); // pretend to be a class name cpp_zname(t->Tident); } else { #if SCPP cpperr(EM_no_type,t->Tident); // no type for argument #endif c = 'X'; goto dochar; } break; case TYtemplate: if (pstate.STintemplate) { CHAR('V'); // pretend to be a class name cpp_zname(((typetemp_t *)t)->Tsym->Sident); } else goto Ldefault; break; #endif default: Ldefault: if (tyfunc(t->Tty)) cpp_function_type(t); else { #if SCPP #ifdef DEBUG if (!errcnt) type_print(t); #endif assert(errcnt); #endif } } }
char *cpp_operator2(token_t *to, int *pcastoverload) { int i; char *s; token_t *tn; int oper; *pcastoverload = 0; if (!to || !to->TKnext) return NULL; for (i = 0; i < arraysize(oparray); i++) { //printf("[%d] %d, %d\n", i, oparray[i].tokn, tok.TKval); if (oparray[i].tokn == to->TKval) goto L1; } //printf("cpp_operator2(): castoverload\n"); *pcastoverload = 1; return NULL; L1: tn = to->TKnext; s = oparray[i].string; oper = oparray[i].oper; switch (oper) { case OPcall: if (tn->TKval != TKrpar) synerr(EM_rpar); // ')' expected break; case OPbrack: if (tn->TKval != TKrbra) synerr(EM_rbra); // ']' expected break; case OPnew: if (tn->TKval != TKlbra) break; oper = OPanew; // operator new[] s = cpp_name_anew; goto L3; case OPdelete: if (tn->TKval != TKlbra) break; oper = OPadelete; // operator delete[] s = cpp_name_adelete; L3: if (tn->TKval != TKrbra) synerr(EM_rbra); // ']' expected if (!(config.flags4 & CFG4anew)) { cpperr(EM_enable_anew); // throw -Aa to support this config.flags4 |= CFG4anew; } break; } Lret: return s; }
char *cpp_operator(int *poper,type **pt) { int i; type *typ_spec; char *s; *pt = NULL; stoken(); /* skip over operator keyword */ for (i = 0; i < arraysize(oparray); i++) { if (oparray[i].tokn == tok.TKval) goto L1; } /* Look for type conversion */ if (type_specifier(&typ_spec)) { type *t; t = ptr_operator(typ_spec); // parse ptr-operator fixdeclar(t); type_free(typ_spec); *pt = t; return cpp_typetostring(t,"?B"); } cpperr(EM_not_overloadable); // that token cannot be overloaded s = "_"; goto L2; L1: s = oparray[i].string; *poper = oparray[i].oper; switch (*poper) { case OPcall: if (stoken() != TKrpar) synerr(EM_rpar); /* ')' expected */ break; case OPbrack: if (stoken() != TKrbra) synerr(EM_rbra); /* ']' expected */ break; case OPnew: if (stoken() != TKlbra) goto Lret; *poper = OPanew; // operator new[] s = cpp_name_anew; goto L3; case OPdelete: if (stoken() != TKlbra) goto Lret; *poper = OPadelete; // operator delete[] s = cpp_name_adelete; L3: if (stoken() != TKrbra) synerr(EM_rbra); // ']' expected if (!(config.flags4 & CFG4anew)) { cpperr(EM_enable_anew); // throw -Aa to support this config.flags4 |= CFG4anew; } break; } L2: stoken(); Lret: return s; }