reflect_optional.go 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130
  1. package jsoniter
  2. import (
  3. "reflect"
  4. "unsafe"
  5. )
  6. func decoderOfOptional(cfg *frozenConfig, prefix string, typ reflect.Type) ValDecoder {
  7. elemType := typ.Elem()
  8. decoder := decoderOfType(cfg, prefix, elemType)
  9. return &OptionalDecoder{elemType, decoder}
  10. }
  11. func encoderOfOptional(cfg *frozenConfig, prefix string, typ reflect.Type) ValEncoder {
  12. elemType := typ.Elem()
  13. elemEncoder := encoderOfType(cfg, prefix, elemType)
  14. encoder := &OptionalEncoder{elemEncoder}
  15. return encoder
  16. }
  17. type OptionalDecoder struct {
  18. ValueType reflect.Type
  19. ValueDecoder ValDecoder
  20. }
  21. func (decoder *OptionalDecoder) Decode(ptr unsafe.Pointer, iter *Iterator) {
  22. if iter.ReadNil() {
  23. *((*unsafe.Pointer)(ptr)) = nil
  24. } else {
  25. if *((*unsafe.Pointer)(ptr)) == nil {
  26. // TODO: use reflect2 instead
  27. //pointer to null, we have to allocate memory to hold the value
  28. value := reflect.New(decoder.ValueType)
  29. newPtr := extractInterface(value.Interface()).word
  30. decoder.ValueDecoder.Decode(newPtr, iter)
  31. *((*uintptr)(ptr)) = uintptr(newPtr)
  32. } else {
  33. //reuse existing instance
  34. decoder.ValueDecoder.Decode(*((*unsafe.Pointer)(ptr)), iter)
  35. }
  36. }
  37. }
  38. type dereferenceDecoder struct {
  39. // only to deference a pointer
  40. valueType reflect.Type
  41. valueDecoder ValDecoder
  42. }
  43. func (decoder *dereferenceDecoder) Decode(ptr unsafe.Pointer, iter *Iterator) {
  44. if *((*unsafe.Pointer)(ptr)) == nil {
  45. //pointer to null, we have to allocate memory to hold the value
  46. value := reflect.New(decoder.valueType)
  47. newPtr := extractInterface(value.Interface()).word
  48. decoder.valueDecoder.Decode(newPtr, iter)
  49. *((*uintptr)(ptr)) = uintptr(newPtr)
  50. } else {
  51. //reuse existing instance
  52. decoder.valueDecoder.Decode(*((*unsafe.Pointer)(ptr)), iter)
  53. }
  54. }
  55. type OptionalEncoder struct {
  56. ValueEncoder ValEncoder
  57. }
  58. func (encoder *OptionalEncoder) Encode(ptr unsafe.Pointer, stream *Stream) {
  59. if *((*unsafe.Pointer)(ptr)) == nil {
  60. stream.WriteNil()
  61. } else {
  62. encoder.ValueEncoder.Encode(*((*unsafe.Pointer)(ptr)), stream)
  63. }
  64. }
  65. func (encoder *OptionalEncoder) IsEmpty(ptr unsafe.Pointer) bool {
  66. return *((*unsafe.Pointer)(ptr)) == nil
  67. }
  68. type dereferenceEncoder struct {
  69. ValueEncoder ValEncoder
  70. }
  71. func (encoder *dereferenceEncoder) Encode(ptr unsafe.Pointer, stream *Stream) {
  72. if *((*unsafe.Pointer)(ptr)) == nil {
  73. stream.WriteNil()
  74. } else {
  75. encoder.ValueEncoder.Encode(*((*unsafe.Pointer)(ptr)), stream)
  76. }
  77. }
  78. func (encoder *dereferenceEncoder) IsEmpty(ptr unsafe.Pointer) bool {
  79. dePtr := *((*unsafe.Pointer)(ptr))
  80. if dePtr == nil {
  81. return true
  82. }
  83. return encoder.ValueEncoder.IsEmpty(dePtr)
  84. }
  85. func (encoder *dereferenceEncoder) IsEmbeddedPtrNil(ptr unsafe.Pointer) bool {
  86. deReferenced := *((*unsafe.Pointer)(ptr))
  87. if deReferenced == nil {
  88. return true
  89. }
  90. isEmbeddedPtrNil, converted := encoder.ValueEncoder.(IsEmbeddedPtrNil)
  91. if !converted {
  92. return false
  93. }
  94. fieldPtr := unsafe.Pointer(deReferenced)
  95. return isEmbeddedPtrNil.IsEmbeddedPtrNil(fieldPtr)
  96. }
  97. type referenceEncoder struct {
  98. encoder ValEncoder
  99. }
  100. func (encoder *referenceEncoder) Encode(ptr unsafe.Pointer, stream *Stream) {
  101. encoder.encoder.Encode(unsafe.Pointer(&ptr), stream)
  102. }
  103. func (encoder *referenceEncoder) IsEmpty(ptr unsafe.Pointer) bool {
  104. return encoder.encoder.IsEmpty(unsafe.Pointer(&ptr))
  105. }
  106. type referenceDecoder struct {
  107. decoder ValDecoder
  108. }
  109. func (decoder *referenceDecoder) Decode(ptr unsafe.Pointer, iter *Iterator) {
  110. decoder.decoder.Decode(unsafe.Pointer(&ptr), iter)
  111. }