mirror of
https://github.com/gin-gonic/gin.git
synced 2025-12-13 13:12:17 +08:00
161 lines
4.0 KiB
Go
161 lines
4.0 KiB
Go
// Copyright (c) 2012-2020 Ugorji Nwoke. All rights reserved.
|
|
// Use of this source code is governed by a MIT license found in the LICENSE file.
|
|
|
|
package codec
|
|
|
|
import (
|
|
"reflect"
|
|
)
|
|
|
|
// major
|
|
const (
|
|
cborMajorUint byte = iota
|
|
cborMajorNegInt
|
|
cborMajorBytes
|
|
cborMajorString
|
|
cborMajorArray
|
|
cborMajorMap
|
|
cborMajorTag
|
|
cborMajorSimpleOrFloat
|
|
)
|
|
|
|
// simple
|
|
const (
|
|
cborBdFalse byte = 0xf4 + iota
|
|
cborBdTrue
|
|
cborBdNil
|
|
cborBdUndefined
|
|
cborBdExt
|
|
cborBdFloat16
|
|
cborBdFloat32
|
|
cborBdFloat64
|
|
)
|
|
|
|
// indefinite
|
|
const (
|
|
cborBdIndefiniteBytes byte = 0x5f
|
|
cborBdIndefiniteString byte = 0x7f
|
|
cborBdIndefiniteArray byte = 0x9f
|
|
cborBdIndefiniteMap byte = 0xbf
|
|
cborBdBreak byte = 0xff
|
|
)
|
|
|
|
// These define some in-stream descriptors for
|
|
// manual encoding e.g. when doing explicit indefinite-length
|
|
const (
|
|
CborStreamBytes byte = 0x5f
|
|
CborStreamString byte = 0x7f
|
|
CborStreamArray byte = 0x9f
|
|
CborStreamMap byte = 0xbf
|
|
CborStreamBreak byte = 0xff
|
|
)
|
|
|
|
// base values
|
|
const (
|
|
cborBaseUint byte = 0x00
|
|
cborBaseNegInt byte = 0x20
|
|
cborBaseBytes byte = 0x40
|
|
cborBaseString byte = 0x60
|
|
cborBaseArray byte = 0x80
|
|
cborBaseMap byte = 0xa0
|
|
cborBaseTag byte = 0xc0
|
|
cborBaseSimple byte = 0xe0
|
|
)
|
|
|
|
// const (
|
|
// cborSelfDesrTag byte = 0xd9
|
|
// cborSelfDesrTag2 byte = 0xd9
|
|
// cborSelfDesrTag3 byte = 0xf7
|
|
// )
|
|
|
|
var (
|
|
cbordescSimpleNames = map[byte]string{
|
|
cborBdNil: "nil",
|
|
cborBdFalse: "false",
|
|
cborBdTrue: "true",
|
|
cborBdFloat16: "float",
|
|
cborBdFloat32: "float",
|
|
cborBdFloat64: "float",
|
|
cborBdBreak: "break",
|
|
}
|
|
cbordescIndefNames = map[byte]string{
|
|
cborBdIndefiniteBytes: "bytes*",
|
|
cborBdIndefiniteString: "string*",
|
|
cborBdIndefiniteArray: "array*",
|
|
cborBdIndefiniteMap: "map*",
|
|
}
|
|
cbordescMajorNames = map[byte]string{
|
|
cborMajorUint: "(u)int",
|
|
cborMajorNegInt: "int",
|
|
cborMajorBytes: "bytes",
|
|
cborMajorString: "string",
|
|
cborMajorArray: "array",
|
|
cborMajorMap: "map",
|
|
cborMajorTag: "tag",
|
|
cborMajorSimpleOrFloat: "simple",
|
|
}
|
|
)
|
|
|
|
func cbordesc(bd byte) (s string) {
|
|
bm := bd >> 5
|
|
if bm == cborMajorSimpleOrFloat {
|
|
s = cbordescSimpleNames[bd]
|
|
} else {
|
|
s = cbordescMajorNames[bm]
|
|
if s == "" {
|
|
s = cbordescIndefNames[bd]
|
|
}
|
|
}
|
|
if s == "" {
|
|
s = "unknown"
|
|
}
|
|
return
|
|
}
|
|
|
|
// -------------------------
|
|
|
|
// CborHandle is a Handle for the CBOR encoding format,
|
|
// defined at http://tools.ietf.org/html/rfc7049 and documented further at http://cbor.io .
|
|
//
|
|
// CBOR is comprehensively supported, including support for:
|
|
// - indefinite-length arrays/maps/bytes/strings
|
|
// - (extension) tags in range 0..0xffff (0 .. 65535)
|
|
// - half, single and double-precision floats
|
|
// - all numbers (1, 2, 4 and 8-byte signed and unsigned integers)
|
|
// - nil, true, false, ...
|
|
// - arrays and maps, bytes and text strings
|
|
//
|
|
// None of the optional extensions (with tags) defined in the spec are supported out-of-the-box.
|
|
// Users can implement them as needed (using SetExt), including spec-documented ones:
|
|
// - timestamp, BigNum, BigFloat, Decimals,
|
|
// - Encoded Text (e.g. URL, regexp, base64, MIME Message), etc.
|
|
type CborHandle struct {
|
|
binaryEncodingType
|
|
notJsonType
|
|
// noElemSeparators
|
|
BasicHandle
|
|
|
|
// IndefiniteLength=true, means that we encode using indefinitelength
|
|
IndefiniteLength bool
|
|
|
|
// TimeRFC3339 says to encode time.Time using RFC3339 format.
|
|
// If unset, we encode time.Time using seconds past epoch.
|
|
TimeRFC3339 bool
|
|
|
|
// SkipUnexpectedTags says to skip over any tags for which extensions are
|
|
// not defined. This is in keeping with the cbor spec on "Optional Tagging of Items".
|
|
//
|
|
// Furthermore, this allows the skipping over of the Self Describing Tag 0xd9d9f7.
|
|
SkipUnexpectedTags bool
|
|
}
|
|
|
|
// Name returns the name of the handle: cbor
|
|
func (h *CborHandle) Name() string { return "cbor" }
|
|
|
|
func (h *CborHandle) desc(bd byte) string { return cbordesc(bd) }
|
|
|
|
// SetInterfaceExt sets an extension
|
|
func (h *CborHandle) SetInterfaceExt(rt reflect.Type, tag uint64, ext InterfaceExt) (err error) {
|
|
return h.SetExt(rt, tag, makeExt(ext))
|
|
}
|