decode.go 24 KB

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