parse.c (55181B)
1 /* parse.c — residual C11 parser core. 2 * 3 * Contains: 4 * - kw_names[] table (used by parse_c to intern keywords) 5 * - Diagnostics/token helpers (perr, advance, peek1, fetch_tok, ...) 6 * - Scope/tag operations 7 * - Type helpers (ty_int, ty_size_t) 8 * - Local-variable slot allocation (make_local, make_local_aligned) 9 * - Static-local symbol naming (mint_static_local_sym) 10 * - Declaration driver (parse_init_declarator, parse_local_decl) 11 * - TU-level driver (parse_param_list, declare_function, 12 * parse_function_body, parse_external_decl, parse_translation_unit, 13 * parse_c) 14 * 15 * All expression, type, initializer, and statement code lives in 16 * parse_expr.c, parse_type.c, parse_init.c, and parse_stmt.c. */ 17 18 #include <stdarg.h> 19 #include <string.h> 20 21 #include "parse/parse_priv.h" 22 23 /* ============================================================ 24 * Keywords 25 * ============================================================ */ 26 27 static const char* const kw_names[KW_COUNT] = { 28 NULL, 29 "auto", 30 "break", 31 "case", 32 "char", 33 "const", 34 "continue", 35 "default", 36 "do", 37 "double", 38 "else", 39 "enum", 40 "extern", 41 "float", 42 "_Float16", 43 "for", 44 "goto", 45 "if", 46 "inline", 47 "int", 48 "long", 49 "register", 50 "restrict", 51 "return", 52 "short", 53 "signed", 54 "sizeof", 55 "static", 56 "struct", 57 "switch", 58 "typedef", 59 "union", 60 "unsigned", 61 "void", 62 "volatile", 63 "while", 64 "_Bool", 65 "_Complex", 66 "_Imaginary", 67 "_Alignas", 68 "_Alignof", 69 "_Atomic", 70 "_Generic", 71 "_Noreturn", 72 "_Static_assert", 73 "_Thread_local", 74 "asm", 75 "__asm__", 76 }; 77 78 /* ============================================================ 79 * Diagnostics 80 * ============================================================ */ 81 82 static SrcLoc tok_loc(const Tok* t) { return t->loc; } 83 84 _Noreturn void perr(Parser* p, const char* fmt, ...) { 85 va_list ap; 86 SrcLoc loc = tok_loc(&p->cur); 87 va_start(ap, fmt); 88 compiler_panicv(p->c, loc, fmt, ap); 89 } 90 91 /* ============================================================ 92 * Token helpers 93 * ============================================================ */ 94 95 /* Width of an encoding prefix on a string-literal spelling: 0 for ordinary, 96 * 1 for L/u/U, 2 for u8. */ 97 static size_t str_prefix_len(u16 flags) { 98 if (flags & TF_STR_U8) return 2; 99 if (flags & (TF_STR_WIDE | TF_STR_U16 | TF_STR_U32)) return 1; 100 return 0; 101 } 102 103 #define STR_ENC_MASK (TF_STR_WIDE | TF_STR_U8 | TF_STR_U16 | TF_STR_U32) 104 105 /* Fuse two adjacent TOK_STR tokens into one per C11 §6.4.5 ¶5. */ 106 static Tok fuse_string_lits(Parser* p, Tok a, Tok b) { 107 u16 ae = (u16)(a.flags & STR_ENC_MASK); 108 u16 be = (u16)(b.flags & STR_ENC_MASK); 109 u16 fused_enc; 110 KitSlice a_sl = kit_sym_str(p->pool->c, a.spelling); 111 KitSlice b_sl = kit_sym_str(p->pool->c, b.spelling); 112 size_t alen = a_sl.len, blen = b_sl.len; 113 const char* as = a_sl.s; 114 const char* bs = b_sl.s; 115 size_t apfx, bpfx; 116 size_t a_content_len, b_content_len; 117 size_t out_pfx_len; 118 size_t out_len; 119 Heap* h = kit_compiler_context(p->c)->heap; 120 char* buf; 121 size_t k = 0; 122 Tok out; 123 if (!as || !bs) perr(p, "bad string literal in concatenation"); 124 if (ae != 0 && be != 0 && ae != be) { 125 perr(p, 126 "concatenating string literals with incompatible " 127 "encoding prefixes"); 128 } 129 fused_enc = ae ? ae : be; 130 apfx = str_prefix_len(a.flags); 131 bpfx = str_prefix_len(b.flags); 132 if (alen < apfx + 2 || as[apfx] != '"' || as[alen - 1] != '"' || 133 blen < bpfx + 2 || bs[bpfx] != '"' || bs[blen - 1] != '"') { 134 perr(p, "malformed string literal in concatenation"); 135 } 136 a_content_len = alen - apfx - 2; 137 b_content_len = blen - bpfx - 2; 138 out_pfx_len = ae ? apfx : bpfx; 139 out_len = out_pfx_len + 1 + a_content_len + b_content_len + 1; 140 buf = (char*)h->alloc(h, out_len, 1); 141 if (!buf) perr(p, "out of memory fusing string literals"); 142 if (out_pfx_len) { 143 const char* src = ae ? as : bs; 144 memcpy(buf + k, src, out_pfx_len); 145 k += out_pfx_len; 146 } 147 buf[k++] = '"'; 148 if (a_content_len) { 149 memcpy(buf + k, as + apfx + 1, a_content_len); 150 k += a_content_len; 151 } 152 if (b_content_len) { 153 memcpy(buf + k, bs + bpfx + 1, b_content_len); 154 k += b_content_len; 155 } 156 buf[k++] = '"'; 157 out = a; 158 out.spelling = kit_sym_intern(p->pool->c, (KitSlice){.s = buf, .len = k}); 159 out.flags = (u16)((a.flags & ~STR_ENC_MASK) | fused_enc); 160 h->free(h, buf, 0); 161 return out; 162 } 163 164 /* Pull one logical token from pp, collapsing adjacent TOK_STR runs. */ 165 static Tok fetch_tok(Parser* p) { 166 Tok t; 167 if (p->has_pending) { 168 t = p->pending; 169 p->has_pending = 0; 170 } else { 171 t = pp_next(p->pp); 172 } 173 if (t.kind != TOK_STR) return t; 174 for (;;) { 175 Tok n = pp_next(p->pp); 176 if (n.kind != TOK_STR) { 177 p->pending = n; 178 p->has_pending = 1; 179 return t; 180 } 181 t = fuse_string_lits(p, t, n); 182 } 183 } 184 185 void advance(Parser* p) { 186 if (p->replay_active) { 187 if (p->replay_pos < p->replay_len) { 188 p->cur = p->replay[p->replay_pos++]; 189 return; 190 } 191 p->replay_active = 0; 192 } 193 if (p->has_next) { 194 p->cur = p->next; 195 p->has_next = 0; 196 } else { 197 p->cur = fetch_tok(p); 198 } 199 } 200 201 Tok peek1(Parser* p) { 202 if (p->replay_active && p->replay_pos < p->replay_len) { 203 return p->replay[p->replay_pos]; 204 } 205 if (!p->has_next) { 206 p->next = fetch_tok(p); 207 p->has_next = 1; 208 } 209 return p->next; 210 } 211 212 void expect_punct(Parser* p, u32 punct, const char* what) { 213 if (!accept_punct(p, punct)) { 214 perr(p, "expected %.*s", KIT_SLICE_ARG(kit_slice_cstr(what))); 215 } 216 } 217 218 int accept_punct(Parser* p, u32 punct) { 219 if (is_punct(&p->cur, punct)) { 220 advance(p); 221 return 1; 222 } 223 return 0; 224 } 225 226 /* Record tokens from the current `{` through the matching `}` into the 227 * parser's replay buffer. */ 228 void record_braced_block(Parser* p) { 229 int depth = 0; 230 if (!is_punct(&p->cur, '{')) perr(p, "internal: record on non-'{'"); 231 p->replay_len = 0; 232 for (;;) { 233 if (p->replay_len == p->replay_cap) { 234 u32 new_cap = p->replay_cap ? p->replay_cap * 2 : 32; 235 Tok* nv = arena_array(p->pool->arena, Tok, new_cap); 236 if (!nv) perr(p, "out of memory in record_braced_block"); 237 if (p->replay && p->replay_len) { 238 memcpy(nv, p->replay, p->replay_len * sizeof(Tok)); 239 } 240 p->replay = nv; 241 p->replay_cap = new_cap; 242 } 243 p->replay[p->replay_len++] = p->cur; 244 if (is_punct(&p->cur, '{')) { 245 ++depth; 246 } else if (is_punct(&p->cur, '}')) { 247 --depth; 248 if (depth == 0) break; 249 } else if (p->cur.kind == TOK_EOF) { 250 perr(p, "unexpected end of file in initializer"); 251 } 252 advance(p); 253 } 254 } 255 256 /* After record_braced_block, rewind to replay from the start. */ 257 void replay_rewind(Parser* p) { 258 if (p->replay_len == 0) perr(p, "internal: replay_rewind with empty buffer"); 259 p->cur = p->replay[0]; 260 p->replay_pos = 1; 261 p->replay_active = 1; 262 p->has_next = 0; 263 } 264 265 /* Count top-level items in a recorded brace list. */ 266 u32 count_recorded_top_level_items(const Tok* vec, u32 len) { 267 u32 count; 268 u32 i; 269 int depth = 0; 270 if (len < 2) return 0; 271 if (len == 2) return 0; /* `{}` */ 272 count = 1; 273 for (i = 1; i < len - 1; ++i) { 274 const Tok* t = &vec[i]; 275 if (is_punct(t, '{') || is_punct(t, '(') || is_punct(t, '[')) 276 ++depth; 277 else if (is_punct(t, '}') || is_punct(t, ')') || is_punct(t, ']')) 278 --depth; 279 else if (depth == 0 && is_punct(t, ',')) 280 ++count; 281 } 282 if (is_punct(&vec[len - 2], ',')) --count; 283 return count; 284 } 285 286 /* ============================================================ 287 * Scopes 288 * ============================================================ */ 289 290 Scope* scope_new(Parser* p, Scope* parent) { 291 Scope* s = arena_new(p->pool->arena, Scope); 292 if (!s) perr(p, "out of memory in scope_new"); 293 s->entries = NULL; 294 s->tags = NULL; 295 s->parent = parent; 296 s->saved_vla_mark = p->vla_mark; 297 return s; 298 } 299 300 void scope_push(Parser* p) { p->scope = scope_new(p, p->scope); } 301 302 void scope_pop(Parser* p) { 303 if (p->scope) { 304 p->vla_mark = p->scope->saved_vla_mark; 305 p->scope = p->scope->parent; 306 } 307 } 308 309 SymEntry* scope_define(Parser* p, Sym name, SymEntryKind kind, 310 const Type* type) { 311 SymEntry* e = arena_new(p->pool->arena, SymEntry); 312 if (!e) perr(p, "out of memory in scope_define"); 313 memset(e, 0, sizeof *e); 314 e->name = name; 315 e->kind = (u8)kind; 316 e->type = type; 317 e->next = p->scope->entries; 318 p->scope->entries = e; 319 return e; 320 } 321 322 SymEntry* scope_lookup_current(Parser* p, Sym name) { 323 SymEntry* e; 324 if (!p->scope) return NULL; 325 for (e = p->scope->entries; e; e = e->next) { 326 if (e->name == name) return e; 327 } 328 return NULL; 329 } 330 331 SymEntry* scope_lookup(Parser* p, Sym name) { 332 Scope* s; 333 for (s = p->scope; s; s = s->parent) { 334 SymEntry* e; 335 for (e = s->entries; e; e = e->next) { 336 if (e->name == name) return e; 337 } 338 } 339 return NULL; 340 } 341 342 static void sym_set_decl(SymEntry* e, DeclId id, DeclStorage storage, 343 DeclLinkage linkage, u32 flags, DeclState state) { 344 e->decl_id = id; 345 e->storage = (u8)storage; 346 e->linkage = (u8)linkage; 347 e->decl_flags = flags; 348 e->decl_state = (u8)state; 349 e->defined = (state == DSTATE_DEFINED || state == DSTATE_FUNC_DEFINED); 350 } 351 352 static SymEntry* external_func_lookup(Parser* p, Sym name) { 353 ExternalFuncDecl* f; 354 for (f = p->external_funcs; f; f = f->next) { 355 if (f->name == name) return f->entry; 356 } 357 return NULL; 358 } 359 360 static void external_func_remember(Parser* p, Sym name, SymEntry* entry) { 361 ExternalFuncDecl* f; 362 if (!entry) return; 363 for (f = p->external_funcs; f; f = f->next) { 364 if (f->name == name) { 365 f->entry = entry; 366 return; 367 } 368 } 369 f = arena_new(p->pool->arena, ExternalFuncDecl); 370 if (!f) perr(p, "out of memory in external_func_remember"); 371 f->name = name; 372 f->entry = entry; 373 f->next = p->external_funcs; 374 p->external_funcs = f; 375 } 376 377 static int is_ordinary_decl_kind(SymEntryKind k) { 378 return k == SEK_LOCAL || k == SEK_GLOBAL || k == SEK_FUNC || 379 k == SEK_TYPEDEF || k == SEK_ENUM_CST; 380 } 381 382 static void reject_same_scope_redefinition(Parser* p, Sym name, 383 SymEntryKind kind, 384 const Type* type) { 385 SymEntry* e = scope_lookup_current(p, name); 386 if (!e || !is_ordinary_decl_kind((SymEntryKind)e->kind)) return; 387 if (e->kind == SEK_TYPEDEF && kind == SEK_TYPEDEF && 388 type_compatible(e->type, type)) { 389 return; 390 } 391 perr(p, "redefinition of identifier"); 392 } 393 394 TagEntry* tag_define(Parser* p, Sym name, TagDeclKind kind, Type* type, 395 int complete) { 396 TagEntry* e = arena_new(p->pool->arena, TagEntry); 397 if (!e) perr(p, "out of memory in tag_define"); 398 memset(e, 0, sizeof *e); 399 e->name = name; 400 e->kind = (u8)kind; 401 e->complete = (u8)(complete ? 1 : 0); 402 e->type = type; 403 e->next = p->scope->tags; 404 p->scope->tags = e; 405 return e; 406 } 407 408 TagEntry* tag_lookup(Parser* p, Sym name) { 409 Scope* s; 410 for (s = p->scope; s; s = s->parent) { 411 TagEntry* e; 412 for (e = s->tags; e; e = e->next) { 413 if (e->name == name) return e; 414 } 415 } 416 return NULL; 417 } 418 419 TagEntry* tag_lookup_local(Parser* p, Sym name) { 420 TagEntry* e; 421 for (e = p->scope->tags; e; e = e->next) { 422 if (e->name == name) return e; 423 } 424 return NULL; 425 } 426 427 /* ============================================================ 428 * Type helpers 429 * ============================================================ */ 430 431 static const Type* ty_size_t(Parser* p) { 432 return c_abi_size_type(p->abi, p->pool); 433 } 434 435 /* ============================================================ 436 * Local-variable slot allocation 437 * ============================================================ */ 438 439 FrameSlot make_local_aligned(Parser* p, Sym name, const Type* type, SrcLoc loc, 440 u32 align_override) { 441 FrameSlotDesc fsd; 442 FrameSlot s; 443 SymEntry* e; 444 u32 nat = c_abi_alignof(p->abi, type); 445 memset(&fsd, 0, sizeof fsd); 446 fsd.type = type; 447 fsd.name = name; 448 fsd.loc = loc; 449 fsd.size = c_abi_sizeof(p->abi, type); 450 fsd.align = (align_override > nat) ? align_override : nat; 451 fsd.kind = FS_LOCAL; 452 fsd.flags = FSF_NONE; 453 s = pcg_local(p, &fsd); 454 reject_same_scope_redefinition(p, name, SEK_LOCAL, type); 455 e = scope_define(p, name, SEK_LOCAL, type); 456 e->v.slot = s; 457 sym_set_decl(e, DECL_NONE, DS_AUTO, DL_NONE, DF_NONE, DSTATE_DEFINED); 458 return s; 459 } 460 461 FrameSlot make_local(Parser* p, Sym name, const Type* type, SrcLoc loc) { 462 return make_local_aligned(p, name, type, loc, 0); 463 } 464 465 static FrameSlot make_vla_size_slot(Parser* p) { 466 FrameSlotDesc fsd; 467 memset(&fsd, 0, sizeof fsd); 468 fsd.type = ty_size_t(p); 469 fsd.size = c_abi_sizeof(p->abi, fsd.type); 470 fsd.align = c_abi_alignof(p->abi, fsd.type); 471 fsd.kind = FS_LOCAL; 472 return pcg_local(p, &fsd); 473 } 474 475 static void store_top_to_size_slot(Parser* p, FrameSlot slot) { 476 pcg_push_local_typed(p, slot, ty_size_t(p)); 477 pcg_swap(p); 478 coerce_top_to_lvalue(p); 479 pcg_store(p); 480 pcg_drop(p); 481 } 482 483 static void reset_vla_pending(Parser* p) { 484 p->vla_pending = 0; 485 p->vla_pending_count_slot = FRAME_SLOT_NONE; 486 p->vla_pending_count_len = 0; 487 } 488 489 static VLABound* add_vla_bound(Parser* p, VLABound* head, const Type* array_ty, 490 FrameSlot byte_slot, FrameSlot count_slot) { 491 VLABound* b = arena_znew(p->pool->arena, VLABound); 492 b->array_ty = array_ty; 493 b->byte_slot = byte_slot; 494 b->count_slot = count_slot; 495 b->next = head; 496 return b; 497 } 498 499 static int build_vla_size(Parser* p, const Type* ty, u32* count_idx, 500 VLABound** bounds, FrameSlot* out_slot, 501 u32* out_static_size, SrcLoc loc) { 502 if (!ty || ty->kind != TY_ARRAY) { 503 *out_static_size = c_abi_sizeof(p->abi, ty); 504 *out_slot = FRAME_SLOT_NONE; 505 return 0; 506 } 507 508 FrameSlot count_slot = FRAME_SLOT_NONE; 509 int count_dynamic = 0; 510 if (ty->arr.incomplete) { 511 if (*count_idx >= p->vla_pending_count_len) { 512 perr(p, "missing VLA bound for declarator"); 513 } 514 count_slot = p->vla_pending_count_slots[(*count_idx)++]; 515 count_dynamic = 1; 516 } 517 518 FrameSlot elem_slot = FRAME_SLOT_NONE; 519 u32 elem_static_size = 0; 520 int elem_dynamic = build_vla_size(p, ty->arr.elem, count_idx, bounds, 521 &elem_slot, &elem_static_size, loc); 522 523 if (count_dynamic || elem_dynamic) { 524 FrameSlot byte_slot = make_vla_size_slot(p); 525 pcg_set_loc(p, loc); 526 if (count_dynamic) { 527 pcg_push_local_typed(p, count_slot, ty_size_t(p)); 528 pcg_load(p); 529 } else { 530 pcg_push_int(p, (i64)ty->arr.count, ty_size_t(p)); 531 } 532 if (elem_dynamic) { 533 pcg_push_local_typed(p, elem_slot, ty_size_t(p)); 534 pcg_load(p); 535 } else { 536 pcg_push_int(p, (i64)elem_static_size, ty_size_t(p)); 537 } 538 pcg_binop(p, BO_IMUL); 539 store_top_to_size_slot(p, byte_slot); 540 *bounds = add_vla_bound(p, *bounds, ty, byte_slot, count_slot); 541 *out_slot = byte_slot; 542 *out_static_size = 0; 543 return 1; 544 } 545 546 *out_slot = FRAME_SLOT_NONE; 547 *out_static_size = ty->arr.count * elem_static_size; 548 return 0; 549 } 550 551 static FrameSlot finish_vla_layout(Parser* p, const Type* ty, SrcLoc loc, 552 VLABound** bounds_out) { 553 FrameSlot byte_slot = FRAME_SLOT_NONE; 554 u32 static_size = 0; 555 u32 count_idx = 0; 556 *bounds_out = NULL; 557 if (!build_vla_size(p, ty, &count_idx, bounds_out, &byte_slot, &static_size, 558 loc)) { 559 perr(p, "VLA declarator did not produce a runtime size"); 560 } 561 if (count_idx != p->vla_pending_count_len) { 562 perr(p, "unused VLA bound in declarator"); 563 } 564 reset_vla_pending(p); 565 return byte_slot; 566 } 567 568 static int type_array_depth(const Type* ty) { 569 int n = 0; 570 while (ty && ty->kind == TY_ARRAY) { 571 ++n; 572 ty = ty->arr.elem; 573 } 574 return n; 575 } 576 577 static void eval_param_vla_count(Parser* p, const ParamVLABoundExpr* expr, 578 FrameSlot slot) { 579 Tok save_cur = p->cur; 580 Tok save_next = p->next; 581 int save_has_next = p->has_next; 582 Tok* save_replay = p->replay; 583 u32 save_cap = p->replay_cap; 584 u32 save_len = p->replay_len; 585 u32 save_pos = p->replay_pos; 586 u8 save_active = p->replay_active; 587 Tok* replay; 588 589 if (!expr->has_expr || expr->ntoks == 0) { 590 perr(p, "missing VLA parameter bound"); 591 } 592 replay = arena_array(p->pool->arena, Tok, expr->ntoks + 1u); 593 memcpy(replay, expr->toks, sizeof(Tok) * expr->ntoks); 594 memset(&replay[expr->ntoks], 0, sizeof(Tok)); 595 replay[expr->ntoks].kind = TOK_EOF; 596 597 p->cur = replay[0]; 598 p->next.kind = TOK_EOF; 599 p->has_next = 0; 600 p->replay = replay; 601 p->replay_cap = expr->ntoks + 1u; 602 p->replay_len = expr->ntoks + 1u; 603 p->replay_pos = 1; 604 p->replay_active = 1; 605 606 parse_assign_expr(p); 607 to_rvalue(p); 608 if (p->cur.kind != TOK_EOF) { 609 perr(p, "unexpected token in VLA parameter bound"); 610 } 611 store_top_to_size_slot(p, slot); 612 613 p->cur = save_cur; 614 p->next = save_next; 615 p->has_next = save_has_next; 616 p->replay = save_replay; 617 p->replay_cap = save_cap; 618 p->replay_len = save_len; 619 p->replay_pos = save_pos; 620 p->replay_active = save_active; 621 } 622 623 static VLABound* build_param_vla_bounds(Parser* p, const ParamInfo* info, 624 SrcLoc loc) { 625 const Type* root = info->declared_type; 626 u32 dim_skip = 0; 627 u32 need; 628 VLABound* bounds = NULL; 629 630 if (!root || info->vla_bound_len == 0) return NULL; 631 if (root->kind == TY_ARRAY) { 632 dim_skip = 1; 633 root = root->arr.elem; 634 } else if (root->kind == TY_PTR) { 635 root = root->ptr.pointee; 636 } 637 need = (u32)type_array_depth(root); 638 if (need == 0) return NULL; 639 if (dim_skip + need > info->vla_bound_len) { 640 perr(p, "missing VLA parameter bound"); 641 } 642 643 reset_vla_pending(p); 644 for (u32 i = 0; i < need; ++i) { 645 const ParamVLABoundExpr* expr = &info->vla_bounds[dim_skip + i]; 646 FrameSlot slot = make_vla_size_slot(p); 647 eval_param_vla_count(p, expr, slot); 648 p->vla_pending = 1; 649 p->vla_pending_count_slots[p->vla_pending_count_len++] = slot; 650 } 651 (void)finish_vla_layout(p, root, loc, &bounds); 652 return bounds; 653 } 654 655 /* ============================================================ 656 * Static-local symbol naming 657 * ============================================================ */ 658 659 /* Mint a unique linker name for a static local: `<orig>.<counter>`. */ 660 Sym mint_static_local_sym(Parser* p, Sym orig) { 661 KitSlice orig_sl = kit_sym_str(p->pool->c, orig); 662 size_t olen = orig_sl.len; 663 const char* on = orig_sl.s; 664 char buf[128]; 665 u32 wlen = 0; 666 u32 id = ++p->static_local_counter; 667 if (olen > 100) olen = 100; 668 for (size_t i = 0; i < olen && wlen < sizeof buf - 1; ++i) { 669 buf[wlen++] = on[i]; 670 } 671 if (wlen < sizeof buf - 1) buf[wlen++] = '.'; 672 { 673 char digits[12]; 674 int dn = 0; 675 if (id == 0) digits[dn++] = '0'; 676 while (id) { 677 digits[dn++] = (char)('0' + (id % 10)); 678 id /= 10; 679 } 680 while (dn && wlen < sizeof buf - 1) buf[wlen++] = digits[--dn]; 681 } 682 return kit_sym_intern(p->pool->c, (KitSlice){.s = buf, .len = wlen}); 683 } 684 685 /* ============================================================ 686 * Declarations 687 * ============================================================ */ 688 689 /* Parse a single init-declarator after the decl-specs have been consumed. */ 690 static SymEntry* declare_function(Parser* p, Sym fname, const Type* fn_ty, 691 const DeclSpecs* specs, SrcLoc fname_loc, 692 const Attr* dattrs, Sym asm_label, 693 ObjSecId* out_section_id, u32* out_decl_flags, 694 Sym* out_alias_target); 695 696 static void parse_init_declarator(Parser* p, const DeclSpecs* specs) { 697 SrcLoc loc; 698 Sym name; 699 DeclaratorInfo dinfo; 700 const Type* var_ty = parse_declarator_full_info( 701 p, specs->type, /*allow_abstract=*/0, &name, &loc, NULL, &dinfo); 702 if ((specs->flags & DF_THREAD) && specs->storage != DS_STATIC && 703 specs->storage != DS_EXTERN) { 704 perr(p, "block-scope _Thread_local requires static or extern"); 705 } 706 validate_decl_type_constraints(p, specs, var_ty, 707 var_ty && var_ty->kind == TY_FUNC, 708 /*is_member=*/0); 709 710 if (specs->storage == DS_TYPEDEF) { 711 if (is_punct(&p->cur, '=')) { 712 perr(p, "typedef declarator cannot have initializer"); 713 } 714 { 715 reject_same_scope_redefinition(p, name, SEK_TYPEDEF, var_ty); 716 SymEntry* e = scope_define(p, name, SEK_TYPEDEF, var_ty); 717 sym_set_decl(e, DECL_NONE, DS_TYPEDEF, DL_NONE, specs->flags, 718 DSTATE_DECLARED); 719 if (p->vla_pending && var_ty && var_ty->kind == TY_ARRAY) { 720 VLABound* bounds = NULL; 721 FrameSlot byte_slot = finish_vla_layout(p, var_ty, loc, &bounds); 722 e->vla_byte_slot = byte_slot; 723 e->vla_bounds = bounds; 724 } else if (specs->vla_byte_slot != FRAME_SLOT_NONE) { 725 e->vla_byte_slot = specs->vla_byte_slot; 726 e->vla_bounds = specs->vla_bounds; 727 } 728 } 729 (void)loc; 730 return; 731 } 732 733 if (var_ty && var_ty->kind == TY_FUNC) { 734 ObjSecId section_id; 735 u32 decl_flags; 736 Sym alias_target; 737 if ((specs->storage == DS_AUTO && specs->storage_explicit) || 738 specs->storage == DS_REGISTER || specs->storage == DS_STATIC) { 739 perr(p, 740 "invalid storage-class specifier for block-scope function " 741 "declaration"); 742 } 743 if (is_punct(&p->cur, '=')) { 744 perr(p, "function declarator cannot have initializer"); 745 } 746 (void)declare_function(p, name, var_ty, specs, loc, NULL, dinfo.asm_label, 747 §ion_id, &decl_flags, &alias_target); 748 (void)section_id; 749 (void)decl_flags; 750 (void)alias_target; 751 return; 752 } 753 754 if (specs->storage == DS_STATIC) { 755 Decl decl_in; 756 DeclId did; 757 ObjSymId sym; 758 SymEntry* e; 759 Sym lname = mint_static_local_sym(p, name); 760 int has_init; 761 u32 align_eff; 762 has_init = accept_punct(p, '='); 763 /* Complete `T x[] = {...}` before declaring the symbol so the registered 764 * (CG) type carries the real element count. Backends such as the C target 765 * derive function-local label-table sizes from the symbol's type, so the 766 * declared type must already be the completed array. */ 767 if (has_init && var_ty && var_ty->kind == TY_ARRAY && 768 var_ty->arr.incomplete) { 769 var_ty = complete_incomplete_array(p, var_ty); 770 } 771 memset(&decl_in, 0, sizeof decl_in); 772 decl_in.name = lname; 773 decl_in.asm_name = dinfo.asm_label; 774 decl_in.type = var_ty; 775 decl_in.loc = loc; 776 decl_in.storage = DS_STATIC; 777 decl_in.linkage = DL_INTERNAL; 778 decl_in.visibility = SV_DEFAULT; 779 decl_in.flags = DF_STATIC_LOCAL | (specs->flags & DF_THREAD); 780 attr_list_to_decl(p->c, p->decls, specs->attrs, &decl_in); 781 did = decl_declare(p->decls, &decl_in); 782 sym = decl_obj_sym(p->decls, did); 783 reject_same_scope_redefinition(p, name, SEK_GLOBAL, var_ty); 784 e = scope_define(p, name, SEK_GLOBAL, var_ty); 785 e->v.sym = sym; 786 sym_set_decl(e, did, DS_STATIC, DL_NONE, decl_in.flags, DSTATE_DEFINED); 787 align_eff = (specs->align > decl_in.align) ? specs->align : decl_in.align; 788 define_static_object(p, sym, decl_in.section_id, var_ty, specs->quals, 789 has_init, loc, align_eff); 790 return; 791 } 792 793 if (specs->storage == DS_EXTERN) { 794 Decl decl_in; 795 DeclId did; 796 ObjSymId sym; 797 SymEntry* e; 798 SymEntry* prior; 799 if (accept_punct(p, '=')) { 800 perr(p, "block-scope extern with initializer not supported"); 801 } 802 prior = scope_lookup(p, name); 803 if (prior && prior->kind == SEK_GLOBAL) { 804 SymEntry* cur = scope_lookup_current(p, name); 805 const Type* composite = NULL; 806 CSemCheck chk = 807 c_sem_check_redeclaration(p->pool, prior->type, var_ty, &composite); 808 if (!chk.ok) perr(p, "%.*s", KIT_SLICE_ARG(kit_slice_cstr(chk.message))); 809 if (cur && cur->kind != SEK_GLOBAL) { 810 perr(p, "redefinition of identifier"); 811 } 812 if (cur) return; 813 e = scope_define(p, name, SEK_GLOBAL, var_ty); 814 e->v.sym = prior->v.sym; 815 sym_set_decl(e, prior->decl_id, DS_EXTERN, (DeclLinkage)prior->linkage, 816 prior->decl_flags, (DeclState)prior->decl_state); 817 return; 818 } 819 memset(&decl_in, 0, sizeof decl_in); 820 decl_in.name = name; 821 decl_in.asm_name = dinfo.asm_label; 822 decl_in.type = var_ty; 823 decl_in.loc = loc; 824 decl_in.storage = DS_EXTERN; 825 decl_in.linkage = DL_EXTERNAL; 826 decl_in.visibility = p->default_visibility; 827 decl_in.flags = specs->flags & DF_THREAD; 828 attr_list_to_decl(p->c, p->decls, specs->attrs, &decl_in); 829 did = decl_declare(p->decls, &decl_in); 830 sym = decl_obj_sym(p->decls, did); 831 reject_same_scope_redefinition(p, name, SEK_GLOBAL, var_ty); 832 e = scope_define(p, name, SEK_GLOBAL, var_ty); 833 e->v.sym = sym; 834 sym_set_decl(e, did, DS_EXTERN, DL_EXTERNAL, decl_in.flags, 835 DSTATE_DECLARED); 836 return; 837 } 838 839 if (var_ty && var_ty->kind == TY_ARRAY && 840 (p->vla_pending || specs->vla_byte_slot != FRAME_SLOT_NONE)) { 841 const Type* elem_ty = var_ty->arr.elem; 842 const Type* ptr_ty = type_ptr(p->pool, elem_ty); 843 FrameSlot byte_slot; 844 FrameSlot ptr_slot; 845 SymEntry* sym_entry; 846 VLABound* bounds = NULL; 847 if (p->vla_pending) { 848 byte_slot = finish_vla_layout(p, var_ty, loc, &bounds); 849 ++p->vla_mark; 850 } else { 851 byte_slot = specs->vla_byte_slot; 852 bounds = specs->vla_bounds; 853 } 854 ptr_slot = make_local(p, name, ptr_ty, loc); 855 pcg_set_loc(p, loc); 856 pcg_push_local_typed(p, byte_slot, ty_size_t(p)); 857 pcg_load(p); 858 pcg_alloca(p); 859 pcg_push_local_typed(p, ptr_slot, ptr_ty); 860 pcg_swap(p); 861 pcg_store(p); 862 pcg_drop(p); 863 sym_entry = scope_lookup(p, name); 864 if (sym_entry && sym_entry->kind == SEK_LOCAL) { 865 sym_entry->vla_byte_slot = byte_slot; 866 sym_entry->vla_bounds = bounds; 867 } 868 if (accept_punct(p, '=')) { 869 perr(p, "VLA initializers are not allowed (§6.7.9 ¶3)"); 870 } 871 return; 872 } 873 /* Non-VLA local. */ 874 { 875 int has_init = is_punct(&p->cur, '='); 876 FrameSlot s; 877 if (has_init && var_ty && var_ty->kind == TY_ARRAY && 878 var_ty->arr.incomplete) { 879 advance(p); /* '=' */ 880 var_ty = complete_incomplete_array(p, var_ty); 881 s = make_local_aligned(p, name, var_ty, loc, specs->align); 882 if (specs->storage == DS_REGISTER) { 883 SymEntry* e = scope_lookup_current(p, name); 884 if (e && e->kind == SEK_LOCAL) { 885 e->storage = DS_REGISTER; 886 e->reg_asm_name = dinfo.asm_label; 887 } 888 } 889 pcg_set_loc(p, loc); 890 init_at(p, s, var_ty, 0, var_ty); 891 return; 892 } 893 s = make_local_aligned(p, name, var_ty, loc, specs->align); 894 if (specs->storage == DS_REGISTER) { 895 SymEntry* e = scope_lookup_current(p, name); 896 if (e && e->kind == SEK_LOCAL) { 897 e->storage = DS_REGISTER; 898 e->reg_asm_name = dinfo.asm_label; 899 } 900 } 901 if (accept_punct(p, '=')) { 902 pcg_set_loc(p, loc); 903 if ((var_ty->kind == TY_STRUCT || var_ty->kind == TY_UNION) && 904 !is_punct(&p->cur, '{')) { 905 parse_assign_expr(p); 906 emit_struct_copy_into_slot(p, s, var_ty, 0, var_ty); 907 } else if (var_ty->kind == TY_ARRAY || var_ty->kind == TY_STRUCT || 908 var_ty->kind == TY_UNION) { 909 init_at(p, s, var_ty, 0, var_ty); 910 } else { 911 pcg_push_local_typed(p, s, var_ty); 912 parse_assign_expr(p); 913 to_rvalue(p); 914 { 915 const Type* rhs = pcg_top_type(p); 916 CSemCheck chk = 917 c_sem_check_assignment(p->pool, var_ty, rhs, C_SEM_ASSIGN_INIT); 918 if (!chk.ok) 919 perr(p, "%.*s", KIT_SLICE_ARG(kit_slice_cstr(chk.message))); 920 } 921 coerce_top_to_lvalue(p); 922 pcg_store(p); 923 pcg_drop(p); 924 } 925 } 926 } 927 } 928 929 void parse_local_decl(Parser* p, const DeclSpecs* specs) { 930 if (accept_punct(p, ';')) return; 931 parse_init_declarator(p, specs); 932 while (accept_punct(p, ',')) { 933 parse_init_declarator(p, specs); 934 } 935 expect_punct(p, ';', "';' after declaration"); 936 } 937 938 /* ============================================================ 939 * External (top-level) declarations 940 * ============================================================ */ 941 942 void parse_param_list(Parser* p, ParamInfo** infos_out, u16* nparams_out, 943 u8* variadic_out) { 944 ParamInfo* infos; 945 u32 cap = 4; 946 u32 n = 0; 947 *variadic_out = 0; 948 *infos_out = NULL; 949 *nparams_out = 0; 950 951 if (is_punct(&p->cur, ')')) { 952 return; 953 } 954 if (is_kw(p, &p->cur, KW_VOID)) { 955 Tok n2 = peek1(p); 956 if (is_punct(&n2, ')')) { 957 advance(p); /* `void` */ 958 return; /* `(void)` */ 959 } 960 } 961 962 infos = (ParamInfo*)arena_array(p->pool->arena, ParamInfo, cap); 963 for (;;) { 964 DeclSpecs specs; 965 Sym pname = 0; 966 SrcLoc ploc = {0, 0, 0}; 967 const Type* pty; 968 if (accept_punct(p, P_ELLIPSIS)) { 969 if (n == 0) perr(p, "ellipsis requires a preceding parameter"); 970 *variadic_out = 1; 971 break; 972 } 973 if (!parse_decl_specs(p, &specs)) { 974 perr(p, "expected parameter type"); 975 } 976 if ((specs.storage_explicit && specs.storage != DS_REGISTER) || 977 specs.storage == DS_TYPEDEF || (specs.flags & DF_THREAD)) { 978 perr(p, "invalid storage-class specifier in parameter declaration"); 979 } 980 p->param_vla_bound_len = 0; 981 p->in_param_decl++; 982 pty = parse_declarator_full(p, specs.type, /*allow_abstract=*/1, &pname, 983 &ploc); 984 p->in_param_decl--; 985 const Type* declared_pty = pty; 986 if (pty && pty->kind == TY_ARRAY) { 987 pty = type_ptr(p->pool, pty->arr.elem); 988 } else if (pty && pty->kind == TY_FUNC) { 989 pty = type_ptr(p->pool, pty); 990 } 991 if (pty && pty->kind == TY_VOID) { 992 perr(p, "'void' must be the only parameter"); 993 } 994 validate_decl_type_constraints(p, &specs, pty, /*is_function=*/0, 995 /*is_member=*/0); 996 if (pname) { 997 for (u32 pi = 0; pi < n; ++pi) { 998 if (infos[pi].name == pname) perr(p, "redefinition of parameter"); 999 } 1000 } 1001 if (n == cap) { 1002 cap *= 2; 1003 ParamInfo* nbuf = (ParamInfo*)arena_array(p->pool->arena, ParamInfo, cap); 1004 memcpy(nbuf, infos, sizeof(ParamInfo) * n); 1005 infos = nbuf; 1006 } 1007 infos[n].name = pname; 1008 infos[n].type = pty; 1009 infos[n].declared_type = declared_pty; 1010 infos[n].loc = ploc; 1011 infos[n].vla_bounds = NULL; 1012 infos[n].vla_bound_len = p->param_vla_bound_len; 1013 if (p->param_vla_bound_len) { 1014 ParamVLABoundExpr* bounds = arena_array(p->pool->arena, ParamVLABoundExpr, 1015 p->param_vla_bound_len); 1016 memcpy(bounds, p->param_vla_bounds, 1017 sizeof(ParamVLABoundExpr) * p->param_vla_bound_len); 1018 infos[n].vla_bounds = bounds; 1019 } 1020 ++n; 1021 if (!accept_punct(p, ',')) break; 1022 } 1023 *infos_out = infos; 1024 *nparams_out = (u16)n; 1025 } 1026 1027 static SymEntry* declare_function(Parser* p, Sym fname, const Type* fn_ty, 1028 const DeclSpecs* specs, SrcLoc fname_loc, 1029 const Attr* dattrs, Sym asm_label, 1030 ObjSecId* out_section_id, u32* out_decl_flags, 1031 Sym* out_alias_target) { 1032 SymEntry* visible; 1033 if (out_section_id) *out_section_id = OBJ_SEC_NONE; 1034 if (out_decl_flags) *out_decl_flags = 0; 1035 if (out_alias_target) *out_alias_target = 0; 1036 SymEntry* existing = scope_lookup_current(p, fname); 1037 if (existing && existing->kind != SEK_FUNC) { 1038 perr(p, "redefinition of identifier"); 1039 } 1040 if (existing && existing->kind == SEK_FUNC) { 1041 const Type* composite = NULL; 1042 CSemCheck chk = 1043 c_sem_check_redeclaration(p->pool, existing->type, fn_ty, &composite); 1044 if (!chk.ok) perr(p, "%.*s", KIT_SLICE_ARG(kit_slice_cstr(chk.message))); 1045 if (specs->storage == DS_STATIC && existing->linkage == DL_EXTERNAL) { 1046 perr(p, "static declaration follows non-static declaration"); 1047 } 1048 existing->type = composite ? composite : existing->type; 1049 Decl tmp; 1050 memset(&tmp, 0, sizeof tmp); 1051 attr_list_to_decl(p->c, p->decls, specs->attrs, &tmp); 1052 attr_list_to_decl(p->c, p->decls, dattrs, &tmp); 1053 if (out_section_id) *out_section_id = tmp.section_id; 1054 if (out_decl_flags) *out_decl_flags = tmp.flags; 1055 if (out_alias_target) *out_alias_target = tmp.alias_target; 1056 decl_apply_redecl_flags(p->decls, existing->decl_id, tmp.flags); 1057 external_func_remember(p, fname, existing); 1058 return existing; 1059 } 1060 visible = scope_lookup(p, fname); 1061 if (!existing && visible && visible->kind == SEK_FUNC) { 1062 existing = visible; 1063 } 1064 if (!existing) { 1065 existing = external_func_lookup(p, fname); 1066 } 1067 if (existing) { 1068 const Type* composite = NULL; 1069 CSemCheck chk = 1070 c_sem_check_redeclaration(p->pool, existing->type, fn_ty, &composite); 1071 if (!chk.ok) perr(p, "%.*s", KIT_SLICE_ARG(kit_slice_cstr(chk.message))); 1072 if (specs->storage == DS_STATIC && existing->linkage == DL_EXTERNAL) { 1073 perr(p, "static declaration follows non-static declaration"); 1074 } 1075 if (scope_lookup_current(p, fname) != existing) { 1076 SymEntry* e = scope_define(p, fname, SEK_FUNC, 1077 composite ? composite : existing->type); 1078 e->v.sym = existing->v.sym; 1079 sym_set_decl(e, existing->decl_id, (DeclStorage)existing->storage, 1080 (DeclLinkage)existing->linkage, existing->decl_flags, 1081 (DeclState)existing->decl_state); 1082 existing = e; 1083 } else if (composite) { 1084 existing->type = composite; 1085 } 1086 { 1087 Decl tmp; 1088 memset(&tmp, 0, sizeof tmp); 1089 attr_list_to_decl(p->c, p->decls, specs->attrs, &tmp); 1090 attr_list_to_decl(p->c, p->decls, dattrs, &tmp); 1091 if (out_section_id) *out_section_id = tmp.section_id; 1092 if (out_decl_flags) *out_decl_flags = tmp.flags; 1093 if (out_alias_target) *out_alias_target = tmp.alias_target; 1094 decl_apply_redecl_flags(p->decls, existing->decl_id, tmp.flags); 1095 } 1096 external_func_remember(p, fname, existing); 1097 return existing; 1098 } 1099 { 1100 Decl decl_in; 1101 DeclId did; 1102 ObjSymId fsym; 1103 SymEntry* e; 1104 memset(&decl_in, 0, sizeof decl_in); 1105 decl_in.name = fname; 1106 decl_in.asm_name = asm_label; 1107 decl_in.type = fn_ty; 1108 decl_in.loc = fname_loc; 1109 decl_in.storage = 1110 (specs->storage == DS_STATIC || 1111 ((specs->flags & DF_INLINE) && specs->storage != DS_EXTERN)) 1112 ? DS_STATIC 1113 : DS_EXTERN; 1114 decl_in.linkage = 1115 (decl_in.storage == DS_STATIC) ? DL_INTERNAL : DL_EXTERNAL; 1116 decl_in.visibility = 1117 decl_in.linkage == DL_EXTERNAL ? p->default_visibility : SV_DEFAULT; 1118 attr_list_to_decl(p->c, p->decls, specs->attrs, &decl_in); 1119 attr_list_to_decl(p->c, p->decls, dattrs, &decl_in); 1120 did = decl_declare(p->decls, &decl_in); 1121 fsym = decl_obj_sym(p->decls, did); 1122 e = scope_define(p, fname, SEK_FUNC, fn_ty); 1123 e->v.sym = fsym; 1124 sym_set_decl(e, did, decl_in.storage, decl_in.linkage, decl_in.flags, 1125 DSTATE_DECLARED); 1126 external_func_remember(p, fname, e); 1127 if (out_section_id) *out_section_id = decl_in.section_id; 1128 if (out_decl_flags) *out_decl_flags = decl_in.flags; 1129 if (out_alias_target) *out_alias_target = decl_in.alias_target; 1130 return e; 1131 } 1132 } 1133 1134 static void parse_function_body(Parser* p, ObjSymId fsym, const Type* fn_ty, 1135 const ABIFuncInfo* abi, const ParamInfo* infos, 1136 u16 nparams, SrcLoc fname_loc, 1137 ObjSecId section_id, u32 decl_flags) { 1138 CGFuncDesc fd; 1139 CGParamDesc* pds = NULL; 1140 1141 memset(&fd, 0, sizeof fd); 1142 fd.sym = fsym; 1143 fd.text_section_id = section_id; 1144 fd.group_id = OBJ_GROUP_NONE; 1145 fd.fn_type = fn_ty; 1146 fd.abi = abi; 1147 fd.params = NULL; 1148 fd.nparams = nparams; 1149 fd.loc = fname_loc; 1150 if (decl_flags & DF_NORETURN) fd.flags |= CGFD_NORETURN; 1151 if (decl_flags & DF_NOINLINE) 1152 fd.inline_policy = KIT_CG_INLINE_NEVER; 1153 else if (decl_flags & DF_ALWAYS_INLINE) 1154 fd.inline_policy = KIT_CG_INLINE_ALWAYS; 1155 else if (decl_flags & DF_INLINE) 1156 fd.inline_policy = KIT_CG_INLINE_HINT; 1157 1158 if (nparams) { 1159 pds = (CGParamDesc*)arena_array(p->pool->arena, CGParamDesc, nparams); 1160 memset(pds, 0, sizeof(CGParamDesc) * nparams); 1161 for (u16 i = 0; i < nparams; ++i) { 1162 pds[i].index = i; 1163 pds[i].name = infos[i].name; 1164 pds[i].type = infos[i].type; 1165 pds[i].slot = FRAME_SLOT_NONE; 1166 pds[i].abi = &abi->params[i]; 1167 pds[i].incoming = NULL; 1168 pds[i].nincoming = 0; 1169 pds[i].loc = infos[i].loc; 1170 } 1171 fd.params = pds; 1172 } 1173 1174 scope_push(p); /* parameter scope */ 1175 GotoLabel* saved_goto_labels = p->goto_labels; 1176 SwitchCtx* saved_switch = p->cur_switch; 1177 u8 saved_computed_goto = p->computed_goto_emitted; 1178 p->goto_labels = NULL; 1179 p->cur_switch = NULL; 1180 p->computed_goto_emitted = 0; 1181 pcg_set_loc(p, fname_loc); 1182 pcg_func_begin(p, &fd); 1183 1184 for (u16 i = 0; i < nparams; ++i) { 1185 FrameSlotDesc fsd; 1186 FrameSlot s; 1187 SymEntry* e; 1188 memset(&fsd, 0, sizeof fsd); 1189 fsd.type = infos[i].type; 1190 fsd.name = infos[i].name; 1191 fsd.loc = infos[i].loc; 1192 fsd.size = c_abi_sizeof(p->abi, infos[i].type); 1193 fsd.align = c_abi_alignof(p->abi, infos[i].type); 1194 fsd.kind = FS_PARAM; 1195 fsd.flags = FSF_NONE; 1196 s = pcg_param_slot(p, i, &fsd); 1197 pds[i].slot = s; 1198 if (infos[i].name) { 1199 reject_same_scope_redefinition(p, infos[i].name, SEK_LOCAL, 1200 infos[i].type); 1201 e = scope_define(p, infos[i].name, SEK_LOCAL, infos[i].type); 1202 e->v.slot = s; 1203 sym_set_decl(e, DECL_NONE, DS_AUTO, DL_NONE, DF_NONE, DSTATE_DEFINED); 1204 e->vla_bounds = build_param_vla_bounds(p, &infos[i], infos[i].loc); 1205 } 1206 } 1207 1208 parse_compound_stmt(p); 1209 if (fn_ty->fn.ret && fn_ty->fn.ret->kind != TY_VOID && 1210 fn_ty->fn.ret->kind != TY_STRUCT && fn_ty->fn.ret->kind != TY_UNION) { 1211 pcg_push_int(p, 0, fn_ty->fn.ret); 1212 pcg_ret(p, 1); 1213 } else { 1214 pcg_ret(p, 0); 1215 } 1216 for (GotoLabel* gl = p->goto_labels; gl; gl = gl->next) { 1217 if (!gl->placed) { 1218 compiler_panic(p->c, gl->first_use, "goto to undefined label"); 1219 } 1220 } 1221 p->goto_labels = saved_goto_labels; 1222 p->cur_switch = saved_switch; 1223 p->computed_goto_emitted = saved_computed_goto; 1224 pcg_func_end(p); 1225 scope_pop(p); 1226 } 1227 1228 /* Parse one external declaration. */ 1229 static void parse_external_decl(Parser* p) { 1230 DeclSpecs specs; 1231 Sym name; 1232 SrcLoc loc; 1233 const Type* base_ty; 1234 Attr* dattrs = NULL; 1235 DeclaratorInfo dinfo; 1236 1237 if (!parse_decl_specs(p, &specs)) { 1238 perr(p, "expected declaration"); 1239 } 1240 if (specs.storage == DS_AUTO && specs.storage_explicit) { 1241 perr(p, "invalid storage-class specifier at file scope"); 1242 } 1243 1244 if (accept_punct(p, ';')) return; 1245 1246 if (specs.storage == DS_TYPEDEF) { 1247 for (;;) { 1248 Sym tname = 0; 1249 SrcLoc tloc = {0, 0, 0}; 1250 const Type* tty = 1251 parse_declarator_full(p, specs.type, 1252 /*allow_abstract=*/0, &tname, &tloc); 1253 validate_decl_type_constraints(p, &specs, tty, 1254 tty && tty->kind == TY_FUNC, 1255 /*is_member=*/0); 1256 if (is_punct(&p->cur, '=')) { 1257 perr(p, "typedef declarator cannot have initializer"); 1258 } 1259 reject_same_scope_redefinition(p, tname, SEK_TYPEDEF, tty); 1260 { 1261 SymEntry* te = scope_define(p, tname, SEK_TYPEDEF, tty); 1262 sym_set_decl(te, DECL_NONE, DS_TYPEDEF, DL_NONE, specs.flags, 1263 DSTATE_DECLARED); 1264 } 1265 (void)tloc; 1266 if (!accept_punct(p, ',')) break; 1267 } 1268 expect_punct(p, ';', "';' after typedef declaration"); 1269 return; 1270 } 1271 1272 base_ty = parse_declarator_full_info(p, specs.type, /*allow_abstract=*/0, 1273 &name, &loc, &dattrs, &dinfo); 1274 1275 if (base_ty && base_ty->kind == TY_FUNC) { 1276 ParamInfo* infos = NULL; 1277 u16 nparams = 0; 1278 const Type* fn_ty; 1279 const ABIFuncInfo* abi; 1280 SymEntry* fent; 1281 1282 fn_ty = base_ty; 1283 infos = dinfo.fn_params; 1284 nparams = dinfo.fn_nparams; 1285 validate_decl_type_constraints(p, &specs, fn_ty, /*is_function=*/1, 1286 /*is_member=*/0); 1287 abi = c_abi_func_info(p->abi, p->pool, fn_ty); 1288 1289 ObjSecId fn_section_id; 1290 u32 fn_decl_flags; 1291 Sym fn_alias_target; 1292 fent = declare_function(p, name, fn_ty, &specs, loc, dattrs, dinfo.asm_label, 1293 &fn_section_id, &fn_decl_flags, &fn_alias_target); 1294 attr_list_append(&fent->attrs, dattrs); 1295 1296 if (is_punct(&p->cur, '{')) { 1297 int suppress_body_codegen = specs.storage == DS_EXTERN && 1298 ((specs.flags | fn_decl_flags) & DF_INLINE); 1299 if (fent->defined) perr(p, "redefinition of function"); 1300 fent->defined = 1; 1301 fent->decl_state = DSTATE_FUNC_DEFINED; 1302 Sym saved_func_name = p->cur_func_name; 1303 const Type* saved_func_ret = p->cur_func_ret; 1304 p->cur_func_name = name; 1305 p->cur_func_ret = fn_ty->fn.ret; 1306 if (suppress_body_codegen) pcg_codegen_suppress_push(p); 1307 parse_function_body(p, fent->v.sym, fn_ty, abi, infos, nparams, loc, 1308 fn_section_id, fn_decl_flags); 1309 if (suppress_body_codegen) pcg_codegen_suppress_pop(p); 1310 p->cur_func_name = saved_func_name; 1311 p->cur_func_ret = saved_func_ret; 1312 return; 1313 } 1314 if (accept_punct(p, ';')) { 1315 if (fn_alias_target != 0) { 1316 SymEntry* te = scope_lookup(p, fn_alias_target); 1317 if (!te) { 1318 const char* nm = kit_sym_str(p->pool->c, fn_alias_target).s; 1319 compiler_panic(p->c, loc, "alias target '%.*s' is undefined", 1320 KIT_SLICE_ARG(kit_slice_cstr(nm ? nm : "?"))); 1321 } 1322 KitCgAlias alias; 1323 memset(&alias, 0, sizeof alias); 1324 alias.display_name = name; 1325 alias.linkage_name = kit_cg_c_linkage_name(p->c, name); 1326 alias.target = te->v.sym; 1327 alias.sym.bind = 1328 (fn_decl_flags & DF_WEAK) ? KIT_SB_WEAK : KIT_SB_GLOBAL; 1329 { 1330 const Decl* fd = decl_get(p->decls, fent->decl_id); 1331 alias.sym.visibility = 1332 fd ? (KitCgVisibility)fd->visibility : KIT_CG_VIS_DEFAULT; 1333 } 1334 if (kit_cg_alias(p->cg, alias) == KIT_CG_SYM_NONE) { 1335 const char* nm = kit_sym_str(p->pool->c, fn_alias_target).s; 1336 compiler_panic(p->c, loc, "alias target '%.*s' is undefined", 1337 KIT_SLICE_ARG(kit_slice_cstr(nm ? nm : "?"))); 1338 } 1339 } 1340 return; 1341 } 1342 perr(p, "expected '{' or ';' after function declarator"); 1343 } 1344 1345 /* Global object declaration. */ 1346 for (;;) { 1347 int has_init = is_punct(&p->cur, '='); 1348 int is_pure_extern = 1349 (specs.storage == DS_EXTERN || specs.storage == DS_REGISTER) && 1350 !has_init; 1351 SymEntry* existing = scope_lookup_current(p, name); 1352 ObjSymId sym = OBJ_SYM_NONE; 1353 ObjSecId section_id = OBJ_SEC_NONE; 1354 SymEntry* e = NULL; 1355 1356 if (existing && existing->kind != SEK_GLOBAL) { 1357 perr(p, "redefinition of identifier"); 1358 } 1359 validate_decl_type_constraints(p, &specs, base_ty, /*is_function=*/0, 1360 /*is_member=*/0); 1361 1362 if (existing && existing->kind == SEK_GLOBAL) { 1363 const Type* composite = NULL; 1364 CSemCheck chk = c_sem_check_redeclaration(p->pool, existing->type, 1365 base_ty, &composite); 1366 if (!chk.ok) perr(p, "%.*s", KIT_SLICE_ARG(kit_slice_cstr(chk.message))); 1367 if (specs.storage == DS_STATIC && existing->linkage == DL_EXTERNAL) { 1368 perr(p, "static declaration follows non-static declaration"); 1369 } 1370 sym = existing->v.sym; 1371 e = existing; 1372 if (has_init && e->defined) { 1373 perr(p, "redefinition of object"); 1374 } 1375 if (composite) e->type = composite; 1376 base_ty = e->type; 1377 } else { 1378 Decl decl_in; 1379 DeclId did; 1380 memset(&decl_in, 0, sizeof decl_in); 1381 decl_in.name = name; 1382 decl_in.asm_name = dinfo.asm_label; 1383 decl_in.type = base_ty; 1384 decl_in.loc = loc; 1385 if (specs.storage == DS_STATIC) { 1386 decl_in.storage = DS_STATIC; 1387 decl_in.linkage = DL_INTERNAL; 1388 } else { 1389 decl_in.storage = DS_EXTERN; 1390 decl_in.linkage = DL_EXTERNAL; 1391 } 1392 decl_in.visibility = 1393 decl_in.linkage == DL_EXTERNAL ? p->default_visibility : SV_DEFAULT; 1394 decl_in.flags = specs.flags & DF_THREAD; 1395 attr_list_to_decl(p->c, p->decls, specs.attrs, &decl_in); 1396 attr_list_to_decl(p->c, p->decls, dattrs, &decl_in); 1397 did = decl_declare(p->decls, &decl_in); 1398 sym = decl_obj_sym(p->decls, did); 1399 section_id = decl_in.section_id; 1400 e = scope_define(p, name, SEK_GLOBAL, base_ty); 1401 e->v.sym = sym; 1402 sym_set_decl(e, did, decl_in.storage, decl_in.linkage, decl_in.flags, 1403 DSTATE_DECLARED); 1404 } 1405 attr_list_append(&e->attrs, dattrs); 1406 1407 u32 attr_align = attrs_pick_aligned(specs.attrs); 1408 { 1409 u32 a2 = attrs_pick_aligned(dattrs); 1410 if (a2 > attr_align) attr_align = a2; 1411 } 1412 u32 align_eff = (specs.align > attr_align) ? specs.align : attr_align; 1413 1414 if (has_init) { 1415 if (e) e->defined = 1; 1416 if (e) e->decl_state = DSTATE_DEFINED; 1417 advance(p); /* '=' */ 1418 if (base_ty && base_ty->kind == TY_ARRAY && base_ty->arr.incomplete) { 1419 const Type* completed = complete_incomplete_array(p, base_ty); 1420 if (completed != base_ty) { 1421 base_ty = completed; 1422 if (e) e->type = base_ty; 1423 } 1424 } 1425 define_static_object(p, sym, section_id, base_ty, specs.quals, 1426 /*has_init=*/1, loc, align_eff); 1427 } else if (!is_pure_extern) { 1428 if (e && e->decl_state == DSTATE_DECLARED) { 1429 e->decl_state = DSTATE_TENTATIVE; 1430 } 1431 define_static_object(p, sym, section_id, base_ty, specs.quals, 1432 /*has_init=*/0, loc, align_eff); 1433 } 1434 1435 if (!accept_punct(p, ',')) break; 1436 dattrs = NULL; 1437 base_ty = parse_declarator_full_info(p, specs.type, /*allow_abstract=*/0, 1438 &name, &loc, &dattrs, &dinfo); 1439 if (base_ty && base_ty->kind == TY_FUNC) { 1440 perr(p, "function declarator in object declaration list"); 1441 } 1442 } 1443 expect_punct(p, ';', "';' after global declaration"); 1444 } 1445 1446 static void parse_file_scope_asm(Parser* p) { 1447 u8* bytes; 1448 size_t nbytes; 1449 advance(p); /* asm / __asm__ */ 1450 for (;;) { 1451 if (is_kw(p, &p->cur, KW_VOLATILE)) { 1452 advance(p); 1453 continue; 1454 } 1455 if (p->cur.kind == TOK_IDENT && p->cur.v.ident == p->sym_volatile_alias) { 1456 advance(p); 1457 continue; 1458 } 1459 break; 1460 } 1461 expect_punct(p, '(', "'(' after file-scope asm"); 1462 if (p->cur.kind != TOK_STR) { 1463 perr(p, "expected string literal in file-scope asm"); 1464 } 1465 bytes = decode_string_literal(p, &p->cur, &nbytes); 1466 advance(p); 1467 expect_punct(p, ')', "')' after file-scope asm"); 1468 expect_punct(p, ';', "';' after file-scope asm"); 1469 if (nbytes > 0) --nbytes; /* drop decode_string_literal's trailing NUL */ 1470 if (pcg_emit_enabled(p)) { 1471 KitSlice asm_src = {{(const char*)bytes}, nbytes}; 1472 kit_cg_file_scope_asm(p->cg, asm_src); 1473 } 1474 } 1475 1476 static void parse_translation_unit(Parser* p) { 1477 while (p->cur.kind != TOK_EOF) { 1478 if (p->cur.kind == TOK_NEWLINE || is_pp_hash(&p->cur)) { 1479 advance(p); 1480 continue; 1481 } 1482 if (is_kw(p, &p->cur, KW_STATIC_ASSERT)) { 1483 parse_static_assert(p); 1484 continue; 1485 } 1486 if (is_kw(p, &p->cur, KW_ASM) || is_kw(p, &p->cur, KW_BUILTIN_ASM)) { 1487 parse_file_scope_asm(p); 1488 continue; 1489 } 1490 if (accept_punct(p, ';')) { 1491 continue; 1492 } 1493 parse_external_decl(p); 1494 } 1495 } 1496 1497 /* ============================================================ 1498 * Entry point 1499 * ============================================================ */ 1500 1501 static u8 parser_default_visibility(KitSymVis vis) { 1502 switch (vis) { 1503 case KIT_SV_HIDDEN: 1504 case KIT_SV_INTERNAL: 1505 return SV_HIDDEN; 1506 case KIT_SV_PROTECTED: 1507 return SV_PROTECTED; 1508 case KIT_SV_DEFAULT: 1509 default: 1510 return SV_DEFAULT; 1511 } 1512 } 1513 1514 void parse_c(Compiler* c, Pool* pool, Pp* pp, DeclTable* decls, CG* cg, 1515 KitSymVis default_visibility) { 1516 Parser p; 1517 CKw i; 1518 u32 syscall_i; 1519 1520 memset(&p, 0, sizeof p); 1521 p.c = c; 1522 p.pp = pp; 1523 p.decls = decls; 1524 p.cg = cg; 1525 p.abi = c; 1526 p.pool = pool; 1527 p.default_visibility = parser_default_visibility(default_visibility); 1528 1529 for (i = (CKw)1; i < KW_COUNT; ++i) { 1530 p.kw_sym[i] = kit_sym_intern(p.pool->c, kit_slice_cstr(kw_names[i])); 1531 } 1532 1533 p.sym_b_alloca = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_alloca")); 1534 p.sym_b_ctz = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_ctz")); 1535 p.sym_b_ctzl = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_ctzl")); 1536 p.sym_b_ctzll = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_ctzll")); 1537 p.sym_b_clz = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_clz")); 1538 p.sym_b_clzl = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_clzl")); 1539 p.sym_b_clzll = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_clzll")); 1540 p.sym_b_trap = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_trap")); 1541 p.sym_b_unreachable = 1542 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_unreachable")); 1543 p.sym_b_return_address = 1544 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_return_address")); 1545 p.sym_b_frame_address = 1546 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_frame_address")); 1547 for (syscall_i = 0; syscall_i < 7u; ++syscall_i) { 1548 char name[16]; 1549 memcpy(name, "__kit_syscall", 13u); 1550 name[13] = (char)('0' + syscall_i); 1551 name[14] = '\0'; 1552 p.sym_kit_syscall[syscall_i] = 1553 kit_sym_intern(p.pool->c, kit_slice_cstr(name)); 1554 } 1555 p.sym_b_memcpy = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_memcpy")); 1556 p.sym_b_memmove = 1557 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_memmove")); 1558 p.sym_b_memcmp = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_memcmp")); 1559 p.sym_b_memset = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_memset")); 1560 p.sym_b_clear_cache = 1561 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin___clear_cache")); 1562 p.sym_b_isnan = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_isnan")); 1563 p.sym_b_fabs = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_fabs")); 1564 p.sym_b_fabsf = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_fabsf")); 1565 p.sym_b_fabsl = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_fabsl")); 1566 p.sym_b_inf = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_inf")); 1567 p.sym_b_inff = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_inff")); 1568 p.sym_b_infl = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_infl")); 1569 p.sym_b_huge_val = 1570 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_huge_val")); 1571 p.sym_b_huge_valf = 1572 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_huge_valf")); 1573 p.sym_b_huge_vall = 1574 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_huge_vall")); 1575 p.sym_b_isless = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_isless")); 1576 p.sym_b_islessequal = 1577 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_islessequal")); 1578 p.sym_b_isgreater = 1579 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_isgreater")); 1580 p.sym_b_isgreaterequal = 1581 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_isgreaterequal")); 1582 p.sym_b_islessgreater = 1583 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_islessgreater")); 1584 p.sym_b_isunordered = 1585 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_isunordered")); 1586 p.sym_func = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__func__")); 1587 p.sym_func_gcc = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__FUNCTION__")); 1588 p.sym_pretty_func_gcc = 1589 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__PRETTY_FUNCTION__")); 1590 p.sym_b_expect = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_expect")); 1591 p.sym_b_offsetof = 1592 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_offsetof")); 1593 p.sym_b_va_list = 1594 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_va_list")); 1595 p.sym_b_va_start = 1596 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_va_start")); 1597 p.sym_b_va_arg = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_va_arg")); 1598 p.sym_b_va_end = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_va_end")); 1599 p.sym_b_va_copy = 1600 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__builtin_va_copy")); 1601 p.sym_attribute = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__attribute__")); 1602 p.sym_volatile_alias = 1603 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__volatile__")); 1604 p.sym_alignof_alias = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__alignof__")); 1605 p.sym_asm_alias = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__asm")); 1606 p.sym_inline_alias = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__inline")); 1607 p.sym_inline_alias2 = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__inline__")); 1608 /* __restrict / __restrict__: GCC keyword spellings of `restrict`. glibc 1609 * headers use these as real keywords (and #undef any fallback macro under 1610 * __GNUC__), so recognize them in the parser, not just via a pp macro. */ 1611 p.sym_restrict_alias = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__restrict")); 1612 p.sym_restrict_alias2 = 1613 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__restrict__")); 1614 p.sym_thread_alias = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__thread")); 1615 p.sym_int128 = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__int128")); 1616 p.sym_int128_t = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__int128_t")); 1617 p.sym_uint128_t = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__uint128_t")); 1618 p.sym_a_load_n = kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_load_n")); 1619 p.sym_a_store_n = 1620 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_store_n")); 1621 p.sym_a_exchange_n = 1622 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_exchange_n")); 1623 p.sym_a_fetch_add = 1624 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_fetch_add")); 1625 p.sym_a_fetch_sub = 1626 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_fetch_sub")); 1627 p.sym_a_fetch_and = 1628 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_fetch_and")); 1629 p.sym_a_fetch_or = 1630 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_fetch_or")); 1631 p.sym_a_fetch_xor = 1632 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_fetch_xor")); 1633 p.sym_a_fetch_nand = 1634 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_fetch_nand")); 1635 p.sym_a_cas_n = 1636 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_compare_exchange_n")); 1637 p.sym_a_always_lock_free = 1638 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_always_lock_free")); 1639 p.sym_a_is_lock_free = 1640 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_is_lock_free")); 1641 p.sym_a_thread_fence = 1642 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_thread_fence")); 1643 p.sym_a_signal_fence = 1644 kit_sym_intern(p.pool->c, KIT_SLICE_LIT("__atomic_signal_fence")); 1645 1646 p.scope = scope_new(&p, NULL); 1647 1648 p.cur = fetch_tok(&p); 1649 1650 parse_translation_unit(&p); 1651 }