decode.go 19 KB

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