op.go 9.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501
  1. /*
  2. * Copyright 2021 ByteDance Inc.
  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. */
  16. package ir
  17. import (
  18. "fmt"
  19. "reflect"
  20. "strconv"
  21. "strings"
  22. "unsafe"
  23. "github.com/bytedance/sonic/internal/encoder/vars"
  24. "github.com/bytedance/sonic/internal/resolver"
  25. "github.com/bytedance/sonic/internal/rt"
  26. )
  27. type Op uint8
  28. const (
  29. OP_null Op = iota + 1
  30. OP_empty_arr
  31. OP_empty_obj
  32. OP_bool
  33. OP_i8
  34. OP_i16
  35. OP_i32
  36. OP_i64
  37. OP_u8
  38. OP_u16
  39. OP_u32
  40. OP_u64
  41. OP_f32
  42. OP_f64
  43. OP_str
  44. OP_bin
  45. OP_quote
  46. OP_number
  47. OP_eface
  48. OP_iface
  49. OP_byte
  50. OP_text
  51. OP_deref
  52. OP_index
  53. OP_load
  54. OP_save
  55. OP_drop
  56. OP_drop_2
  57. OP_recurse
  58. OP_is_nil
  59. OP_is_nil_p1
  60. OP_is_zero_1
  61. OP_is_zero_2
  62. OP_is_zero_4
  63. OP_is_zero_8
  64. OP_is_zero_map
  65. OP_goto
  66. OP_map_iter
  67. OP_map_stop
  68. OP_map_check_key
  69. OP_map_write_key
  70. OP_map_value_next
  71. OP_slice_len
  72. OP_slice_next
  73. OP_marshal
  74. OP_marshal_p
  75. OP_marshal_text
  76. OP_marshal_text_p
  77. OP_cond_set
  78. OP_cond_testc
  79. OP_unsupported
  80. OP_is_zero
  81. )
  82. const (
  83. _INT_SIZE = 32 << (^uint(0) >> 63)
  84. _PTR_SIZE = 32 << (^uintptr(0) >> 63)
  85. _PTR_BYTE = unsafe.Sizeof(uintptr(0))
  86. )
  87. const OpSize = unsafe.Sizeof(NewInsOp(0))
  88. var OpNames = [256]string{
  89. OP_null: "null",
  90. OP_empty_arr: "empty_arr",
  91. OP_empty_obj: "empty_obj",
  92. OP_bool: "bool",
  93. OP_i8: "i8",
  94. OP_i16: "i16",
  95. OP_i32: "i32",
  96. OP_i64: "i64",
  97. OP_u8: "u8",
  98. OP_u16: "u16",
  99. OP_u32: "u32",
  100. OP_u64: "u64",
  101. OP_f32: "f32",
  102. OP_f64: "f64",
  103. OP_str: "str",
  104. OP_bin: "bin",
  105. OP_quote: "quote",
  106. OP_number: "number",
  107. OP_eface: "eface",
  108. OP_iface: "iface",
  109. OP_byte: "byte",
  110. OP_text: "text",
  111. OP_deref: "deref",
  112. OP_index: "index",
  113. OP_load: "load",
  114. OP_save: "save",
  115. OP_drop: "drop",
  116. OP_drop_2: "drop_2",
  117. OP_recurse: "recurse",
  118. OP_is_nil: "is_nil",
  119. OP_is_nil_p1: "is_nil_p1",
  120. OP_is_zero_1: "is_zero_1",
  121. OP_is_zero_2: "is_zero_2",
  122. OP_is_zero_4: "is_zero_4",
  123. OP_is_zero_8: "is_zero_8",
  124. OP_is_zero_map: "is_zero_map",
  125. OP_goto: "goto",
  126. OP_map_iter: "map_iter",
  127. OP_map_stop: "map_stop",
  128. OP_map_check_key: "map_check_key",
  129. OP_map_write_key: "map_write_key",
  130. OP_map_value_next: "map_value_next",
  131. OP_slice_len: "slice_len",
  132. OP_slice_next: "slice_next",
  133. OP_marshal: "marshal",
  134. OP_marshal_p: "marshal_p",
  135. OP_marshal_text: "marshal_text",
  136. OP_marshal_text_p: "marshal_text_p",
  137. OP_cond_set: "cond_set",
  138. OP_cond_testc: "cond_testc",
  139. OP_unsupported: "unsupported type",
  140. }
  141. func (self Op) String() string {
  142. if ret := OpNames[self]; ret != "" {
  143. return ret
  144. } else {
  145. return "<invalid>"
  146. }
  147. }
  148. func OP_int() Op {
  149. switch _INT_SIZE {
  150. case 32:
  151. return OP_i32
  152. case 64:
  153. return OP_i64
  154. default:
  155. panic("unsupported int size")
  156. }
  157. }
  158. func OP_uint() Op {
  159. switch _INT_SIZE {
  160. case 32:
  161. return OP_u32
  162. case 64:
  163. return OP_u64
  164. default:
  165. panic("unsupported uint size")
  166. }
  167. }
  168. func OP_uintptr() Op {
  169. switch _PTR_SIZE {
  170. case 32:
  171. return OP_u32
  172. case 64:
  173. return OP_u64
  174. default:
  175. panic("unsupported pointer size")
  176. }
  177. }
  178. func OP_is_zero_ints() Op {
  179. switch _INT_SIZE {
  180. case 32:
  181. return OP_is_zero_4
  182. case 64:
  183. return OP_is_zero_8
  184. default:
  185. panic("unsupported integer size")
  186. }
  187. }
  188. type Instr struct {
  189. o Op
  190. u int // union {op: 8, _: 8, vi: 48}, vi maybe int or len(str)
  191. p unsafe.Pointer // maybe GoString.Ptr, or *GoType
  192. }
  193. func NewInsOp(op Op) Instr {
  194. return Instr{o: op}
  195. }
  196. func NewInsVi(op Op, vi int) Instr {
  197. return Instr{o: op, u: vi}
  198. }
  199. func NewInsVs(op Op, vs string) Instr {
  200. return Instr{
  201. o: op,
  202. u: len(vs),
  203. p: (*rt.GoString)(unsafe.Pointer(&vs)).Ptr,
  204. }
  205. }
  206. func NewInsVt(op Op, vt reflect.Type) Instr {
  207. return Instr{
  208. o: op,
  209. p: unsafe.Pointer(rt.UnpackType(vt)),
  210. }
  211. }
  212. type typAndTab struct {
  213. vt *rt.GoType
  214. itab *rt.GoItab
  215. }
  216. type typAndField struct {
  217. vt reflect.Type
  218. fv *resolver.FieldMeta
  219. }
  220. func NewInsVtab(op Op, vt reflect.Type, itab *rt.GoItab) Instr {
  221. return Instr{
  222. o: op,
  223. p: unsafe.Pointer(&typAndTab{
  224. vt: rt.UnpackType(vt),
  225. itab: itab,
  226. }),
  227. }
  228. }
  229. func NewInsField(op Op, fv *resolver.FieldMeta) Instr {
  230. return Instr{
  231. o: op,
  232. p: unsafe.Pointer(fv),
  233. }
  234. }
  235. func NewInsVp(op Op, vt reflect.Type, pv bool) Instr {
  236. i := 0
  237. if pv {
  238. i = 1
  239. }
  240. return Instr{
  241. o: op,
  242. u: i,
  243. p: unsafe.Pointer(rt.UnpackType(vt)),
  244. }
  245. }
  246. func (self Instr) Op() Op {
  247. return Op(self.o)
  248. }
  249. func (self Instr) Vi() int {
  250. return self.u
  251. }
  252. func (self Instr) Vf() uint8 {
  253. return (*rt.GoType)(self.p).KindFlags
  254. }
  255. func (self Instr) VField() (*resolver.FieldMeta) {
  256. return (*resolver.FieldMeta)(self.p)
  257. }
  258. func (self Instr) Vs() (v string) {
  259. (*rt.GoString)(unsafe.Pointer(&v)).Ptr = self.p
  260. (*rt.GoString)(unsafe.Pointer(&v)).Len = self.Vi()
  261. return
  262. }
  263. func (self Instr) Vk() reflect.Kind {
  264. return (*rt.GoType)(self.p).Kind()
  265. }
  266. func (self Instr) GoType() *rt.GoType {
  267. return (*rt.GoType)(self.p)
  268. }
  269. func (self Instr) Vt() reflect.Type {
  270. return (*rt.GoType)(self.p).Pack()
  271. }
  272. func (self Instr) Vr() *rt.GoType {
  273. return (*rt.GoType)(self.p)
  274. }
  275. func (self Instr) Vp() (vt reflect.Type, pv bool) {
  276. return (*rt.GoType)(self.p).Pack(), self.u == 1
  277. }
  278. func (self Instr) Vtab() (vt *rt.GoType, itab *rt.GoItab) {
  279. tt := (*typAndTab)(self.p)
  280. return tt.vt, tt.itab
  281. }
  282. func (self Instr) Vp2() (vt *rt.GoType, pv bool) {
  283. return (*rt.GoType)(self.p), self.u == 1
  284. }
  285. func (self Instr) I64() int64 {
  286. return int64(self.Vi())
  287. }
  288. func (self Instr) Byte() byte {
  289. return byte(self.Vi())
  290. }
  291. func (self Instr) Vlen() int {
  292. return int((*rt.GoType)(self.p).Size)
  293. }
  294. func (self Instr) isBranch() bool {
  295. switch self.Op() {
  296. case OP_goto:
  297. fallthrough
  298. case OP_is_nil:
  299. fallthrough
  300. case OP_is_nil_p1:
  301. fallthrough
  302. case OP_is_zero_1:
  303. fallthrough
  304. case OP_is_zero_2:
  305. fallthrough
  306. case OP_is_zero_4:
  307. fallthrough
  308. case OP_is_zero_8:
  309. fallthrough
  310. case OP_map_check_key:
  311. fallthrough
  312. case OP_map_write_key:
  313. fallthrough
  314. case OP_slice_next:
  315. fallthrough
  316. case OP_cond_testc:
  317. return true
  318. default:
  319. return false
  320. }
  321. }
  322. func (self Instr) Disassemble() string {
  323. switch self.Op() {
  324. case OP_byte:
  325. return fmt.Sprintf("%-18s%s", self.Op().String(), strconv.QuoteRune(rune(self.Vi())))
  326. case OP_text:
  327. return fmt.Sprintf("%-18s%s", self.Op().String(), strconv.Quote(self.Vs()))
  328. case OP_index:
  329. return fmt.Sprintf("%-18s%d", self.Op().String(), self.Vi())
  330. case OP_recurse:
  331. fallthrough
  332. case OP_map_iter:
  333. return fmt.Sprintf("%-18s%s", self.Op().String(), self.Vt())
  334. case OP_marshal:
  335. fallthrough
  336. case OP_marshal_p:
  337. fallthrough
  338. case OP_marshal_text:
  339. fallthrough
  340. case OP_marshal_text_p:
  341. vt, _ := self.Vtab()
  342. return fmt.Sprintf("%-18s%s", self.Op().String(), vt.Pack())
  343. case OP_goto:
  344. fallthrough
  345. case OP_is_nil:
  346. fallthrough
  347. case OP_is_nil_p1:
  348. fallthrough
  349. case OP_is_zero_1:
  350. fallthrough
  351. case OP_is_zero_2:
  352. fallthrough
  353. case OP_is_zero_4:
  354. fallthrough
  355. case OP_is_zero_8:
  356. fallthrough
  357. case OP_is_zero_map:
  358. fallthrough
  359. case OP_cond_testc:
  360. fallthrough
  361. case OP_map_check_key:
  362. fallthrough
  363. case OP_map_write_key:
  364. return fmt.Sprintf("%-18sL_%d", self.Op().String(), self.Vi())
  365. case OP_slice_next:
  366. return fmt.Sprintf("%-18sL_%d, %s", self.Op().String(), self.Vi(), self.Vt())
  367. default:
  368. return fmt.Sprintf("%#v", self)
  369. }
  370. }
  371. type (
  372. Program []Instr
  373. )
  374. func (self Program) PC() int {
  375. return len(self)
  376. }
  377. func (self Program) Tag(n int) {
  378. if n >= vars.MaxStack {
  379. panic("type nesting too deep")
  380. }
  381. }
  382. func (self Program) Pin(i int) {
  383. v := &self[i]
  384. v.u = self.PC()
  385. }
  386. func (self Program) Rel(v []int) {
  387. for _, i := range v {
  388. self.Pin(i)
  389. }
  390. }
  391. func (self *Program) Add(op Op) {
  392. *self = append(*self, NewInsOp(op))
  393. }
  394. func (self *Program) Key(op Op) {
  395. *self = append(*self,
  396. NewInsVi(OP_byte, '"'),
  397. NewInsOp(op),
  398. NewInsVi(OP_byte, '"'),
  399. )
  400. }
  401. func (self *Program) Int(op Op, vi int) {
  402. *self = append(*self, NewInsVi(op, vi))
  403. }
  404. func (self *Program) Str(op Op, vs string) {
  405. *self = append(*self, NewInsVs(op, vs))
  406. }
  407. func (self *Program) Rtt(op Op, vt reflect.Type) {
  408. *self = append(*self, NewInsVt(op, vt))
  409. }
  410. func (self *Program) Vp(op Op, vt reflect.Type, pv bool) {
  411. *self = append(*self, NewInsVp(op, vt, pv))
  412. }
  413. func (self *Program) Vtab(op Op, vt reflect.Type, itab *rt.GoItab) {
  414. *self = append(*self, NewInsVtab(op, vt, itab))
  415. }
  416. func (self *Program) VField(op Op, fv *resolver.FieldMeta) {
  417. *self = append(*self, NewInsField(op, fv))
  418. }
  419. func (self Program) Disassemble() string {
  420. nb := len(self)
  421. tab := make([]bool, nb+1)
  422. ret := make([]string, 0, nb+1)
  423. /* prescan to get all the labels */
  424. for _, ins := range self {
  425. if ins.isBranch() {
  426. tab[ins.Vi()] = true
  427. }
  428. }
  429. /* disassemble each instruction */
  430. for i, ins := range self {
  431. if !tab[i] {
  432. ret = append(ret, "\t"+ins.Disassemble())
  433. } else {
  434. ret = append(ret, fmt.Sprintf("L_%d:\n\t%s", i, ins.Disassemble()))
  435. }
  436. }
  437. /* add the last label, if needed */
  438. if tab[nb] {
  439. ret = append(ret, fmt.Sprintf("L_%d:", nb))
  440. }
  441. /* add an "end" indicator, and join all the strings */
  442. return strings.Join(append(ret, "\tend"), "\n")
  443. }