decode.go 22 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939
  1. package yaml
  2. import (
  3. "encoding"
  4. "encoding/base64"
  5. "fmt"
  6. "io"
  7. "math"
  8. "reflect"
  9. "strconv"
  10. "strings"
  11. "time"
  12. )
  13. type NodeKind uint32
  14. const (
  15. DocumentNode NodeKind = 1 << iota
  16. SequenceNode
  17. MappingNode
  18. ScalarNode
  19. AliasNode
  20. )
  21. type Style uint32
  22. const (
  23. TaggedStyle Style = 1 << iota
  24. DoubleQuotedStyle
  25. SingleQuotedStyle
  26. LiteralStyle
  27. FoldedStyle
  28. FlowStyle
  29. )
  30. type Node struct {
  31. Kind NodeKind
  32. Style Style
  33. Line int
  34. Column int
  35. Tag string
  36. Value string
  37. Anchor string
  38. Alias *Node
  39. Children []*Node
  40. Header string
  41. Inline string
  42. Footer string
  43. }
  44. func (n *Node) LongTag() string {
  45. return longTag(n.ShortTag())
  46. }
  47. func (n *Node) ShortTag() string {
  48. if n.indicatedString() {
  49. return strTag
  50. }
  51. if n.Tag == "" || n.Tag == "!" {
  52. switch n.Kind {
  53. case MappingNode:
  54. return mapTag
  55. case SequenceNode:
  56. return seqTag
  57. case AliasNode:
  58. if n.Alias != nil {
  59. return n.Alias.ShortTag()
  60. }
  61. case ScalarNode:
  62. tag, _ := resolve("", n.Value)
  63. return tag
  64. }
  65. return ""
  66. }
  67. return shortTag(n.Tag)
  68. }
  69. func (n *Node) indicatedString() bool {
  70. return n.Kind == ScalarNode &&
  71. (shortTag(n.Tag) == strTag ||
  72. (n.Tag == "" || n.Tag == "!") && n.Style&(SingleQuotedStyle|DoubleQuotedStyle|LiteralStyle|FoldedStyle) != 0)
  73. }
  74. func (n *Node) SetString(s string) {
  75. n.Kind = ScalarNode
  76. n.Value = s
  77. if strings.Contains(s, "\n") {
  78. n.Style = LiteralStyle
  79. } else if n.ShortTag() != strTag {
  80. n.Style = DoubleQuotedStyle
  81. }
  82. }
  83. // ----------------------------------------------------------------------------
  84. // Parser, produces a node tree out of a libyaml event stream.
  85. type parser struct {
  86. parser yaml_parser_t
  87. event yaml_event_t
  88. doc *Node
  89. anchors map[string]*Node
  90. doneInit bool
  91. }
  92. func newParser(b []byte) *parser {
  93. p := parser{}
  94. if !yaml_parser_initialize(&p.parser) {
  95. panic("failed to initialize YAML emitter")
  96. }
  97. if len(b) == 0 {
  98. b = []byte{'\n'}
  99. }
  100. yaml_parser_set_input_string(&p.parser, b)
  101. return &p
  102. }
  103. func newParserFromReader(r io.Reader) *parser {
  104. p := parser{}
  105. if !yaml_parser_initialize(&p.parser) {
  106. panic("failed to initialize YAML emitter")
  107. }
  108. yaml_parser_set_input_reader(&p.parser, r)
  109. return &p
  110. }
  111. func (p *parser) init() {
  112. if p.doneInit {
  113. return
  114. }
  115. p.anchors = make(map[string]*Node)
  116. p.expect(yaml_STREAM_START_EVENT)
  117. p.doneInit = true
  118. }
  119. func (p *parser) destroy() {
  120. if p.event.typ != yaml_NO_EVENT {
  121. yaml_event_delete(&p.event)
  122. }
  123. yaml_parser_delete(&p.parser)
  124. }
  125. // expect consumes an event from the event stream and
  126. // checks that it's of the expected type.
  127. func (p *parser) expect(e yaml_event_type_t) {
  128. if p.event.typ == yaml_NO_EVENT {
  129. if !yaml_parser_parse(&p.parser, &p.event) {
  130. p.fail()
  131. }
  132. }
  133. if p.event.typ == yaml_STREAM_END_EVENT {
  134. failf("attempted to go past the end of stream; corrupted value?")
  135. }
  136. if p.event.typ != e {
  137. p.parser.problem = fmt.Sprintf("expected %s event but got %s", e, p.event.typ)
  138. p.fail()
  139. }
  140. yaml_event_delete(&p.event)
  141. p.event.typ = yaml_NO_EVENT
  142. }
  143. // peek peeks at the next event in the event stream,
  144. // puts the results into p.event and returns the event type.
  145. func (p *parser) peek() yaml_event_type_t {
  146. if p.event.typ != yaml_NO_EVENT {
  147. return p.event.typ
  148. }
  149. if !yaml_parser_parse(&p.parser, &p.event) {
  150. p.fail()
  151. }
  152. return p.event.typ
  153. }
  154. func (p *parser) fail() {
  155. var where string
  156. var line int
  157. if p.parser.problem_mark.line != 0 {
  158. line = p.parser.problem_mark.line
  159. // Scanner errors don't iterate line before returning error
  160. if p.parser.error == yaml_SCANNER_ERROR {
  161. line++
  162. }
  163. } else if p.parser.context_mark.line != 0 {
  164. line = p.parser.context_mark.line
  165. }
  166. if line != 0 {
  167. where = "line " + strconv.Itoa(line) + ": "
  168. }
  169. var msg string
  170. if len(p.parser.problem) > 0 {
  171. msg = p.parser.problem
  172. } else {
  173. msg = "unknown problem parsing YAML content"
  174. }
  175. failf("%s%s", where, msg)
  176. }
  177. func (p *parser) anchor(n *Node, anchor []byte) {
  178. if anchor != nil {
  179. n.Anchor = string(anchor)
  180. p.anchors[n.Anchor] = n
  181. }
  182. }
  183. func (p *parser) parse() *Node {
  184. p.init()
  185. switch p.peek() {
  186. case yaml_SCALAR_EVENT:
  187. return p.scalar()
  188. case yaml_ALIAS_EVENT:
  189. return p.alias()
  190. case yaml_MAPPING_START_EVENT:
  191. return p.mapping()
  192. case yaml_SEQUENCE_START_EVENT:
  193. return p.sequence()
  194. case yaml_DOCUMENT_START_EVENT:
  195. return p.document()
  196. case yaml_STREAM_END_EVENT:
  197. // Happens when attempting to decode an empty buffer.
  198. return nil
  199. default:
  200. panic("attempted to parse unknown event: " + p.event.typ.String())
  201. }
  202. }
  203. func (p *parser) node(kind NodeKind, defaultTag, tag, value string) *Node {
  204. var style Style
  205. if tag != "" && tag != "!" {
  206. tag = shortTag(tag)
  207. style = TaggedStyle
  208. } else if defaultTag != "" {
  209. tag = defaultTag
  210. } else if kind == ScalarNode {
  211. tag, _ = resolve("", value)
  212. }
  213. return &Node{
  214. Kind: kind,
  215. Tag: tag,
  216. Value: value,
  217. Style: style,
  218. Line: p.event.start_mark.line + 1,
  219. Column: p.event.start_mark.column + 1,
  220. Header: string(p.event.header_comment),
  221. Inline: string(p.event.inline_comment),
  222. Footer: string(p.event.footer_comment),
  223. }
  224. }
  225. func (p *parser) parseChild(parent *Node) *Node {
  226. child := p.parse()
  227. parent.Children = append(parent.Children, child)
  228. return child
  229. }
  230. func (p *parser) document() *Node {
  231. n := p.node(DocumentNode, "", "", "")
  232. p.doc = n
  233. p.expect(yaml_DOCUMENT_START_EVENT)
  234. p.parseChild(n)
  235. if p.peek() == yaml_DOCUMENT_END_EVENT {
  236. n.Footer = string(p.event.footer_comment)
  237. }
  238. p.expect(yaml_DOCUMENT_END_EVENT)
  239. return n
  240. }
  241. func (p *parser) alias() *Node {
  242. n := p.node(AliasNode, "", "", string(p.event.anchor))
  243. n.Alias = p.anchors[n.Value]
  244. if n.Alias == nil {
  245. failf("unknown anchor '%s' referenced", n.Value)
  246. }
  247. p.expect(yaml_ALIAS_EVENT)
  248. return n
  249. }
  250. func (p *parser) scalar() *Node {
  251. var parsedStyle = p.event.scalar_style()
  252. var nodeStyle Style
  253. switch {
  254. case parsedStyle&yaml_DOUBLE_QUOTED_SCALAR_STYLE != 0:
  255. nodeStyle = DoubleQuotedStyle
  256. case parsedStyle&yaml_SINGLE_QUOTED_SCALAR_STYLE != 0:
  257. nodeStyle = SingleQuotedStyle
  258. case parsedStyle&yaml_LITERAL_SCALAR_STYLE != 0:
  259. nodeStyle = LiteralStyle
  260. case parsedStyle&yaml_FOLDED_SCALAR_STYLE != 0:
  261. nodeStyle = FoldedStyle
  262. }
  263. var nodeValue = string(p.event.value)
  264. var nodeTag = string(p.event.tag)
  265. var defaultTag string
  266. if nodeStyle == 0 {
  267. if nodeValue == "<<" {
  268. defaultTag = mergeTag
  269. }
  270. } else {
  271. defaultTag = strTag
  272. }
  273. n := p.node(ScalarNode, defaultTag, nodeTag, nodeValue)
  274. n.Style |= nodeStyle
  275. p.anchor(n, p.event.anchor)
  276. p.expect(yaml_SCALAR_EVENT)
  277. return n
  278. }
  279. func (p *parser) sequence() *Node {
  280. n := p.node(SequenceNode, seqTag, string(p.event.tag), "")
  281. if p.event.sequence_style()&yaml_FLOW_SEQUENCE_STYLE != 0 {
  282. n.Style |= FlowStyle
  283. }
  284. p.anchor(n, p.event.anchor)
  285. p.expect(yaml_SEQUENCE_START_EVENT)
  286. for p.peek() != yaml_SEQUENCE_END_EVENT {
  287. p.parseChild(n)
  288. }
  289. n.Inline = string(p.event.inline_comment)
  290. n.Footer = string(p.event.footer_comment)
  291. p.expect(yaml_SEQUENCE_END_EVENT)
  292. return n
  293. }
  294. func (p *parser) mapping() *Node {
  295. n := p.node(MappingNode, mapTag, string(p.event.tag), "")
  296. if p.event.mapping_style()&yaml_FLOW_MAPPING_STYLE != 0 {
  297. n.Style |= FlowStyle
  298. }
  299. p.anchor(n, p.event.anchor)
  300. p.expect(yaml_MAPPING_START_EVENT)
  301. for p.peek() != yaml_MAPPING_END_EVENT {
  302. k := p.parseChild(n)
  303. v := p.parseChild(n)
  304. if v.Footer != "" {
  305. k.Footer = v.Footer
  306. v.Footer = ""
  307. }
  308. }
  309. n.Inline = string(p.event.inline_comment)
  310. n.Footer = string(p.event.footer_comment)
  311. p.expect(yaml_MAPPING_END_EVENT)
  312. return n
  313. }
  314. // ----------------------------------------------------------------------------
  315. // Decoder, unmarshals a node into a provided value.
  316. type decoder struct {
  317. doc *Node
  318. aliases map[*Node]bool
  319. terrors []string
  320. stringMapType reflect.Type
  321. generalMapType reflect.Type
  322. knownFields bool
  323. uniqueKeys bool
  324. }
  325. var (
  326. nodeType = reflect.TypeOf(Node{})
  327. durationType = reflect.TypeOf(time.Duration(0))
  328. stringMapType = reflect.TypeOf(map[string]interface{}{})
  329. generalMapType = reflect.TypeOf(map[interface{}]interface{}{})
  330. ifaceType = generalMapType.Elem()
  331. timeType = reflect.TypeOf(time.Time{})
  332. ptrTimeType = reflect.TypeOf(&time.Time{})
  333. )
  334. func newDecoder() *decoder {
  335. d := &decoder{
  336. stringMapType: stringMapType,
  337. generalMapType: generalMapType,
  338. uniqueKeys: true,
  339. }
  340. d.aliases = make(map[*Node]bool)
  341. return d
  342. }
  343. func (d *decoder) terror(n *Node, tag string, out reflect.Value) {
  344. if n.Tag != "" {
  345. tag = n.Tag
  346. }
  347. value := n.Value
  348. if tag != seqTag && tag != mapTag {
  349. if len(value) > 10 {
  350. value = " `" + value[:7] + "...`"
  351. } else {
  352. value = " `" + value + "`"
  353. }
  354. }
  355. d.terrors = append(d.terrors, fmt.Sprintf("line %d: cannot unmarshal %s%s into %s", n.Line, shortTag(tag), value, out.Type()))
  356. }
  357. func (d *decoder) callUnmarshaler(n *Node, u Unmarshaler) (good bool) {
  358. if err := u.UnmarshalYAML(n); err != nil {
  359. fail(err)
  360. }
  361. return true
  362. }
  363. func (d *decoder) callObsoleteUnmarshaler(n *Node, u obsoleteUnmarshaler) (good bool) {
  364. terrlen := len(d.terrors)
  365. err := u.UnmarshalYAML(func(v interface{}) (err error) {
  366. defer handleErr(&err)
  367. d.unmarshal(n, reflect.ValueOf(v))
  368. if len(d.terrors) > terrlen {
  369. issues := d.terrors[terrlen:]
  370. d.terrors = d.terrors[:terrlen]
  371. return &TypeError{issues}
  372. }
  373. return nil
  374. })
  375. if e, ok := err.(*TypeError); ok {
  376. d.terrors = append(d.terrors, e.Errors...)
  377. return false
  378. }
  379. if err != nil {
  380. fail(err)
  381. }
  382. return true
  383. }
  384. // d.prepare initializes and dereferences pointers and calls UnmarshalYAML
  385. // if a value is found to implement it.
  386. // It returns the initialized and dereferenced out value, whether
  387. // unmarshalling was already done by UnmarshalYAML, and if so whether
  388. // its types unmarshalled appropriately.
  389. //
  390. // If n holds a null value, prepare returns before doing anything.
  391. func (d *decoder) prepare(n *Node, out reflect.Value) (newout reflect.Value, unmarshaled, good bool) {
  392. if n.ShortTag() == nullTag {
  393. return out, false, false
  394. }
  395. again := true
  396. for again {
  397. again = false
  398. if out.Kind() == reflect.Ptr {
  399. if out.IsNil() {
  400. out.Set(reflect.New(out.Type().Elem()))
  401. }
  402. out = out.Elem()
  403. again = true
  404. }
  405. if out.CanAddr() {
  406. outi := out.Addr().Interface()
  407. if u, ok := outi.(Unmarshaler); ok {
  408. good = d.callUnmarshaler(n, u)
  409. return out, true, good
  410. }
  411. if u, ok := outi.(obsoleteUnmarshaler); ok {
  412. good = d.callObsoleteUnmarshaler(n, u)
  413. return out, true, good
  414. }
  415. }
  416. }
  417. return out, false, false
  418. }
  419. func (d *decoder) fieldByIndex(n *Node, v reflect.Value, index []int) (field reflect.Value) {
  420. if n.ShortTag() == nullTag {
  421. return reflect.Value{}
  422. }
  423. for _, num := range index {
  424. for {
  425. if v.Kind() == reflect.Ptr {
  426. if v.IsNil() {
  427. v.Set(reflect.New(v.Type().Elem()))
  428. }
  429. v = v.Elem()
  430. continue
  431. }
  432. break
  433. }
  434. v = v.Field(num)
  435. }
  436. return v
  437. }
  438. func (d *decoder) unmarshal(n *Node, out reflect.Value) (good bool) {
  439. if out.Type() == nodeType {
  440. out.Set(reflect.ValueOf(n).Elem())
  441. return true
  442. }
  443. switch n.Kind {
  444. case DocumentNode:
  445. return d.document(n, out)
  446. case AliasNode:
  447. return d.alias(n, out)
  448. }
  449. out, unmarshaled, good := d.prepare(n, out)
  450. if unmarshaled {
  451. return good
  452. }
  453. switch n.Kind {
  454. case ScalarNode:
  455. good = d.scalar(n, out)
  456. case MappingNode:
  457. good = d.mapping(n, out)
  458. case SequenceNode:
  459. good = d.sequence(n, out)
  460. default:
  461. panic("internal error: unknown node kind: " + strconv.Itoa(int(n.Kind)))
  462. }
  463. return good
  464. }
  465. func (d *decoder) document(n *Node, out reflect.Value) (good bool) {
  466. if len(n.Children) == 1 {
  467. d.doc = n
  468. d.unmarshal(n.Children[0], out)
  469. return true
  470. }
  471. return false
  472. }
  473. func (d *decoder) alias(n *Node, out reflect.Value) (good bool) {
  474. if d.aliases[n] {
  475. // TODO this could actually be allowed in some circumstances.
  476. failf("anchor '%s' value contains itself", n.Value)
  477. }
  478. d.aliases[n] = true
  479. good = d.unmarshal(n.Alias, out)
  480. delete(d.aliases, n)
  481. return good
  482. }
  483. var zeroValue reflect.Value
  484. func resetMap(out reflect.Value) {
  485. for _, k := range out.MapKeys() {
  486. out.SetMapIndex(k, zeroValue)
  487. }
  488. }
  489. func (d *decoder) scalar(n *Node, out reflect.Value) bool {
  490. var tag string
  491. var resolved interface{}
  492. if n.indicatedString() {
  493. tag = strTag
  494. resolved = n.Value
  495. } else {
  496. tag, resolved = resolve(n.Tag, n.Value)
  497. if tag == binaryTag {
  498. data, err := base64.StdEncoding.DecodeString(resolved.(string))
  499. if err != nil {
  500. failf("!!binary value contains invalid base64 data")
  501. }
  502. resolved = string(data)
  503. }
  504. }
  505. if resolved == nil {
  506. if out.Kind() == reflect.Map && !out.CanAddr() {
  507. resetMap(out)
  508. } else {
  509. out.Set(reflect.Zero(out.Type()))
  510. }
  511. return true
  512. }
  513. if resolvedv := reflect.ValueOf(resolved); out.Type() == resolvedv.Type() {
  514. // We've resolved to exactly the type we want, so use that.
  515. out.Set(resolvedv)
  516. return true
  517. }
  518. // Perhaps we can use the value as a TextUnmarshaler to
  519. // set its value.
  520. if out.CanAddr() {
  521. u, ok := out.Addr().Interface().(encoding.TextUnmarshaler)
  522. if ok {
  523. var text []byte
  524. if tag == binaryTag {
  525. text = []byte(resolved.(string))
  526. } else {
  527. // We let any value be unmarshaled into TextUnmarshaler.
  528. // That might be more lax than we'd like, but the
  529. // TextUnmarshaler itself should bowl out any dubious values.
  530. text = []byte(n.Value)
  531. }
  532. err := u.UnmarshalText(text)
  533. if err != nil {
  534. fail(err)
  535. }
  536. return true
  537. }
  538. }
  539. switch out.Kind() {
  540. case reflect.String:
  541. if tag == binaryTag {
  542. out.SetString(resolved.(string))
  543. return true
  544. }
  545. if resolved != nil {
  546. out.SetString(n.Value)
  547. return true
  548. }
  549. case reflect.Interface:
  550. if resolved == nil {
  551. out.Set(reflect.Zero(out.Type()))
  552. } else {
  553. out.Set(reflect.ValueOf(resolved))
  554. }
  555. return true
  556. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
  557. // This used to work in v2, but it's very unfriendly.
  558. isDuration := out.Type() == durationType
  559. switch resolved := resolved.(type) {
  560. case int:
  561. if !isDuration && !out.OverflowInt(int64(resolved)) {
  562. out.SetInt(int64(resolved))
  563. return true
  564. }
  565. case int64:
  566. if !isDuration && !out.OverflowInt(resolved) {
  567. out.SetInt(resolved)
  568. return true
  569. }
  570. case uint64:
  571. if !isDuration && resolved <= math.MaxInt64 && !out.OverflowInt(int64(resolved)) {
  572. out.SetInt(int64(resolved))
  573. return true
  574. }
  575. case float64:
  576. if !isDuration && resolved <= math.MaxInt64 && !out.OverflowInt(int64(resolved)) {
  577. out.SetInt(int64(resolved))
  578. return true
  579. }
  580. case string:
  581. if out.Type() == durationType {
  582. d, err := time.ParseDuration(resolved)
  583. if err == nil {
  584. out.SetInt(int64(d))
  585. return true
  586. }
  587. }
  588. }
  589. case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
  590. switch resolved := resolved.(type) {
  591. case int:
  592. if resolved >= 0 && !out.OverflowUint(uint64(resolved)) {
  593. out.SetUint(uint64(resolved))
  594. return true
  595. }
  596. case int64:
  597. if resolved >= 0 && !out.OverflowUint(uint64(resolved)) {
  598. out.SetUint(uint64(resolved))
  599. return true
  600. }
  601. case uint64:
  602. if !out.OverflowUint(uint64(resolved)) {
  603. out.SetUint(uint64(resolved))
  604. return true
  605. }
  606. case float64:
  607. if resolved <= math.MaxUint64 && !out.OverflowUint(uint64(resolved)) {
  608. out.SetUint(uint64(resolved))
  609. return true
  610. }
  611. }
  612. case reflect.Bool:
  613. switch resolved := resolved.(type) {
  614. case bool:
  615. out.SetBool(resolved)
  616. return true
  617. case string:
  618. // This offers some compatibility with the 1.1 spec (https://yaml.org/type/bool.html).
  619. // It only works if explicitly attempting to unmarshal into a typed bool value.
  620. switch resolved {
  621. case "y", "Y", "yes", "Yes", "YES", "on", "On", "ON":
  622. out.SetBool(true)
  623. return true
  624. case "n", "N", "no", "No", "NO", "off", "Off", "OFF":
  625. out.SetBool(false)
  626. return true
  627. }
  628. }
  629. case reflect.Float32, reflect.Float64:
  630. switch resolved := resolved.(type) {
  631. case int:
  632. out.SetFloat(float64(resolved))
  633. return true
  634. case int64:
  635. out.SetFloat(float64(resolved))
  636. return true
  637. case uint64:
  638. out.SetFloat(float64(resolved))
  639. return true
  640. case float64:
  641. out.SetFloat(resolved)
  642. return true
  643. }
  644. case reflect.Struct:
  645. if resolvedv := reflect.ValueOf(resolved); out.Type() == resolvedv.Type() {
  646. out.Set(resolvedv)
  647. return true
  648. }
  649. case reflect.Ptr:
  650. if out.Type().Elem() == reflect.TypeOf(resolved) {
  651. // TODO DOes this make sense? When is out a Ptr except when decoding a nil value?
  652. elem := reflect.New(out.Type().Elem())
  653. elem.Elem().Set(reflect.ValueOf(resolved))
  654. out.Set(elem)
  655. return true
  656. }
  657. }
  658. d.terror(n, tag, out)
  659. return false
  660. }
  661. func settableValueOf(i interface{}) reflect.Value {
  662. v := reflect.ValueOf(i)
  663. sv := reflect.New(v.Type()).Elem()
  664. sv.Set(v)
  665. return sv
  666. }
  667. func (d *decoder) sequence(n *Node, out reflect.Value) (good bool) {
  668. l := len(n.Children)
  669. var iface reflect.Value
  670. switch out.Kind() {
  671. case reflect.Slice:
  672. out.Set(reflect.MakeSlice(out.Type(), l, l))
  673. case reflect.Array:
  674. if l != out.Len() {
  675. failf("invalid array: want %d elements but got %d", out.Len(), l)
  676. }
  677. case reflect.Interface:
  678. // No type hints. Will have to use a generic sequence.
  679. iface = out
  680. out = settableValueOf(make([]interface{}, l))
  681. default:
  682. d.terror(n, seqTag, out)
  683. return false
  684. }
  685. et := out.Type().Elem()
  686. j := 0
  687. for i := 0; i < l; i++ {
  688. e := reflect.New(et).Elem()
  689. if ok := d.unmarshal(n.Children[i], e); ok {
  690. out.Index(j).Set(e)
  691. j++
  692. }
  693. }
  694. if out.Kind() != reflect.Array {
  695. out.Set(out.Slice(0, j))
  696. }
  697. if iface.IsValid() {
  698. iface.Set(out)
  699. }
  700. return true
  701. }
  702. func (d *decoder) mapping(n *Node, out reflect.Value) (good bool) {
  703. l := len(n.Children)
  704. if d.uniqueKeys {
  705. nerrs := len(d.terrors)
  706. for i := 0; i < l; i += 2 {
  707. ni := n.Children[i]
  708. for j := i+2; j < l; j += 2 {
  709. nj := n.Children[j]
  710. if ni.Kind == nj.Kind && ni.Value == nj.Value {
  711. d.terrors = append(d.terrors, fmt.Sprintf("line %d: mapping key %#v already defined at line %d", nj.Line, nj.Value, ni.Line))
  712. }
  713. }
  714. }
  715. if len(d.terrors) > nerrs {
  716. return false
  717. }
  718. }
  719. switch out.Kind() {
  720. case reflect.Struct:
  721. return d.mappingStruct(n, out)
  722. case reflect.Map:
  723. // okay
  724. case reflect.Interface:
  725. iface := out
  726. if isStringMap(n) {
  727. out = reflect.MakeMap(d.stringMapType)
  728. } else {
  729. out = reflect.MakeMap(d.generalMapType)
  730. }
  731. iface.Set(out)
  732. default:
  733. d.terror(n, mapTag, out)
  734. return false
  735. }
  736. outt := out.Type()
  737. kt := outt.Key()
  738. et := outt.Elem()
  739. stringMapType := d.stringMapType
  740. generalMapType := d.generalMapType
  741. if outt.Elem() == ifaceType {
  742. if outt.Key().Kind() == reflect.String {
  743. d.stringMapType = outt
  744. } else if outt.Key() == ifaceType {
  745. d.generalMapType = outt
  746. }
  747. }
  748. if out.IsNil() {
  749. out.Set(reflect.MakeMap(outt))
  750. }
  751. for i := 0; i < l; i += 2 {
  752. if isMerge(n.Children[i]) {
  753. d.merge(n.Children[i+1], out)
  754. continue
  755. }
  756. k := reflect.New(kt).Elem()
  757. if d.unmarshal(n.Children[i], k) {
  758. kkind := k.Kind()
  759. if kkind == reflect.Interface {
  760. kkind = k.Elem().Kind()
  761. }
  762. if kkind == reflect.Map || kkind == reflect.Slice {
  763. failf("invalid map key: %#v", k.Interface())
  764. }
  765. e := reflect.New(et).Elem()
  766. if d.unmarshal(n.Children[i+1], e) {
  767. out.SetMapIndex(k, e)
  768. }
  769. }
  770. }
  771. d.stringMapType = stringMapType
  772. d.generalMapType = generalMapType
  773. return true
  774. }
  775. func isStringMap(n *Node) bool {
  776. if n.Kind != MappingNode {
  777. return false
  778. }
  779. l := len(n.Children)
  780. for i := 0; i < l; i++ {
  781. if n.Children[i].ShortTag() != strTag {
  782. return false
  783. }
  784. }
  785. return true
  786. }
  787. func (d *decoder) mappingStruct(n *Node, out reflect.Value) (good bool) {
  788. sinfo, err := getStructInfo(out.Type())
  789. if err != nil {
  790. panic(err)
  791. }
  792. var inlineMap reflect.Value
  793. var elemType reflect.Type
  794. if sinfo.InlineMap != -1 {
  795. inlineMap = out.Field(sinfo.InlineMap)
  796. inlineMap.Set(reflect.New(inlineMap.Type()).Elem())
  797. elemType = inlineMap.Type().Elem()
  798. }
  799. for _, index := range sinfo.InlineUnmarshalers {
  800. field := d.fieldByIndex(n, out, index)
  801. d.prepare(n, field)
  802. }
  803. var doneFields []bool
  804. if d.uniqueKeys {
  805. doneFields = make([]bool, len(sinfo.FieldsList))
  806. }
  807. name := settableValueOf("")
  808. l := len(n.Children)
  809. for i := 0; i < l; i += 2 {
  810. ni := n.Children[i]
  811. if isMerge(ni) {
  812. d.merge(n.Children[i+1], out)
  813. continue
  814. }
  815. if !d.unmarshal(ni, name) {
  816. continue
  817. }
  818. if info, ok := sinfo.FieldsMap[name.String()]; ok {
  819. if d.uniqueKeys {
  820. if doneFields[info.Id] {
  821. d.terrors = append(d.terrors, fmt.Sprintf("line %d: field %s already set in type %s", ni.Line, name.String(), out.Type()))
  822. continue
  823. }
  824. doneFields[info.Id] = true
  825. }
  826. var field reflect.Value
  827. if info.Inline == nil {
  828. field = out.Field(info.Num)
  829. } else {
  830. field = d.fieldByIndex(n, out, info.Inline)
  831. }
  832. d.unmarshal(n.Children[i+1], field)
  833. } else if sinfo.InlineMap != -1 {
  834. if inlineMap.IsNil() {
  835. inlineMap.Set(reflect.MakeMap(inlineMap.Type()))
  836. }
  837. value := reflect.New(elemType).Elem()
  838. d.unmarshal(n.Children[i+1], value)
  839. inlineMap.SetMapIndex(name, value)
  840. } else if d.knownFields {
  841. d.terrors = append(d.terrors, fmt.Sprintf("line %d: field %s not found in type %s", ni.Line, name.String(), out.Type()))
  842. }
  843. }
  844. return true
  845. }
  846. func failWantMap() {
  847. failf("map merge requires map or sequence of maps as the value")
  848. }
  849. func (d *decoder) merge(n *Node, out reflect.Value) {
  850. switch n.Kind {
  851. case MappingNode:
  852. d.unmarshal(n, out)
  853. case AliasNode:
  854. if n.Alias != nil && n.Alias.Kind != MappingNode {
  855. failWantMap()
  856. }
  857. d.unmarshal(n, out)
  858. case SequenceNode:
  859. // Step backwards as earlier nodes take precedence.
  860. for i := len(n.Children) - 1; i >= 0; i-- {
  861. ni := n.Children[i]
  862. if ni.Kind == AliasNode {
  863. if ni.Alias != nil && ni.Alias.Kind != MappingNode {
  864. failWantMap()
  865. }
  866. } else if ni.Kind != MappingNode {
  867. failWantMap()
  868. }
  869. d.unmarshal(ni, out)
  870. }
  871. default:
  872. failWantMap()
  873. }
  874. }
  875. func isMerge(n *Node) bool {
  876. return n.Kind == ScalarNode && n.Value == "<<" && (n.Tag == "" || n.Tag == "!" || shortTag(n.Tag) == mergeTag)
  877. }