parser.go 23 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213
  1. package parser
  2. import (
  3. "fmt"
  4. "io"
  5. "sort"
  6. "strconv"
  7. "github.com/d5/tengo/v2/token"
  8. )
  9. type bailout struct{}
  10. var stmtStart = map[token.Token]bool{
  11. token.Break: true,
  12. token.Continue: true,
  13. token.For: true,
  14. token.If: true,
  15. token.Return: true,
  16. token.Export: true,
  17. }
  18. // Error represents a parser error.
  19. type Error struct {
  20. Pos SourceFilePos
  21. Msg string
  22. }
  23. func (e Error) Error() string {
  24. if e.Pos.Filename != "" || e.Pos.IsValid() {
  25. return fmt.Sprintf("Parse Error: %s\n\tat %s", e.Msg, e.Pos)
  26. }
  27. return fmt.Sprintf("Parse Error: %s", e.Msg)
  28. }
  29. // ErrorList is a collection of parser errors.
  30. type ErrorList []*Error
  31. // Add adds a new parser error to the collection.
  32. func (p *ErrorList) Add(pos SourceFilePos, msg string) {
  33. *p = append(*p, &Error{pos, msg})
  34. }
  35. // Len returns the number of elements in the collection.
  36. func (p ErrorList) Len() int {
  37. return len(p)
  38. }
  39. func (p ErrorList) Swap(i, j int) {
  40. p[i], p[j] = p[j], p[i]
  41. }
  42. func (p ErrorList) Less(i, j int) bool {
  43. e := &p[i].Pos
  44. f := &p[j].Pos
  45. if e.Filename != f.Filename {
  46. return e.Filename < f.Filename
  47. }
  48. if e.Line != f.Line {
  49. return e.Line < f.Line
  50. }
  51. if e.Column != f.Column {
  52. return e.Column < f.Column
  53. }
  54. return p[i].Msg < p[j].Msg
  55. }
  56. // Sort sorts the collection.
  57. func (p ErrorList) Sort() {
  58. sort.Sort(p)
  59. }
  60. func (p ErrorList) Error() string {
  61. switch len(p) {
  62. case 0:
  63. return "no errors"
  64. case 1:
  65. return p[0].Error()
  66. }
  67. return fmt.Sprintf("%s (and %d more errors)", p[0], len(p)-1)
  68. }
  69. // Err returns an error.
  70. func (p ErrorList) Err() error {
  71. if len(p) == 0 {
  72. return nil
  73. }
  74. return p
  75. }
  76. // Parser parses the Tengo source files. It's based on Go's parser
  77. // implementation.
  78. type Parser struct {
  79. file *SourceFile
  80. errors ErrorList
  81. scanner *Scanner
  82. pos Pos
  83. token token.Token
  84. tokenLit string
  85. exprLevel int // < 0: in control clause, >= 0: in expression
  86. syncPos Pos // last sync position
  87. syncCount int // number of advance calls without progress
  88. trace bool
  89. indent int
  90. traceOut io.Writer
  91. }
  92. // NewParser creates a Parser.
  93. func NewParser(file *SourceFile, src []byte, trace io.Writer) *Parser {
  94. p := &Parser{
  95. file: file,
  96. trace: trace != nil,
  97. traceOut: trace,
  98. }
  99. p.scanner = NewScanner(p.file, src,
  100. func(pos SourceFilePos, msg string) {
  101. p.errors.Add(pos, msg)
  102. }, 0)
  103. p.next()
  104. return p
  105. }
  106. // ParseFile parses the source and returns an AST file unit.
  107. func (p *Parser) ParseFile() (file *File, err error) {
  108. defer func() {
  109. if e := recover(); e != nil {
  110. if _, ok := e.(bailout); !ok {
  111. panic(e)
  112. }
  113. }
  114. p.errors.Sort()
  115. err = p.errors.Err()
  116. }()
  117. if p.trace {
  118. defer untracep(tracep(p, "File"))
  119. }
  120. if p.errors.Len() > 0 {
  121. return nil, p.errors.Err()
  122. }
  123. stmts := p.parseStmtList()
  124. if p.errors.Len() > 0 {
  125. return nil, p.errors.Err()
  126. }
  127. file = &File{
  128. InputFile: p.file,
  129. Stmts: stmts,
  130. }
  131. return
  132. }
  133. func (p *Parser) parseExpr() Expr {
  134. if p.trace {
  135. defer untracep(tracep(p, "Expression"))
  136. }
  137. expr := p.parseBinaryExpr(token.LowestPrec + 1)
  138. // ternary conditional expression
  139. if p.token == token.Question {
  140. return p.parseCondExpr(expr)
  141. }
  142. return expr
  143. }
  144. func (p *Parser) parseBinaryExpr(prec1 int) Expr {
  145. if p.trace {
  146. defer untracep(tracep(p, "BinaryExpression"))
  147. }
  148. x := p.parseUnaryExpr()
  149. for {
  150. op, prec := p.token, p.token.Precedence()
  151. if prec < prec1 {
  152. return x
  153. }
  154. pos := p.expect(op)
  155. y := p.parseBinaryExpr(prec + 1)
  156. x = &BinaryExpr{
  157. LHS: x,
  158. RHS: y,
  159. Token: op,
  160. TokenPos: pos,
  161. }
  162. }
  163. }
  164. func (p *Parser) parseCondExpr(cond Expr) Expr {
  165. questionPos := p.expect(token.Question)
  166. trueExpr := p.parseExpr()
  167. colonPos := p.expect(token.Colon)
  168. falseExpr := p.parseExpr()
  169. return &CondExpr{
  170. Cond: cond,
  171. True: trueExpr,
  172. False: falseExpr,
  173. QuestionPos: questionPos,
  174. ColonPos: colonPos,
  175. }
  176. }
  177. func (p *Parser) parseUnaryExpr() Expr {
  178. if p.trace {
  179. defer untracep(tracep(p, "UnaryExpression"))
  180. }
  181. switch p.token {
  182. case token.Add, token.Sub, token.Not, token.Xor:
  183. pos, op := p.pos, p.token
  184. p.next()
  185. x := p.parseUnaryExpr()
  186. return &UnaryExpr{
  187. Token: op,
  188. TokenPos: pos,
  189. Expr: x,
  190. }
  191. }
  192. return p.parsePrimaryExpr()
  193. }
  194. func (p *Parser) parsePrimaryExpr() Expr {
  195. if p.trace {
  196. defer untracep(tracep(p, "PrimaryExpression"))
  197. }
  198. x := p.parseOperand()
  199. L:
  200. for {
  201. switch p.token {
  202. case token.Period:
  203. p.next()
  204. switch p.token {
  205. case token.Ident:
  206. x = p.parseSelector(x)
  207. default:
  208. pos := p.pos
  209. p.errorExpected(pos, "selector")
  210. p.advance(stmtStart)
  211. return &BadExpr{From: pos, To: p.pos}
  212. }
  213. case token.LBrack:
  214. x = p.parseIndexOrSlice(x)
  215. case token.LParen:
  216. x = p.parseCall(x)
  217. default:
  218. break L
  219. }
  220. }
  221. return x
  222. }
  223. func (p *Parser) parseCall(x Expr) *CallExpr {
  224. if p.trace {
  225. defer untracep(tracep(p, "Call"))
  226. }
  227. lparen := p.expect(token.LParen)
  228. p.exprLevel++
  229. var list []Expr
  230. var ellipsis Pos
  231. for p.token != token.RParen && p.token != token.EOF && !ellipsis.IsValid() {
  232. list = append(list, p.parseExpr())
  233. if p.token == token.Ellipsis {
  234. ellipsis = p.pos
  235. p.next()
  236. }
  237. if !p.expectComma(token.RParen, "call argument") {
  238. break
  239. }
  240. }
  241. p.exprLevel--
  242. rparen := p.expect(token.RParen)
  243. return &CallExpr{
  244. Func: x,
  245. LParen: lparen,
  246. RParen: rparen,
  247. Ellipsis: ellipsis,
  248. Args: list,
  249. }
  250. }
  251. func (p *Parser) expectComma(closing token.Token, want string) bool {
  252. if p.token == token.Comma {
  253. p.next()
  254. if p.token == closing {
  255. p.errorExpected(p.pos, want)
  256. return false
  257. }
  258. return true
  259. }
  260. if p.token == token.Semicolon && p.tokenLit == "\n" {
  261. p.next()
  262. }
  263. return false
  264. }
  265. func (p *Parser) parseIndexOrSlice(x Expr) Expr {
  266. if p.trace {
  267. defer untracep(tracep(p, "IndexOrSlice"))
  268. }
  269. lbrack := p.expect(token.LBrack)
  270. p.exprLevel++
  271. var index [2]Expr
  272. if p.token != token.Colon {
  273. index[0] = p.parseExpr()
  274. }
  275. numColons := 0
  276. if p.token == token.Colon {
  277. numColons++
  278. p.next()
  279. if p.token != token.RBrack && p.token != token.EOF {
  280. index[1] = p.parseExpr()
  281. }
  282. }
  283. p.exprLevel--
  284. rbrack := p.expect(token.RBrack)
  285. if numColons > 0 {
  286. // slice expression
  287. return &SliceExpr{
  288. Expr: x,
  289. LBrack: lbrack,
  290. RBrack: rbrack,
  291. Low: index[0],
  292. High: index[1],
  293. }
  294. }
  295. return &IndexExpr{
  296. Expr: x,
  297. LBrack: lbrack,
  298. RBrack: rbrack,
  299. Index: index[0],
  300. }
  301. }
  302. func (p *Parser) parseSelector(x Expr) Expr {
  303. if p.trace {
  304. defer untracep(tracep(p, "Selector"))
  305. }
  306. sel := p.parseIdent()
  307. return &SelectorExpr{Expr: x, Sel: &StringLit{
  308. Value: sel.Name,
  309. ValuePos: sel.NamePos,
  310. Literal: sel.Name,
  311. }}
  312. }
  313. func (p *Parser) parseOperand() Expr {
  314. if p.trace {
  315. defer untracep(tracep(p, "Operand"))
  316. }
  317. switch p.token {
  318. case token.Ident:
  319. return p.parseIdent()
  320. case token.Int:
  321. v, err := strconv.ParseInt(p.tokenLit, 0, 64)
  322. if err == strconv.ErrRange {
  323. p.error(p.pos, "number out of range")
  324. } else if err != nil {
  325. p.error(p.pos, "invalid integer")
  326. }
  327. x := &IntLit{
  328. Value: v,
  329. ValuePos: p.pos,
  330. Literal: p.tokenLit,
  331. }
  332. p.next()
  333. return x
  334. case token.Float:
  335. v, err := strconv.ParseFloat(p.tokenLit, 64)
  336. if err == strconv.ErrRange {
  337. p.error(p.pos, "number out of range")
  338. } else if err != nil {
  339. p.error(p.pos, "invalid float")
  340. }
  341. x := &FloatLit{
  342. Value: v,
  343. ValuePos: p.pos,
  344. Literal: p.tokenLit,
  345. }
  346. p.next()
  347. return x
  348. case token.Char:
  349. return p.parseCharLit()
  350. case token.String:
  351. v, _ := strconv.Unquote(p.tokenLit)
  352. x := &StringLit{
  353. Value: v,
  354. ValuePos: p.pos,
  355. Literal: p.tokenLit,
  356. }
  357. p.next()
  358. return x
  359. case token.True:
  360. x := &BoolLit{
  361. Value: true,
  362. ValuePos: p.pos,
  363. Literal: p.tokenLit,
  364. }
  365. p.next()
  366. return x
  367. case token.False:
  368. x := &BoolLit{
  369. Value: false,
  370. ValuePos: p.pos,
  371. Literal: p.tokenLit,
  372. }
  373. p.next()
  374. return x
  375. case token.Undefined:
  376. x := &UndefinedLit{TokenPos: p.pos}
  377. p.next()
  378. return x
  379. case token.Import:
  380. return p.parseImportExpr()
  381. case token.LParen:
  382. lparen := p.pos
  383. p.next()
  384. p.exprLevel++
  385. x := p.parseExpr()
  386. p.exprLevel--
  387. rparen := p.expect(token.RParen)
  388. return &ParenExpr{
  389. LParen: lparen,
  390. Expr: x,
  391. RParen: rparen,
  392. }
  393. case token.LBrack: // array literal
  394. return p.parseArrayLit()
  395. case token.LBrace: // map literal
  396. return p.parseMapLit()
  397. case token.Func: // function literal
  398. return p.parseFuncLit()
  399. case token.Error: // error expression
  400. return p.parseErrorExpr()
  401. case token.Immutable: // immutable expression
  402. return p.parseImmutableExpr()
  403. default:
  404. p.errorExpected(p.pos, "operand")
  405. }
  406. pos := p.pos
  407. p.advance(stmtStart)
  408. return &BadExpr{From: pos, To: p.pos}
  409. }
  410. func (p *Parser) parseImportExpr() Expr {
  411. pos := p.pos
  412. p.next()
  413. p.expect(token.LParen)
  414. if p.token != token.String {
  415. p.errorExpected(p.pos, "module name")
  416. p.advance(stmtStart)
  417. return &BadExpr{From: pos, To: p.pos}
  418. }
  419. // module name
  420. moduleName, _ := strconv.Unquote(p.tokenLit)
  421. expr := &ImportExpr{
  422. ModuleName: moduleName,
  423. Token: token.Import,
  424. TokenPos: pos,
  425. }
  426. p.next()
  427. p.expect(token.RParen)
  428. return expr
  429. }
  430. func (p *Parser) parseCharLit() Expr {
  431. if n := len(p.tokenLit); n >= 3 {
  432. code, _, _, err := strconv.UnquoteChar(p.tokenLit[1:n-1], '\'')
  433. if err == nil {
  434. x := &CharLit{
  435. Value: code,
  436. ValuePos: p.pos,
  437. Literal: p.tokenLit,
  438. }
  439. p.next()
  440. return x
  441. }
  442. }
  443. pos := p.pos
  444. p.error(pos, "illegal char literal")
  445. p.next()
  446. return &BadExpr{
  447. From: pos,
  448. To: p.pos,
  449. }
  450. }
  451. func (p *Parser) parseFuncLit() Expr {
  452. if p.trace {
  453. defer untracep(tracep(p, "FuncLit"))
  454. }
  455. typ := p.parseFuncType()
  456. p.exprLevel++
  457. body := p.parseBody()
  458. p.exprLevel--
  459. return &FuncLit{
  460. Type: typ,
  461. Body: body,
  462. }
  463. }
  464. func (p *Parser) parseArrayLit() Expr {
  465. if p.trace {
  466. defer untracep(tracep(p, "ArrayLit"))
  467. }
  468. lbrack := p.expect(token.LBrack)
  469. p.exprLevel++
  470. var elements []Expr
  471. for p.token != token.RBrack && p.token != token.EOF {
  472. elements = append(elements, p.parseExpr())
  473. if !p.expectComma(token.RBrack, "array element") {
  474. break
  475. }
  476. }
  477. p.exprLevel--
  478. rbrack := p.expect(token.RBrack)
  479. return &ArrayLit{
  480. Elements: elements,
  481. LBrack: lbrack,
  482. RBrack: rbrack,
  483. }
  484. }
  485. func (p *Parser) parseErrorExpr() Expr {
  486. pos := p.pos
  487. p.next()
  488. lparen := p.expect(token.LParen)
  489. value := p.parseExpr()
  490. rparen := p.expect(token.RParen)
  491. return &ErrorExpr{
  492. ErrorPos: pos,
  493. Expr: value,
  494. LParen: lparen,
  495. RParen: rparen,
  496. }
  497. }
  498. func (p *Parser) parseImmutableExpr() Expr {
  499. pos := p.pos
  500. p.next()
  501. lparen := p.expect(token.LParen)
  502. value := p.parseExpr()
  503. rparen := p.expect(token.RParen)
  504. return &ImmutableExpr{
  505. ErrorPos: pos,
  506. Expr: value,
  507. LParen: lparen,
  508. RParen: rparen,
  509. }
  510. }
  511. func (p *Parser) parseFuncType() *FuncType {
  512. if p.trace {
  513. defer untracep(tracep(p, "FuncType"))
  514. }
  515. pos := p.expect(token.Func)
  516. params := p.parseIdentList()
  517. return &FuncType{
  518. FuncPos: pos,
  519. Params: params,
  520. }
  521. }
  522. func (p *Parser) parseBody() *BlockStmt {
  523. if p.trace {
  524. defer untracep(tracep(p, "Body"))
  525. }
  526. lbrace := p.expect(token.LBrace)
  527. list := p.parseStmtList()
  528. rbrace := p.expect(token.RBrace)
  529. return &BlockStmt{
  530. LBrace: lbrace,
  531. RBrace: rbrace,
  532. Stmts: list,
  533. }
  534. }
  535. func (p *Parser) parseStmtList() (list []Stmt) {
  536. if p.trace {
  537. defer untracep(tracep(p, "StatementList"))
  538. }
  539. for p.token != token.RBrace && p.token != token.EOF {
  540. list = append(list, p.parseStmt())
  541. }
  542. return
  543. }
  544. func (p *Parser) parseIdent() *Ident {
  545. pos := p.pos
  546. name := "_"
  547. if p.token == token.Ident {
  548. name = p.tokenLit
  549. p.next()
  550. } else {
  551. p.expect(token.Ident)
  552. }
  553. return &Ident{
  554. NamePos: pos,
  555. Name: name,
  556. }
  557. }
  558. func (p *Parser) parseIdentList() *IdentList {
  559. if p.trace {
  560. defer untracep(tracep(p, "IdentList"))
  561. }
  562. var params []*Ident
  563. lparen := p.expect(token.LParen)
  564. isVarArgs := false
  565. if p.token != token.RParen {
  566. if p.token == token.Ellipsis {
  567. isVarArgs = true
  568. p.next()
  569. }
  570. params = append(params, p.parseIdent())
  571. for !isVarArgs && p.token == token.Comma {
  572. p.next()
  573. if p.token == token.Ellipsis {
  574. isVarArgs = true
  575. p.next()
  576. }
  577. params = append(params, p.parseIdent())
  578. }
  579. }
  580. rparen := p.expect(token.RParen)
  581. return &IdentList{
  582. LParen: lparen,
  583. RParen: rparen,
  584. VarArgs: isVarArgs,
  585. List: params,
  586. }
  587. }
  588. func (p *Parser) parseStmt() (stmt Stmt) {
  589. if p.trace {
  590. defer untracep(tracep(p, "Statement"))
  591. }
  592. switch p.token {
  593. case // simple statements
  594. token.Func, token.Error, token.Immutable, token.Ident, token.Int,
  595. token.Float, token.Char, token.String, token.True, token.False,
  596. token.Undefined, token.Import, token.LParen, token.LBrace,
  597. token.LBrack, token.Add, token.Sub, token.Mul, token.And, token.Xor,
  598. token.Not:
  599. s := p.parseSimpleStmt(false)
  600. p.expectSemi()
  601. return s
  602. case token.Return:
  603. return p.parseReturnStmt()
  604. case token.Export:
  605. return p.parseExportStmt()
  606. case token.If:
  607. return p.parseIfStmt()
  608. case token.For:
  609. return p.parseForStmt()
  610. case token.Break, token.Continue:
  611. return p.parseBranchStmt(p.token)
  612. case token.Semicolon:
  613. s := &EmptyStmt{Semicolon: p.pos, Implicit: p.tokenLit == "\n"}
  614. p.next()
  615. return s
  616. case token.RBrace:
  617. // semicolon may be omitted before a closing "}"
  618. return &EmptyStmt{Semicolon: p.pos, Implicit: true}
  619. default:
  620. pos := p.pos
  621. p.errorExpected(pos, "statement")
  622. p.advance(stmtStart)
  623. return &BadStmt{From: pos, To: p.pos}
  624. }
  625. }
  626. func (p *Parser) parseForStmt() Stmt {
  627. if p.trace {
  628. defer untracep(tracep(p, "ForStmt"))
  629. }
  630. pos := p.expect(token.For)
  631. // for {}
  632. if p.token == token.LBrace {
  633. body := p.parseBlockStmt()
  634. p.expectSemi()
  635. return &ForStmt{
  636. ForPos: pos,
  637. Body: body,
  638. }
  639. }
  640. prevLevel := p.exprLevel
  641. p.exprLevel = -1
  642. var s1 Stmt
  643. if p.token != token.Semicolon { // skipping init
  644. s1 = p.parseSimpleStmt(true)
  645. }
  646. // for _ in seq {} or
  647. // for value in seq {} or
  648. // for key, value in seq {}
  649. if forInStmt, isForIn := s1.(*ForInStmt); isForIn {
  650. forInStmt.ForPos = pos
  651. p.exprLevel = prevLevel
  652. forInStmt.Body = p.parseBlockStmt()
  653. p.expectSemi()
  654. return forInStmt
  655. }
  656. // for init; cond; post {}
  657. var s2, s3 Stmt
  658. if p.token == token.Semicolon {
  659. p.next()
  660. if p.token != token.Semicolon {
  661. s2 = p.parseSimpleStmt(false) // cond
  662. }
  663. p.expect(token.Semicolon)
  664. if p.token != token.LBrace {
  665. s3 = p.parseSimpleStmt(false) // post
  666. }
  667. } else {
  668. // for cond {}
  669. s2 = s1
  670. s1 = nil
  671. }
  672. // body
  673. p.exprLevel = prevLevel
  674. body := p.parseBlockStmt()
  675. p.expectSemi()
  676. cond := p.makeExpr(s2, "condition expression")
  677. return &ForStmt{
  678. ForPos: pos,
  679. Init: s1,
  680. Cond: cond,
  681. Post: s3,
  682. Body: body,
  683. }
  684. }
  685. func (p *Parser) parseBranchStmt(tok token.Token) Stmt {
  686. if p.trace {
  687. defer untracep(tracep(p, "BranchStmt"))
  688. }
  689. pos := p.expect(tok)
  690. var label *Ident
  691. if p.token == token.Ident {
  692. label = p.parseIdent()
  693. }
  694. p.expectSemi()
  695. return &BranchStmt{
  696. Token: tok,
  697. TokenPos: pos,
  698. Label: label,
  699. }
  700. }
  701. func (p *Parser) parseIfStmt() Stmt {
  702. if p.trace {
  703. defer untracep(tracep(p, "IfStmt"))
  704. }
  705. pos := p.expect(token.If)
  706. init, cond := p.parseIfHeader()
  707. body := p.parseBlockStmt()
  708. var elseStmt Stmt
  709. if p.token == token.Else {
  710. p.next()
  711. switch p.token {
  712. case token.If:
  713. elseStmt = p.parseIfStmt()
  714. case token.LBrace:
  715. elseStmt = p.parseBlockStmt()
  716. p.expectSemi()
  717. default:
  718. p.errorExpected(p.pos, "if or {")
  719. elseStmt = &BadStmt{From: p.pos, To: p.pos}
  720. }
  721. } else {
  722. p.expectSemi()
  723. }
  724. return &IfStmt{
  725. IfPos: pos,
  726. Init: init,
  727. Cond: cond,
  728. Body: body,
  729. Else: elseStmt,
  730. }
  731. }
  732. func (p *Parser) parseBlockStmt() *BlockStmt {
  733. if p.trace {
  734. defer untracep(tracep(p, "BlockStmt"))
  735. }
  736. lbrace := p.expect(token.LBrace)
  737. list := p.parseStmtList()
  738. rbrace := p.expect(token.RBrace)
  739. return &BlockStmt{
  740. LBrace: lbrace,
  741. RBrace: rbrace,
  742. Stmts: list,
  743. }
  744. }
  745. func (p *Parser) parseIfHeader() (init Stmt, cond Expr) {
  746. if p.token == token.LBrace {
  747. p.error(p.pos, "missing condition in if statement")
  748. cond = &BadExpr{From: p.pos, To: p.pos}
  749. return
  750. }
  751. outer := p.exprLevel
  752. p.exprLevel = -1
  753. if p.token == token.Semicolon {
  754. p.error(p.pos, "missing init in if statement")
  755. return
  756. }
  757. init = p.parseSimpleStmt(false)
  758. var condStmt Stmt
  759. if p.token == token.LBrace {
  760. condStmt = init
  761. init = nil
  762. } else if p.token == token.Semicolon {
  763. p.next()
  764. condStmt = p.parseSimpleStmt(false)
  765. } else {
  766. p.error(p.pos, "missing condition in if statement")
  767. }
  768. if condStmt != nil {
  769. cond = p.makeExpr(condStmt, "boolean expression")
  770. }
  771. if cond == nil {
  772. cond = &BadExpr{From: p.pos, To: p.pos}
  773. }
  774. p.exprLevel = outer
  775. return
  776. }
  777. func (p *Parser) makeExpr(s Stmt, want string) Expr {
  778. if s == nil {
  779. return nil
  780. }
  781. if es, isExpr := s.(*ExprStmt); isExpr {
  782. return es.Expr
  783. }
  784. found := "simple statement"
  785. if _, isAss := s.(*AssignStmt); isAss {
  786. found = "assignment"
  787. }
  788. p.error(s.Pos(), fmt.Sprintf("expected %s, found %s", want, found))
  789. return &BadExpr{From: s.Pos(), To: p.safePos(s.End())}
  790. }
  791. func (p *Parser) parseReturnStmt() Stmt {
  792. if p.trace {
  793. defer untracep(tracep(p, "ReturnStmt"))
  794. }
  795. pos := p.pos
  796. p.expect(token.Return)
  797. var x Expr
  798. if p.token != token.Semicolon && p.token != token.RBrace {
  799. x = p.parseExpr()
  800. }
  801. p.expectSemi()
  802. return &ReturnStmt{
  803. ReturnPos: pos,
  804. Result: x,
  805. }
  806. }
  807. func (p *Parser) parseExportStmt() Stmt {
  808. if p.trace {
  809. defer untracep(tracep(p, "ExportStmt"))
  810. }
  811. pos := p.pos
  812. p.expect(token.Export)
  813. x := p.parseExpr()
  814. p.expectSemi()
  815. return &ExportStmt{
  816. ExportPos: pos,
  817. Result: x,
  818. }
  819. }
  820. func (p *Parser) parseSimpleStmt(forIn bool) Stmt {
  821. if p.trace {
  822. defer untracep(tracep(p, "SimpleStmt"))
  823. }
  824. x := p.parseExprList()
  825. switch p.token {
  826. case token.Assign, token.Define: // assignment statement
  827. pos, tok := p.pos, p.token
  828. p.next()
  829. y := p.parseExprList()
  830. return &AssignStmt{
  831. LHS: x,
  832. RHS: y,
  833. Token: tok,
  834. TokenPos: pos,
  835. }
  836. case token.In:
  837. if forIn {
  838. p.next()
  839. y := p.parseExpr()
  840. var key, value *Ident
  841. var ok bool
  842. switch len(x) {
  843. case 1:
  844. key = &Ident{Name: "_", NamePos: x[0].Pos()}
  845. value, ok = x[0].(*Ident)
  846. if !ok {
  847. p.errorExpected(x[0].Pos(), "identifier")
  848. value = &Ident{Name: "_", NamePos: x[0].Pos()}
  849. }
  850. case 2:
  851. key, ok = x[0].(*Ident)
  852. if !ok {
  853. p.errorExpected(x[0].Pos(), "identifier")
  854. key = &Ident{Name: "_", NamePos: x[0].Pos()}
  855. }
  856. value, ok = x[1].(*Ident)
  857. if !ok {
  858. p.errorExpected(x[1].Pos(), "identifier")
  859. value = &Ident{Name: "_", NamePos: x[1].Pos()}
  860. }
  861. }
  862. return &ForInStmt{
  863. Key: key,
  864. Value: value,
  865. Iterable: y,
  866. }
  867. }
  868. }
  869. if len(x) > 1 {
  870. p.errorExpected(x[0].Pos(), "1 expression")
  871. // continue with first expression
  872. }
  873. switch p.token {
  874. case token.Define,
  875. token.AddAssign, token.SubAssign, token.MulAssign, token.QuoAssign,
  876. token.RemAssign, token.AndAssign, token.OrAssign, token.XorAssign,
  877. token.ShlAssign, token.ShrAssign, token.AndNotAssign:
  878. pos, tok := p.pos, p.token
  879. p.next()
  880. y := p.parseExpr()
  881. return &AssignStmt{
  882. LHS: []Expr{x[0]},
  883. RHS: []Expr{y},
  884. Token: tok,
  885. TokenPos: pos,
  886. }
  887. case token.Inc, token.Dec:
  888. // increment or decrement statement
  889. s := &IncDecStmt{Expr: x[0], Token: p.token, TokenPos: p.pos}
  890. p.next()
  891. return s
  892. }
  893. return &ExprStmt{Expr: x[0]}
  894. }
  895. func (p *Parser) parseExprList() (list []Expr) {
  896. if p.trace {
  897. defer untracep(tracep(p, "ExpressionList"))
  898. }
  899. list = append(list, p.parseExpr())
  900. for p.token == token.Comma {
  901. p.next()
  902. list = append(list, p.parseExpr())
  903. }
  904. return
  905. }
  906. func (p *Parser) parseMapElementLit() *MapElementLit {
  907. if p.trace {
  908. defer untracep(tracep(p, "MapElementLit"))
  909. }
  910. pos := p.pos
  911. name := "_"
  912. if p.token == token.Ident {
  913. name = p.tokenLit
  914. } else if p.token == token.String {
  915. v, _ := strconv.Unquote(p.tokenLit)
  916. name = v
  917. } else {
  918. p.errorExpected(pos, "map key")
  919. }
  920. p.next()
  921. colonPos := p.expect(token.Colon)
  922. valueExpr := p.parseExpr()
  923. return &MapElementLit{
  924. Key: name,
  925. KeyPos: pos,
  926. ColonPos: colonPos,
  927. Value: valueExpr,
  928. }
  929. }
  930. func (p *Parser) parseMapLit() *MapLit {
  931. if p.trace {
  932. defer untracep(tracep(p, "MapLit"))
  933. }
  934. lbrace := p.expect(token.LBrace)
  935. p.exprLevel++
  936. var elements []*MapElementLit
  937. for p.token != token.RBrace && p.token != token.EOF {
  938. elements = append(elements, p.parseMapElementLit())
  939. if !p.expectComma(token.RBrace, "map element") {
  940. break
  941. }
  942. }
  943. p.exprLevel--
  944. rbrace := p.expect(token.RBrace)
  945. return &MapLit{
  946. LBrace: lbrace,
  947. RBrace: rbrace,
  948. Elements: elements,
  949. }
  950. }
  951. func (p *Parser) expect(token token.Token) Pos {
  952. pos := p.pos
  953. if p.token != token {
  954. p.errorExpected(pos, "'"+token.String()+"'")
  955. }
  956. p.next()
  957. return pos
  958. }
  959. func (p *Parser) expectSemi() {
  960. switch p.token {
  961. case token.RParen, token.RBrace:
  962. // semicolon is optional before a closing ')' or '}'
  963. case token.Comma:
  964. // permit a ',' instead of a ';' but complain
  965. p.errorExpected(p.pos, "';'")
  966. fallthrough
  967. case token.Semicolon:
  968. p.next()
  969. default:
  970. p.errorExpected(p.pos, "';'")
  971. p.advance(stmtStart)
  972. }
  973. }
  974. func (p *Parser) advance(to map[token.Token]bool) {
  975. for ; p.token != token.EOF; p.next() {
  976. if to[p.token] {
  977. if p.pos == p.syncPos && p.syncCount < 10 {
  978. p.syncCount++
  979. return
  980. }
  981. if p.pos > p.syncPos {
  982. p.syncPos = p.pos
  983. p.syncCount = 0
  984. return
  985. }
  986. }
  987. }
  988. }
  989. func (p *Parser) error(pos Pos, msg string) {
  990. filePos := p.file.Position(pos)
  991. n := len(p.errors)
  992. if n > 0 && p.errors[n-1].Pos.Line == filePos.Line {
  993. // discard errors reported on the same line
  994. return
  995. }
  996. if n > 10 {
  997. // too many errors; terminate early
  998. panic(bailout{})
  999. }
  1000. p.errors.Add(filePos, msg)
  1001. }
  1002. func (p *Parser) errorExpected(pos Pos, msg string) {
  1003. msg = "expected " + msg
  1004. if pos == p.pos {
  1005. // error happened at the current position: provide more specific
  1006. switch {
  1007. case p.token == token.Semicolon && p.tokenLit == "\n":
  1008. msg += ", found newline"
  1009. case p.token.IsLiteral():
  1010. msg += ", found " + p.tokenLit
  1011. default:
  1012. msg += ", found '" + p.token.String() + "'"
  1013. }
  1014. }
  1015. p.error(pos, msg)
  1016. }
  1017. func (p *Parser) next() {
  1018. if p.trace && p.pos.IsValid() {
  1019. s := p.token.String()
  1020. switch {
  1021. case p.token.IsLiteral():
  1022. p.printTrace(s, p.tokenLit)
  1023. case p.token.IsOperator(), p.token.IsKeyword():
  1024. p.printTrace(`"` + s + `"`)
  1025. default:
  1026. p.printTrace(s)
  1027. }
  1028. }
  1029. p.token, p.tokenLit, p.pos = p.scanner.Scan()
  1030. }
  1031. func (p *Parser) printTrace(a ...interface{}) {
  1032. const (
  1033. dots = ". . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . "
  1034. n = len(dots)
  1035. )
  1036. filePos := p.file.Position(p.pos)
  1037. _, _ = fmt.Fprintf(p.traceOut, "%5d: %5d:%3d: ", p.pos, filePos.Line,
  1038. filePos.Column)
  1039. i := 2 * p.indent
  1040. for i > n {
  1041. _, _ = fmt.Fprint(p.traceOut, dots)
  1042. i -= n
  1043. }
  1044. _, _ = fmt.Fprint(p.traceOut, dots[0:i])
  1045. _, _ = fmt.Fprintln(p.traceOut, a...)
  1046. }
  1047. func (p *Parser) safePos(pos Pos) Pos {
  1048. fileBase := p.file.Base
  1049. fileSize := p.file.Size
  1050. if int(pos) < fileBase || int(pos) > fileBase+fileSize {
  1051. return Pos(fileBase + fileSize)
  1052. }
  1053. return pos
  1054. }
  1055. func tracep(p *Parser, msg string) *Parser {
  1056. p.printTrace(msg, "(")
  1057. p.indent++
  1058. return p
  1059. }
  1060. func untracep(p *Parser) {
  1061. p.indent--
  1062. p.printTrace(")")
  1063. }