ast2.go (33778B)
1 // Copyright 2019 The CC Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package cc // import "modernc.org/cc/v3" 6 7 import ( 8 "fmt" 9 "io" 10 "os" 11 "path/filepath" 12 "sort" 13 "strings" 14 ) 15 16 // Source is a named part of a translation unit. If Value is empty, Name is 17 // interpreted as a path to file containing the source code. 18 type Source struct { 19 Name string 20 Value string 21 DoNotCache bool // Disable caching of this source 22 } 23 24 // Promote returns the type the operands of a binary operation are promoted to 25 // or the type and argument passed in a function call is promoted. 26 func (n *AssignmentExpression) Promote() Type { return n.promote } 27 28 type StructInfo struct { 29 Size uintptr 30 31 Align int 32 } 33 34 // AST represents a translation unit and its related data. 35 type AST struct { 36 Enums map[StringID]Operand // Enumeration constants declared in file scope. 37 Macros map[StringID]*Macro // Macros as defined after parsing. 38 PtrdiffType Type 39 Scope Scope // File scope. 40 SizeType Type 41 StructTypes map[StringID]Type // Tagged struct/union types declared in file scope. 42 // Alignment and size of every struct/union defined in the translation 43 // unit. Valid only after Translate. 44 Structs map[StructInfo]struct{} 45 // TLD contains pruned file scope declarators, ie. either the first one 46 // or the first one that has an initializer. 47 TLD map[*Declarator]struct{} 48 TrailingSeperator StringID // White space and/or comments preceding EOF. 49 TranslationUnit *TranslationUnit 50 WideCharType Type 51 cfg *Config 52 cpp *cpp 53 } 54 55 // Eval returns the operand that represents the value of m, if it expands to a 56 // valid constant expression other than an identifier, or an error, if any. 57 func (n *AST) Eval(m *Macro) (o Operand, err error) { 58 defer func() { 59 if e := recover(); e != nil { 60 o = nil 61 err = fmt.Errorf("%v", e) 62 } 63 }() 64 65 if m.IsFnLike() { 66 return nil, fmt.Errorf("cannot evaluate function-like macro") 67 } 68 69 n.cpp.ctx.cfg.ignoreErrors = true 70 n.cpp.ctx.evalIdentError = true 71 v := n.cpp.eval(m.repl) 72 switch x := v.(type) { 73 case int64: 74 return &operand{abi: &n.cfg.ABI, typ: n.cfg.ABI.Type(LongLong), value: Int64Value(x)}, nil 75 case uint64: 76 return &operand{abi: &n.cfg.ABI, typ: n.cfg.ABI.Type(ULongLong), value: Uint64Value(x)}, nil 77 default: 78 return nil, fmt.Errorf("unexpected value: %T", x) 79 } 80 } 81 82 // Parse preprocesses and parses a translation unit and returns an *AST or 83 // error, if any. 84 // 85 // Search paths listed in includePaths and sysIncludePaths are used to resolve 86 // #include "foo.h" and #include <foo.h> preprocessing directives respectively. 87 // A special search path "@" is interpreted as 'the same directory as where the 88 // file with the #include directive is'. 89 // 90 // The sources should typically provide, usually in this particular order: 91 // 92 // - predefined macros, eg. 93 // 94 // #define __SIZE_TYPE__ long unsigned int 95 // 96 // - built-in declarations, eg. 97 // 98 // int __builtin_printf(char *__format, ...); 99 // 100 // - command-line provided directives, eg. 101 // 102 // #define FOO 103 // #define BAR 42 104 // #undef QUX 105 // 106 // - normal C sources, eg. 107 // 108 // int main() {} 109 // 110 // All search and file paths should be absolute paths. 111 // 112 // If the preprocessed translation unit is empty, the function may return (nil, 113 // nil). 114 // 115 // The parser does only the minimum declarations/identifier resolving necessary 116 // for correct parsing. Redeclarations are not checked. 117 // 118 // Declarators (*Declarator) and StructDeclarators (*StructDeclarator) are 119 // inserted in the appropriate scopes. 120 // 121 // Tagged struct/union specifier definitions (*StructOrUnionSpecifier) are 122 // inserted in the appropriate scopes. 123 // 124 // Tagged enum specifier definitions (*EnumSpecifier) and enumeration constants 125 // (*Enumerator) are inserted in the appropriate scopes. 126 // 127 // Labels (*LabeledStatement) are inserted in the appropriate scopes. 128 func Parse(cfg *Config, includePaths, sysIncludePaths []string, sources []Source) (*AST, error) { 129 return parse(newContext(cfg), includePaths, sysIncludePaths, sources) 130 } 131 132 func parse(ctx *context, includePaths, sysIncludePaths []string, sources []Source) (*AST, error) { 133 if s := ctx.cfg.SharedFunctionDefinitions; s != nil { 134 if s.M == nil { 135 s.M = map[*FunctionDefinition]struct{}{} 136 } 137 if s.m == nil { 138 s.m = map[sharedFunctionDefinitionKey]*FunctionDefinition{} 139 } 140 } 141 if debugWorkingDir || ctx.cfg.DebugWorkingDir { 142 switch wd, err := os.Getwd(); err { 143 case nil: 144 fmt.Fprintf(os.Stderr, "OS working dir: %s\n", wd) 145 default: 146 fmt.Fprintf(os.Stderr, "OS working dir: error %s\n", err) 147 } 148 fmt.Fprintf(os.Stderr, "Config.WorkingDir: %s\n", ctx.cfg.WorkingDir) 149 } 150 if debugIncludePaths || ctx.cfg.DebugIncludePaths { 151 fmt.Fprintf(os.Stderr, "include paths: %v\n", includePaths) 152 fmt.Fprintf(os.Stderr, "system include paths: %v\n", sysIncludePaths) 153 } 154 ctx.includePaths = includePaths 155 ctx.sysIncludePaths = sysIncludePaths 156 var in []source 157 for _, v := range sources { 158 ts, err := cache.get(ctx, v) 159 if err != nil { 160 return nil, err 161 } 162 163 in = append(in, ts) 164 } 165 166 p := newParser(ctx, make(chan *[]Token, 5000)) //DONE benchmark tuned 167 var sep StringID 168 var ssep []byte 169 var seq int32 170 cpp := newCPP(ctx) 171 go func() { 172 173 defer func() { 174 close(p.in) 175 ctx.intMaxWidth = cpp.intMaxWidth() 176 }() 177 178 toks := tokenPool.Get().(*[]Token) 179 *toks = (*toks)[:0] 180 for pline := range cpp.translationPhase4(in) { 181 line := *pline 182 for _, tok := range line { 183 switch tok.char { 184 case ' ', '\n': 185 if ctx.cfg.PreserveOnlyLastNonBlankSeparator { 186 if strings.TrimSpace(tok.value.String()) != "" { 187 sep = tok.value 188 } 189 break 190 } 191 192 switch { 193 case sep != 0: 194 ssep = append(ssep, tok.String()...) 195 default: 196 sep = tok.value 197 ssep = append(ssep[:0], sep.String()...) 198 } 199 default: 200 var t Token 201 t.Rune = tok.char 202 switch { 203 case len(ssep) != 0: 204 t.Sep = dict.id(ssep) 205 default: 206 t.Sep = sep 207 } 208 t.Value = tok.value 209 t.Src = tok.src 210 t.file = tok.file 211 t.macro = tok.macro 212 t.pos = tok.pos 213 seq++ 214 t.seq = seq 215 *toks = append(*toks, t) 216 sep = 0 217 ssep = ssep[:0] 218 } 219 } 220 token4Pool.Put(pline) 221 var c rune 222 if n := len(*toks); n != 0 { 223 c = (*toks)[n-1].Rune 224 } 225 switch c { 226 case STRINGLITERAL, LONGSTRINGLITERAL: 227 // nop 228 default: 229 if len(*toks) != 0 { 230 p.in <- translationPhase5(ctx, toks) 231 toks = tokenPool.Get().(*[]Token) 232 *toks = (*toks)[:0] 233 } 234 } 235 } 236 if len(*toks) != 0 { 237 p.in <- translationPhase5(ctx, toks) 238 } 239 }() 240 241 tu := p.translationUnit() 242 if p.errored { // Must drain 243 go func() { 244 for range p.in { 245 } 246 }() 247 } 248 249 if err := ctx.Err(); err != nil { 250 return nil, err 251 } 252 253 if p.errored && !ctx.cfg.ignoreErrors { 254 return nil, fmt.Errorf("%v: syntax error", p.tok.Position()) 255 } 256 257 if p.scopes != 0 { 258 panic(internalErrorf("invalid scope nesting but no error reported")) 259 } 260 261 ts := sep 262 if len(ssep) != 0 { 263 ts = dict.id(ssep) 264 } 265 return &AST{ 266 Macros: cpp.macros, 267 Scope: p.fileScope, 268 TLD: map[*Declarator]struct{}{}, 269 TrailingSeperator: ts, 270 TranslationUnit: tu, 271 cfg: ctx.cfg, 272 cpp: cpp, 273 }, nil 274 } 275 276 func translationPhase5(ctx *context, toks *[]Token) *[]Token { 277 // [0], 5.1.1.2, 5 278 // 279 // Each source character set member and escape sequence in character 280 // constants and string literals is converted to the corresponding 281 // member of the execution character set; if there is no corresponding 282 // member, it is converted to an implementation- defined member other 283 // than the null (wide) character. 284 for i, tok := range *toks { 285 var cpt cppToken 286 switch tok.Rune { 287 case STRINGLITERAL, LONGSTRINGLITERAL: 288 cpt.char = tok.Rune 289 cpt.value = tok.Value 290 cpt.src = tok.Src 291 cpt.file = tok.file 292 cpt.pos = tok.pos 293 (*toks)[i].Value = dict.sid(stringConst(ctx, cpt)) 294 case CHARCONST, LONGCHARCONST: 295 var cpt cppToken 296 cpt.char = tok.Rune 297 cpt.value = tok.Value 298 cpt.src = tok.Src 299 cpt.file = tok.file 300 cpt.pos = tok.pos 301 switch r := charConst(ctx, cpt); { 302 case r <= 255: 303 (*toks)[i].Value = dict.sid(string(r)) 304 default: 305 switch cpt.char { 306 case CHARCONST: 307 ctx.err(tok.Position(), "invalid character constant: %s", tok.Value) 308 default: 309 (*toks)[i].Value = dict.sid(string(r)) 310 } 311 } 312 } 313 } 314 return toks 315 } 316 317 // Preprocess preprocesses a translation unit and outputs the result to w. 318 // 319 // Please see Parse for the documentation of the other parameters. 320 func Preprocess(cfg *Config, includePaths, sysIncludePaths []string, sources []Source, w io.Writer) error { 321 ctx := newContext(cfg) 322 if debugWorkingDir || ctx.cfg.DebugWorkingDir { 323 switch wd, err := os.Getwd(); err { 324 case nil: 325 fmt.Fprintf(os.Stderr, "OS working dir: %s\n", wd) 326 default: 327 fmt.Fprintf(os.Stderr, "OS working dir: error %s\n", err) 328 } 329 fmt.Fprintf(os.Stderr, "Config.WorkingDir: %s\n", ctx.cfg.WorkingDir) 330 } 331 if debugIncludePaths || ctx.cfg.DebugIncludePaths { 332 fmt.Fprintf(os.Stderr, "include paths: %v\n", includePaths) 333 fmt.Fprintf(os.Stderr, "system include paths: %v\n", sysIncludePaths) 334 } 335 ctx.includePaths = includePaths 336 ctx.sysIncludePaths = sysIncludePaths 337 var in []source 338 for _, v := range sources { 339 ts, err := cache.get(ctx, v) 340 if err != nil { 341 return err 342 } 343 344 in = append(in, ts) 345 } 346 347 var sep StringID 348 cpp := newCPP(ctx) 349 toks := tokenPool.Get().(*[]Token) 350 *toks = (*toks)[:0] 351 for pline := range cpp.translationPhase4(in) { 352 line := *pline 353 for _, tok := range line { 354 switch tok.char { 355 case ' ', '\n': 356 if ctx.cfg.PreserveOnlyLastNonBlankSeparator { 357 if strings.TrimSpace(tok.value.String()) != "" { 358 sep = tok.value 359 } 360 break 361 } 362 363 switch { 364 case sep != 0: 365 sep = dict.sid(sep.String() + tok.String()) 366 default: 367 sep = tok.value 368 } 369 default: 370 var t Token 371 t.Rune = tok.char 372 t.Sep = sep 373 t.Value = tok.value 374 t.Src = tok.src 375 t.file = tok.file 376 t.pos = tok.pos 377 *toks = append(*toks, t) 378 sep = 0 379 } 380 } 381 token4Pool.Put(pline) 382 var c rune 383 if n := len(*toks); n != 0 { 384 c = (*toks)[n-1].Rune 385 } 386 switch c { 387 case STRINGLITERAL, LONGSTRINGLITERAL: 388 // nop 389 default: 390 if len(*toks) != 0 { 391 for _, v := range *translationPhase5(ctx, toks) { 392 if err := wTok(w, v); err != nil { 393 return err 394 } 395 } 396 toks = tokenPool.Get().(*[]Token) 397 *toks = (*toks)[:0] 398 } 399 } 400 } 401 if len(*toks) != 0 { 402 for _, v := range *translationPhase5(ctx, toks) { 403 if err := wTok(w, v); err != nil { 404 return err 405 } 406 } 407 } 408 if _, err := fmt.Fprintln(w); err != nil { 409 return err 410 } 411 return ctx.Err() 412 } 413 414 func wTok(w io.Writer, tok Token) (err error) { 415 switch tok.Rune { 416 case STRINGLITERAL, LONGSTRINGLITERAL: 417 _, err = fmt.Fprintf(w, `%s"%s"`, tok.Sep, cQuotedString(tok.String(), true)) 418 case CHARCONST, LONGCHARCONST: 419 _, err = fmt.Fprintf(w, `%s'%s'`, tok.Sep, cQuotedString(tok.String(), false)) 420 default: 421 _, err = fmt.Fprintf(w, "%s%s", tok.Sep, tok) 422 } 423 return err 424 } 425 426 func cQuotedString(s string, isString bool) []byte { 427 var b []byte 428 for i := 0; i < len(s); i++ { 429 c := s[i] 430 switch c { 431 case '\b': 432 b = append(b, '\\', 'b') 433 continue 434 case '\f': 435 b = append(b, '\\', 'f') 436 continue 437 case '\n': 438 b = append(b, '\\', 'n') 439 continue 440 case '\r': 441 b = append(b, '\\', 'r') 442 continue 443 case '\t': 444 b = append(b, '\\', 't') 445 continue 446 case '\\': 447 b = append(b, '\\', '\\') 448 continue 449 case '"': 450 switch { 451 case isString: 452 b = append(b, '\\', '"') 453 default: 454 b = append(b, '"') 455 } 456 continue 457 case '\'': 458 switch { 459 case isString: 460 b = append(b, '\'') 461 default: 462 b = append(b, '\\', '\'') 463 } 464 continue 465 } 466 467 switch { 468 case c < ' ' || c >= 0x7f: 469 b = append(b, '\\', octal(c>>6), octal(c>>3), octal(c)) 470 default: 471 b = append(b, c) 472 } 473 } 474 return b 475 } 476 477 func octal(b byte) byte { return '0' + b&7 } 478 479 var trcSource = Source{"<builtin-trc>", ` 480 extern void *stderr; 481 int fflush(void *stream); 482 int fprintf(void *stream, const char *format, ...); 483 `, false} 484 485 // Translate parses and typechecks a translation unit and returns an *AST or 486 // error, if any. 487 // 488 // Please see Parse for the documentation of the parameters. 489 func Translate(cfg *Config, includePaths, sysIncludePaths []string, sources []Source) (*AST, error) { 490 if cfg.InjectTracingCode { 491 for i, v := range sources { 492 if filepath.Ext(v.Name) == ".c" { 493 sources = append(append(append([]Source(nil), sources[:i]...), trcSource), sources[i:]...) 494 } 495 } 496 } 497 return translate(newContext(cfg), includePaths, sysIncludePaths, sources) 498 } 499 500 func translate(ctx *context, includePaths, sysIncludePaths []string, sources []Source) (*AST, error) { 501 ast, err := parse(ctx, includePaths, sysIncludePaths, sources) 502 if err != nil { 503 return nil, err 504 } 505 506 if ctx, err = ast.typecheck(); err != nil { 507 return nil, err 508 } 509 510 ast.PtrdiffType = ptrdiffT(ctx, ast.Scope, Token{}) 511 ast.SizeType = sizeT(ctx, ast.Scope, Token{}) 512 ast.WideCharType = wcharT(ctx, ast.Scope, Token{}) 513 return ast, nil 514 } 515 516 // Typecheck determines types of objects and expressions and verifies types are 517 // valid in the context they are used. 518 func (n *AST) Typecheck() error { 519 _, err := n.typecheck() 520 return err 521 } 522 523 func (n *AST) typecheck() (*context, error) { 524 ctx := newContext(n.cfg) 525 if err := ctx.cfg.ABI.sanityCheck(ctx, int(ctx.intMaxWidth), n.Scope); err != nil { 526 return nil, err 527 } 528 529 ctx.intBits = int(ctx.cfg.ABI.Types[Int].Size) * 8 530 ctx.ast = n 531 n.TranslationUnit.check(ctx) 532 n.Structs = ctx.structs 533 var a []int 534 for k := range n.Scope { 535 a = append(a, int(k)) 536 } 537 sort.Ints(a) 538 for _, v := range a { 539 nm := StringID(v) 540 defs := n.Scope[nm] 541 var r, w int 542 for _, v := range defs { 543 switch x := v.(type) { 544 case *Declarator: 545 r += x.Read 546 w += x.Write 547 } 548 } 549 for _, v := range defs { 550 switch x := v.(type) { 551 case *Declarator: 552 x.Read = r 553 x.Write = w 554 } 555 } 556 var pruned *Declarator 557 for _, v := range defs { 558 switch x := v.(type) { 559 case *Declarator: 560 //TODO check compatible types 561 switch { 562 case x.IsExtern() && !x.fnDef: 563 // nop 564 case pruned == nil: 565 pruned = x 566 case pruned.hasInitializer && x.hasInitializer: 567 ctx.errNode(x, "multiple initializers for the same symbol") 568 continue 569 case pruned.fnDef && x.fnDef: 570 ctx.errNode(x, "multiple function definitions") 571 continue 572 case x.hasInitializer || x.fnDef: 573 pruned = x 574 } 575 } 576 } 577 if pruned == nil { 578 continue 579 } 580 581 n.TLD[pruned] = struct{}{} 582 } 583 n.Enums = ctx.enums 584 n.StructTypes = ctx.structTypes 585 return ctx, ctx.Err() 586 } 587 588 func (n *AlignmentSpecifier) align() int { 589 switch n.Case { 590 case AlignmentSpecifierAlignasType: // "_Alignas" '(' TypeName ')' 591 return n.TypeName.Type().Align() 592 case AlignmentSpecifierAlignasExpr: // "_Alignas" '(' ConstantExpression ')' 593 return n.ConstantExpression.Operand.Type().Align() 594 default: 595 panic(internalError()) 596 } 597 } 598 599 // Closure reports the variables closed over by a nested function (case 600 // BlockItemFuncDef). 601 func (n *BlockItem) Closure() map[StringID]struct{} { return n.closure } 602 603 // FunctionDefinition returns the nested function (case BlockItemFuncDef). 604 func (n *BlockItem) FunctionDefinition() *FunctionDefinition { return n.fn } 605 606 func (n *Declarator) IsStatic() bool { return n.td != nil && n.td.static() } 607 608 // IsImplicit reports whether n was not declared nor defined, only inferred. 609 func (n *Declarator) IsImplicit() bool { return n.implicit } 610 611 func (n *Declarator) isVisible(at int32) bool { return at == 0 || n.DirectDeclarator.ends() < at } 612 613 func (n *Declarator) setLHS(lhs *Declarator) { 614 if n == nil { 615 return 616 } 617 618 if n.lhs == nil { 619 n.lhs = map[*Declarator]struct{}{} 620 } 621 n.lhs[lhs] = struct{}{} 622 } 623 624 // LHS reports which declarators n is used in assignment RHS or which function 625 // declarators n is used in a function argument. To collect this information, 626 // TrackAssignments in Config must be set during type checking. 627 // The returned map may contain a nil key. That means that n is assigned to a 628 // declarator not known at typechecking time. 629 func (n *Declarator) LHS() map[*Declarator]struct{} { return n.lhs } 630 631 // Called reports whether n is involved in expr in expr(callArgs). 632 func (n *Declarator) Called() bool { return n.called } 633 634 // FunctionDefinition returns the function definition associated with n, if any. 635 func (n *Declarator) FunctionDefinition() *FunctionDefinition { 636 return n.funcDefinition 637 } 638 639 // NameTok returns n's declaring name token. 640 func (n *Declarator) NameTok() (r Token) { 641 if n == nil || n.DirectDeclarator == nil { 642 return r 643 } 644 645 return n.DirectDeclarator.NameTok() 646 } 647 648 // LexicalScope returns the lexical scope of n. 649 func (n *Declarator) LexicalScope() Scope { return n.DirectDeclarator.lexicalScope } 650 651 // Name returns n's declared name. 652 func (n *Declarator) Name() StringID { 653 if n == nil || n.DirectDeclarator == nil { 654 return 0 655 } 656 657 return n.DirectDeclarator.Name() 658 } 659 660 // ParamScope returns the scope in which n's function parameters are declared 661 // if the underlying type of n is a function or nil otherwise. If n is part of 662 // a function definition the scope is the same as the scope of the function 663 // body. 664 func (n *Declarator) ParamScope() Scope { 665 if n == nil { 666 return nil 667 } 668 669 return n.DirectDeclarator.ParamScope() 670 } 671 672 // Type returns the type of n. 673 func (n *Declarator) Type() Type { return n.typ } 674 675 // IsExtern reports whether n was declared with storage class specifier 'extern'. 676 func (n *Declarator) IsExtern() bool { return n.td != nil && n.td.extern() } 677 678 func (n *DeclarationSpecifiers) auto() bool { return n != nil && n.class&fAuto != 0 } 679 func (n *DeclarationSpecifiers) extern() bool { return n != nil && n.class&fExtern != 0 } 680 func (n *DeclarationSpecifiers) register() bool { return n != nil && n.class&fRegister != 0 } 681 func (n *DeclarationSpecifiers) static() bool { return n != nil && n.class&fStatic != 0 } 682 func (n *DeclarationSpecifiers) threadLocal() bool { return n != nil && n.class&fThreadLocal != 0 } 683 func (n *DeclarationSpecifiers) typedef() bool { return n != nil && n.class&fTypedef != 0 } 684 685 func (n *DirectAbstractDeclarator) TypeQualifier() Type { return n.typeQualifiers } 686 687 func (n *DirectDeclarator) ends() int32 { 688 switch n.Case { 689 case DirectDeclaratorIdent: // IDENTIFIER 690 return n.Token.seq 691 case DirectDeclaratorDecl: // '(' Declarator ')' 692 return n.Token2.seq 693 case DirectDeclaratorArr: // DirectDeclarator '[' TypeQualifierList AssignmentExpression ']' 694 return n.Token2.seq 695 case DirectDeclaratorStaticArr: // DirectDeclarator '[' "static" TypeQualifierList AssignmentExpression ']' 696 return n.Token3.seq 697 case DirectDeclaratorArrStatic: // DirectDeclarator '[' TypeQualifierList "static" AssignmentExpression ']' 698 return n.Token3.seq 699 case DirectDeclaratorStar: // DirectDeclarator '[' TypeQualifierList '*' ']' 700 return n.Token3.seq 701 case DirectDeclaratorFuncParam: // DirectDeclarator '(' ParameterTypeList ')' 702 return n.Token2.seq 703 case DirectDeclaratorFuncIdent: // DirectDeclarator '(' IdentifierList ')' 704 return n.Token2.seq 705 default: 706 panic(internalError()) 707 } 708 } 709 710 func (n *DirectDeclarator) TypeQualifier() Type { return n.typeQualifiers } 711 712 // NameTok returns n's declarin name token. 713 func (n *DirectDeclarator) NameTok() (r Token) { 714 for { 715 if n == nil { 716 return r 717 } 718 719 switch n.Case { 720 case DirectDeclaratorIdent: // IDENTIFIER 721 return n.Token 722 case DirectDeclaratorDecl: // '(' Declarator ')' 723 return n.Declarator.NameTok() 724 default: 725 n = n.DirectDeclarator 726 } 727 } 728 } 729 730 // Name returns n's declared name. 731 func (n *DirectDeclarator) Name() StringID { 732 for { 733 if n == nil { 734 return 0 735 } 736 737 switch n.Case { 738 case DirectDeclaratorIdent: // IDENTIFIER 739 return n.Token.Value 740 case DirectDeclaratorDecl: // '(' Declarator ')' 741 return n.Declarator.Name() 742 default: 743 n = n.DirectDeclarator 744 } 745 } 746 } 747 748 // ParamScope returns the innermost scope in which function parameters are 749 // declared for Case DirectDeclaratorFuncParam or DirectDeclaratorFuncIdent or 750 // nil otherwise. 751 func (n *DirectDeclarator) ParamScope() Scope { 752 if n == nil { 753 return nil 754 } 755 756 switch n.Case { 757 case DirectDeclaratorIdent: // IDENTIFIER 758 return nil 759 case DirectDeclaratorDecl: // '(' Declarator ')' 760 return n.Declarator.ParamScope() 761 case DirectDeclaratorArr: // DirectDeclarator '[' TypeQualifierList AssignmentExpression ']' 762 return n.DirectDeclarator.ParamScope() 763 case DirectDeclaratorStaticArr: // DirectDeclarator '[' "static" TypeQualifierList AssignmentExpression ']' 764 return n.DirectDeclarator.ParamScope() 765 case DirectDeclaratorArrStatic: // DirectDeclarator '[' TypeQualifierList "static" AssignmentExpression ']' 766 return n.DirectDeclarator.ParamScope() 767 case DirectDeclaratorStar: // DirectDeclarator '[' TypeQualifierList '*' ']' 768 return n.DirectDeclarator.ParamScope() 769 case DirectDeclaratorFuncParam: // DirectDeclarator '(' ParameterTypeList ')' 770 if s := n.DirectDeclarator.ParamScope(); s != nil { 771 return s 772 } 773 774 return n.paramScope 775 case DirectDeclaratorFuncIdent: // DirectDeclarator '(' IdentifierList ')' 776 if s := n.DirectDeclarator.ParamScope(); s != nil { 777 return s 778 } 779 780 return n.paramScope 781 default: 782 panic(internalError()) 783 } 784 } 785 786 func (n *Enumerator) isVisible(at int32) bool { return n.Token.seq < at } 787 788 func (n *EnumSpecifier) Type() Type { return n.typ } 789 790 // Promote returns the type the operands of the binary operation are promoted to. 791 func (n *EqualityExpression) Promote() Type { return n.promote } 792 793 // Promote returns the type the operands of the binary operation are promoted to. 794 func (n *AdditiveExpression) Promote() Type { return n.promote } 795 796 // Promote returns the type the operands of the binary operation are promoted to. 797 func (n *MultiplicativeExpression) Promote() Type { return n.promote } 798 799 // Promote returns the type the operands of the binary operation are promoted to. 800 func (n *InclusiveOrExpression) Promote() Type { return n.promote } 801 802 // Promote returns the type the operands of the binary operation are promoted to. 803 func (n *ExclusiveOrExpression) Promote() Type { return n.promote } 804 805 // Promote returns the type the operands of the binary operation are promoted to. 806 func (n *AndExpression) Promote() Type { return n.promote } 807 808 func (n *InitDeclarator) Value() *InitializerValue { return n.initializer } 809 810 // FirstDesignatorField returns the first field a designator of an union type 811 // denotes, if any. 812 func (n *Initializer) FirstDesignatorField() Field { return n.field0 } 813 814 // TrailingComma returns the comma token following n, if any. 815 func (n *Initializer) TrailingComma() *Token { return n.trailingComma } 816 817 // IsConst reports whether n is constant. 818 func (n *Initializer) IsConst() bool { return n == nil || n.isConst } 819 820 // IsZero reports whether n is a zero value. 821 func (n *Initializer) IsZero() bool { return n == nil || n.isZero } 822 823 // List returns n as a flattened list of all items that are case 824 // InitializerExpr. 825 func (n *Initializer) List() []*Initializer { return n.list } 826 827 // Parent returns the parent of n, if any. 828 func (n *Initializer) Parent() *Initializer { return n.parent } 829 830 // Type returns the type this initializer initializes. 831 func (n *Initializer) Type() Type { return n.typ } 832 833 // IsConst reports whether n is constant. 834 func (n *InitializerList) IsConst() bool { return n == nil || n.isConst } 835 836 // IsZero reports whether n is a zero value. 837 func (n *InitializerList) IsZero() bool { return n == nil || n.isZero } 838 839 // List returns n as a flattened list of all items that are case 840 // InitializerExpr. 841 func (n *InitializerList) List() []*Initializer { 842 if n == nil { 843 return nil 844 } 845 846 return n.list 847 } 848 849 // IsEmpty reprts whether n is an empty list. 850 func (n *InitializerList) IsEmpty() bool { return len(n.list) == 0 } 851 852 // LexicalScope returns the lexical scope of n. 853 func (n *JumpStatement) LexicalScope() Scope { return n.lexicalScope } 854 855 // LexicalScope returns the lexical scope of n. 856 func (n *LabeledStatement) LexicalScope() Scope { return n.lexicalScope } 857 858 func (n *ParameterDeclaration) Type() Type { return n.typ } 859 860 func (n *Pointer) TypeQualifier() Type { return n.typeQualifiers } 861 862 // ResolvedIn reports which scope the identifier of cases 863 // PrimaryExpressionIdent, PrimaryExpressionEnum were resolved in, if any. 864 func (n *PrimaryExpression) ResolvedIn() Scope { return n.resolvedIn } 865 866 // ResolvedTo reports which Node the identifier of cases 867 // PrimaryExpressionIdent, PrimaryExpressionEnum resolved to, if any. 868 func (n *PrimaryExpression) ResolvedTo() Node { return n.resolvedTo } 869 870 // Promote returns the type the operands of the binary operation are promoted to. 871 func (n *RelationalExpression) Promote() Type { return n.promote } 872 873 // Cases returns the cases a switch statement consist of, in source order. 874 func (n *SelectionStatement) Cases() []*LabeledStatement { return n.cases } 875 876 // Promote returns the type the shift count operand is promoted to. 877 func (n *ShiftExpression) Promote() Type { return n.promote } 878 879 func (n *StructOrUnionSpecifier) Type() Type { return n.typ } 880 881 // Promote returns the type the type the switch expression is promoted to. 882 func (n *SelectionStatement) Promote() Type { return n.promote } 883 884 // Type returns the type of n. 885 func (n *TypeName) Type() Type { return n.typ } 886 887 // // LexicalScope returns the lexical scope of n. 888 // func (n *AttributeValue) LexicalScope() Scope { return n.lexicalScope } 889 890 // // Scope returns n's scope. 891 // func (n *CompoundStatement) Scope() Scope { return n.scope } 892 893 // // LexicalScope returns the lexical scope of n. 894 // func (n *Designator) LexicalScope() Scope { return n.lexicalScope } 895 896 // // LexicalScope returns the lexical scope of n. 897 // func (n *DirectDeclarator) LexicalScope() Scope { return n.lexicalScope } 898 899 // LexicalScope returns the lexical scope of n. 900 func (n *EnumSpecifier) LexicalScope() Scope { return n.lexicalScope } 901 902 // // LexicalScope returns the lexical scope of n. 903 // func (n *IdentifierList) LexicalScope() Scope { return n.lexicalScope } 904 905 // // LexicalScope returns the lexical scope of n. 906 // func (n *PrimaryExpression) LexicalScope() Scope { return n.lexicalScope } 907 908 // // LexicalScope returns the lexical scope of n. 909 // func (n *StructOrUnionSpecifier) LexicalScope() Scope { return n.lexicalScope } 910 911 // // ResolvedIn reports which scope the identifier of case 912 // // TypeSpecifierTypedefName was resolved in, if any. 913 // func (n *TypeSpecifier) ResolvedIn() Scope { return n.resolvedIn } 914 915 func (n *TypeSpecifier) list() (r []*TypeSpecifier) { 916 switch n.Case { 917 case TypeSpecifierAtomic: 918 return n.AtomicTypeSpecifier.list 919 default: 920 return []*TypeSpecifier{n} 921 } 922 } 923 924 // // LexicalScope returns the lexical scope of n. 925 // func (n *UnaryExpression) LexicalScope() Scope { return n.lexicalScope } 926 927 func (n *UnaryExpression) Declarator() *Declarator { 928 switch n.Case { 929 case UnaryExpressionPostfix: // PostfixExpression 930 return n.PostfixExpression.Declarator() 931 default: 932 return nil 933 } 934 } 935 936 func (n *PostfixExpression) Declarator() *Declarator { 937 switch n.Case { 938 case PostfixExpressionPrimary: // PrimaryExpression 939 return n.PrimaryExpression.Declarator() 940 default: 941 return nil 942 } 943 } 944 945 func (n *PrimaryExpression) Declarator() *Declarator { 946 switch n.Case { 947 case PrimaryExpressionIdent: // IDENTIFIER 948 if n.Operand != nil { 949 return n.Operand.Declarator() 950 } 951 952 return nil 953 case PrimaryExpressionExpr: // '(' Expression ')' 954 return n.Expression.Declarator() 955 default: 956 return nil 957 } 958 } 959 960 func (n *Expression) Declarator() *Declarator { 961 switch n.Case { 962 case ExpressionAssign: // AssignmentExpression 963 return n.AssignmentExpression.Declarator() 964 default: 965 return nil 966 } 967 } 968 969 func (n *AssignmentExpression) Declarator() *Declarator { 970 switch n.Case { 971 case AssignmentExpressionCond: // ConditionalExpression 972 return n.ConditionalExpression.Declarator() 973 default: 974 return nil 975 } 976 } 977 978 func (n *ConditionalExpression) Declarator() *Declarator { 979 switch n.Case { 980 case ConditionalExpressionLOr: // LogicalOrExpression 981 return n.LogicalOrExpression.Declarator() 982 default: 983 return nil 984 } 985 } 986 987 func (n *LogicalOrExpression) Declarator() *Declarator { 988 switch n.Case { 989 case LogicalOrExpressionLAnd: // LogicalAndExpression 990 return n.LogicalAndExpression.Declarator() 991 default: 992 return nil 993 } 994 } 995 996 func (n *LogicalAndExpression) Declarator() *Declarator { 997 switch n.Case { 998 case LogicalAndExpressionOr: // InclusiveOrExpression 999 return n.InclusiveOrExpression.Declarator() 1000 default: 1001 return nil 1002 } 1003 } 1004 1005 func (n *InclusiveOrExpression) Declarator() *Declarator { 1006 switch n.Case { 1007 case InclusiveOrExpressionXor: // ExclusiveOrExpression 1008 return n.ExclusiveOrExpression.Declarator() 1009 default: 1010 return nil 1011 } 1012 } 1013 1014 func (n *ExclusiveOrExpression) Declarator() *Declarator { 1015 switch n.Case { 1016 case ExclusiveOrExpressionAnd: // AndExpression 1017 return n.AndExpression.Declarator() 1018 default: 1019 return nil 1020 } 1021 } 1022 1023 func (n *AndExpression) Declarator() *Declarator { 1024 switch n.Case { 1025 case AndExpressionEq: // EqualityExpression 1026 return n.EqualityExpression.Declarator() 1027 default: 1028 return nil 1029 } 1030 } 1031 1032 func (n *EqualityExpression) Declarator() *Declarator { 1033 switch n.Case { 1034 case EqualityExpressionRel: // RelationalExpression 1035 return n.RelationalExpression.Declarator() 1036 default: 1037 return nil 1038 } 1039 } 1040 1041 func (n *RelationalExpression) Declarator() *Declarator { 1042 switch n.Case { 1043 case RelationalExpressionShift: // ShiftExpression 1044 return n.ShiftExpression.Declarator() 1045 default: 1046 return nil 1047 } 1048 } 1049 1050 func (n *ShiftExpression) Declarator() *Declarator { 1051 switch n.Case { 1052 case ShiftExpressionAdd: // AdditiveExpression 1053 return n.AdditiveExpression.Declarator() 1054 default: 1055 return nil 1056 } 1057 } 1058 1059 func (n *AdditiveExpression) Declarator() *Declarator { 1060 switch n.Case { 1061 case AdditiveExpressionMul: // MultiplicativeExpression 1062 return n.MultiplicativeExpression.Declarator() 1063 default: 1064 return nil 1065 } 1066 } 1067 1068 func (n *MultiplicativeExpression) Declarator() *Declarator { 1069 switch n.Case { 1070 case MultiplicativeExpressionCast: // CastExpression 1071 return n.CastExpression.Declarator() 1072 default: 1073 return nil 1074 } 1075 } 1076 1077 func (n *CastExpression) Declarator() *Declarator { 1078 switch n.Case { 1079 case CastExpressionUnary: // UnaryExpression 1080 return n.UnaryExpression.Declarator() 1081 default: 1082 return nil 1083 } 1084 } 1085 1086 // Has reports whether n has any of attributes in key. 1087 func (n *AttributeSpecifier) Has(key ...StringID) (*ExpressionList, bool) { 1088 if n == nil { 1089 return nil, false 1090 } 1091 1092 for list := n.AttributeValueList; list != nil; list = list.AttributeValueList { 1093 av := list.AttributeValue 1094 for _, k := range key { 1095 if av.Token.Value == k { 1096 switch av.Case { 1097 case AttributeValueIdent: // IDENTIFIER 1098 return nil, true 1099 case AttributeValueExpr: // IDENTIFIER '(' ExpressionList ')' 1100 return av.ExpressionList, true 1101 } 1102 } 1103 } 1104 } 1105 return nil, false 1106 } 1107 1108 // Has reports whether n has any of attributes in key. 1109 func (n *AttributeSpecifierList) Has(key ...StringID) (*ExpressionList, bool) { 1110 for ; n != nil; n = n.AttributeSpecifierList { 1111 if exprList, ok := n.AttributeSpecifier.Has(key...); ok { 1112 return exprList, ok 1113 } 1114 } 1115 return nil, false 1116 } 1117 1118 // Parent returns the CompoundStatement that contains n, if any. 1119 func (n *CompoundStatement) Parent() *CompoundStatement { return n.parent } 1120 1121 // IsJumpTarget returns whether n or any of its children contain a named 1122 // labeled statement. 1123 func (n *CompoundStatement) IsJumpTarget() bool { return n.isJumpTarget } 1124 1125 func (n *CompoundStatement) hasLabel() { 1126 for ; n != nil; n = n.parent { 1127 n.isJumpTarget = true 1128 } 1129 } 1130 1131 // Declarations returns the list of declarations in n. 1132 func (n *CompoundStatement) Declarations() []*Declaration { return n.declarations } 1133 1134 // Children returns the list of n's children. 1135 func (n *CompoundStatement) Children() []*CompoundStatement { return n.children } 1136 1137 // CompoundStatements returns the list of compound statements in n. 1138 func (n *FunctionDefinition) CompoundStatements() []*CompoundStatement { return n.compoundStatements } 1139 1140 // CompoundStatement returns the block containing n. 1141 func (n *LabeledStatement) CompoundStatement() *CompoundStatement { return n.block } 1142 1143 // LabeledStatements returns labeled statements of n. 1144 func (n *CompoundStatement) LabeledStatements() []*LabeledStatement { return n.labeledStmts } 1145 1146 // HasInitializer reports whether d has an initializator. 1147 func (n *Declarator) HasInitializer() bool { return n.hasInitializer } 1148 1149 // Context reports the statement, if any, a break or continue belongs to. Valid 1150 // only after typecheck and for n.Case == JumpStatementBreak or 1151 // JumpStatementContinue. 1152 func (n *JumpStatement) Context() Node { return n.context } 1153 1154 // IsFunctionPrototype reports whether n is a function prototype. 1155 func (n *Declarator) IsFunctionPrototype() bool { 1156 return n != nil && n.Type() != nil && n.Type().Kind() == Function && !n.fnDef && !n.IsParameter 1157 } 1158 1159 // DeclarationSpecifiers returns the declaration specifiers associated with n or nil. 1160 func (n *Declarator) DeclarationSpecifiers() *DeclarationSpecifiers { 1161 if x, ok := n.td.(*DeclarationSpecifiers); ok { 1162 return x 1163 } 1164 1165 return nil 1166 } 1167 1168 // SpecifierQualifierList returns the specifier qualifer list associated with n or nil. 1169 func (n *Declarator) SpecifierQualifierList() *SpecifierQualifierList { 1170 if x, ok := n.td.(*SpecifierQualifierList); ok { 1171 return x 1172 } 1173 1174 return nil 1175 } 1176 1177 // TypeQualifier returns the type qualifiers associated with n or nil. 1178 func (n *Declarator) TypeQualifiers() *TypeQualifiers { 1179 if x, ok := n.td.(*TypeQualifiers); ok { 1180 return x 1181 } 1182 1183 return nil 1184 } 1185 1186 // StructDeclaration returns the struct declaration associated with n. 1187 func (n *StructDeclarator) StructDeclaration() *StructDeclaration { return n.decl }