github.com/cloudwego/frugal@v0.1.15/internal/binary/decoder/skipping_emu_test.go (about)

     1  /*
     2   * Copyright 2022 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  
    17  package decoder
    18  
    19  import (
    20      `encoding/hex`
    21      `testing`
    22      `unsafe`
    23  
    24      `github.com/cloudwego/frugal/internal/binary/defs`
    25      `github.com/cloudwego/frugal/internal/rt`
    26  )
    27  
    28  func run_skipping_emu(t *testing.T, v []byte, exp int, tag defs.Tag) {
    29      var sb _skipbuf_t
    30      mm := *(*rt.GoSlice)(unsafe.Pointer(&v))
    31      rv := do_skip(&sb, mm.Ptr, mm.Len, tag)
    32      if rv != exp {
    33          if rv >= 0 && exp < 0 {
    34              t.Errorf("got %d while expecting error %d", rv, exp)
    35          } else if rv < 0 && exp >= 0 {
    36              t.Errorf("got unexpected error %d while expecting %d", rv, exp)
    37          } else if rv < 0 && exp < 0 {
    38              t.Errorf("got a wrong error %d while expecting error %d", rv, exp)
    39          } else {
    40              t.Errorf("got unexpected return value %d while expecting %d", rv, exp)
    41          }
    42          t.FailNow()
    43      }
    44  }
    45  
    46  func TestSkippingEmu_SkipPrimitives(t *testing.T) {
    47      run_skipping_emu(t, []byte{0}                      , 1, defs.T_bool)
    48      run_skipping_emu(t, []byte{0}                      , 1, defs.T_i8)
    49      run_skipping_emu(t, []byte{0, 1, 2, 3, 4, 5, 6, 7} , 8, defs.T_double)
    50      run_skipping_emu(t, []byte{0, 1}                   , 2, defs.T_i16)
    51      run_skipping_emu(t, []byte{0, 1, 2, 3}             , 4, defs.T_i32)
    52      run_skipping_emu(t, []byte{0, 1, 2, 3, 4, 5, 6, 7} , 8, defs.T_i64)
    53  }
    54  
    55  func TestSkippingEmu_SkipPrimitivesButGotEOF(t *testing.T) {
    56      run_skipping_emu(t, []byte{}                    , EEOF, defs.T_bool)
    57      run_skipping_emu(t, []byte{}                    , EEOF, defs.T_i8)
    58      run_skipping_emu(t, []byte{}                    , EEOF, defs.T_double)
    59      run_skipping_emu(t, []byte{0}                   , EEOF, defs.T_double)
    60      run_skipping_emu(t, []byte{0, 1}                , EEOF, defs.T_double)
    61      run_skipping_emu(t, []byte{0, 1, 2}             , EEOF, defs.T_double)
    62      run_skipping_emu(t, []byte{0, 1, 2, 3}          , EEOF, defs.T_double)
    63      run_skipping_emu(t, []byte{0, 1, 2, 3, 4}       , EEOF, defs.T_double)
    64      run_skipping_emu(t, []byte{0, 1, 2, 3, 4, 5}    , EEOF, defs.T_double)
    65      run_skipping_emu(t, []byte{0, 1, 2, 3, 4, 5, 6} , EEOF, defs.T_double)
    66      run_skipping_emu(t, []byte{}                    , EEOF, defs.T_i16)
    67      run_skipping_emu(t, []byte{0}                   , EEOF, defs.T_i16)
    68      run_skipping_emu(t, []byte{}                    , EEOF, defs.T_i32)
    69      run_skipping_emu(t, []byte{0}                   , EEOF, defs.T_i32)
    70      run_skipping_emu(t, []byte{0, 1}                , EEOF, defs.T_i32)
    71      run_skipping_emu(t, []byte{0, 1, 2}             , EEOF, defs.T_i32)
    72      run_skipping_emu(t, []byte{}                    , EEOF, defs.T_i64)
    73      run_skipping_emu(t, []byte{0}                   , EEOF, defs.T_i64)
    74      run_skipping_emu(t, []byte{0, 1}                , EEOF, defs.T_i64)
    75      run_skipping_emu(t, []byte{0, 1, 2}             , EEOF, defs.T_i64)
    76      run_skipping_emu(t, []byte{0, 1, 2, 3}          , EEOF, defs.T_i64)
    77      run_skipping_emu(t, []byte{0, 1, 2, 3, 4}       , EEOF, defs.T_i64)
    78      run_skipping_emu(t, []byte{0, 1, 2, 3, 4, 5}    , EEOF, defs.T_i64)
    79      run_skipping_emu(t, []byte{0, 1, 2, 3, 4, 5, 6} , EEOF, defs.T_i64)
    80  }
    81  
    82  func TestSkippingEmu_SkipStringsAndBinaries(t *testing.T) {
    83      run_skipping_emu(t, []byte{0, 0, 0, 0}                     ,  4, defs.T_string)
    84      run_skipping_emu(t, []byte("\x00\x00\x00\x0chello, world") , 16, defs.T_string)
    85  }
    86  
    87  func TestSkippingEmu_SkipStringsAndBinariesButGotEOF(t *testing.T) {
    88      run_skipping_emu(t, []byte{}                              , EEOF, defs.T_string)
    89      run_skipping_emu(t, []byte{0}                             , EEOF, defs.T_string)
    90      run_skipping_emu(t, []byte{0, 0}                          , EEOF, defs.T_string)
    91      run_skipping_emu(t, []byte{0, 0, 0}                       , EEOF, defs.T_string)
    92      run_skipping_emu(t, []byte{0, 0, 0, 12}                   , EEOF, defs.T_string)
    93      run_skipping_emu(t, []byte("\x00\x00\x00\x0ch")           , EEOF, defs.T_string)
    94      run_skipping_emu(t, []byte("\x00\x00\x00\x0che")          , EEOF, defs.T_string)
    95      run_skipping_emu(t, []byte("\x00\x00\x00\x0chel")         , EEOF, defs.T_string)
    96      run_skipping_emu(t, []byte("\x00\x00\x00\x0chell")        , EEOF, defs.T_string)
    97      run_skipping_emu(t, []byte("\x00\x00\x00\x0chello")       , EEOF, defs.T_string)
    98      run_skipping_emu(t, []byte("\x00\x00\x00\x0chello,")      , EEOF, defs.T_string)
    99      run_skipping_emu(t, []byte("\x00\x00\x00\x0chello, ")     , EEOF, defs.T_string)
   100      run_skipping_emu(t, []byte("\x00\x00\x00\x0chello, w")    , EEOF, defs.T_string)
   101      run_skipping_emu(t, []byte("\x00\x00\x00\x0chello, wo")   , EEOF, defs.T_string)
   102      run_skipping_emu(t, []byte("\x00\x00\x00\x0chello, wor")  , EEOF, defs.T_string)
   103      run_skipping_emu(t, []byte("\x00\x00\x00\x0chello, worl") , EEOF, defs.T_string)
   104  }
   105  
   106  func TestSkippingEmu_SkipStruct(t *testing.T) {
   107      run_skipping_emu(t, []byte{ 0}                                             ,  1, defs.T_struct)
   108      run_skipping_emu(t, []byte{ 2, 0, 0, 1, 0}                                 ,  5, defs.T_struct)
   109      run_skipping_emu(t, []byte{ 3, 0, 0, 1, 0}                                 ,  5, defs.T_struct)
   110      run_skipping_emu(t, []byte{ 3, 0, 0, 1, 6, 0, 1, 1, 2, 0}                  , 10, defs.T_struct)
   111      run_skipping_emu(t, []byte{ 4, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 0}            , 12, defs.T_struct)
   112      run_skipping_emu(t, []byte{ 6, 0, 0, 1, 2, 0}                              ,  6, defs.T_struct)
   113      run_skipping_emu(t, []byte{ 8, 0, 0, 1, 2, 3, 4, 0}                        ,  8, defs.T_struct)
   114      run_skipping_emu(t, []byte{10, 0, 0, 1, 2, 3, 4, 5, 6, 7, 8, 0}            , 12, defs.T_struct)
   115      run_skipping_emu(t, []byte("\x0b\x00\x00\x00\x00\x00\x0chello, world\x00") , 20, defs.T_struct)
   116      run_skipping_emu(t, []byte{12, 0, 0, 0, 0}                                 ,  5, defs.T_struct)
   117      run_skipping_emu(t, []byte{12, 0, 0, 3, 0, 0, 1, 0, 0}                     ,  9, defs.T_struct)
   118      run_skipping_emu(t, []byte{13, 0, 0, 3, 6, 0, 0, 0, 1, 1, 2, 3, 0}         , 13, defs.T_struct)
   119      run_skipping_emu(t, []byte{14, 0, 0, 8, 0, 0, 0, 1, 1, 2, 3, 4, 0}         , 13, defs.T_struct)
   120      run_skipping_emu(t, []byte{15, 0, 0, 6, 0, 0, 0, 2, 1, 2, 3, 4, 0}         , 13, defs.T_struct)
   121  }
   122  
   123  func TestSkippingEmu_SkipStructButGotErrors(t *testing.T) {
   124      run_skipping_emu(t, []byte{}         , EEOF, defs.T_struct)
   125      run_skipping_emu(t, []byte{ 2}       , EEOF, defs.T_struct)
   126      run_skipping_emu(t, []byte{ 2, 0, 0} , EEOF, defs.T_struct)
   127      run_skipping_emu(t, []byte{ 9}       , ETAG, defs.T_struct)
   128      run_skipping_emu(t, []byte{11}       , EEOF, defs.T_struct)
   129      run_skipping_emu(t, []byte{11, 0, 0} , EEOF, defs.T_struct)
   130  }
   131  
   132  func TestSkippingEmu_SkipMapOfPrimitives(t *testing.T) {
   133      run_skipping_emu(t, []byte{3, 6, 0, 0, 0, 0}                                     ,  6, defs.T_map)
   134      run_skipping_emu(t, []byte{3, 6, 0, 0, 0, 3, 1, 2, 3, 4, 5, 6, 7, 8, 9}          , 15, defs.T_map)
   135      run_skipping_emu(t, []byte{6, 8, 0, 0, 0, 2, 1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4} , 18, defs.T_map)
   136  }
   137  
   138  func TestSkippingEmu_SkipMapWithNonPrimitiveKeys(t *testing.T) {
   139      run_skipping_emu(t, []byte{11, 8, 0, 0, 0, 0}                                              ,  6, defs.T_map)
   140      run_skipping_emu(t, []byte("\x0b\x08\x00\x00\x00\x01\x00\x00\x00\x04test\x01\x02\x03\x04") , 18, defs.T_map)
   141  }
   142  
   143  func TestSkippingEmu_SkipMapButGotErrors(t *testing.T) {
   144      run_skipping_emu(t, []byte{}                                                     , EEOF, defs.T_map)
   145      run_skipping_emu(t, []byte{3}                                                    , EEOF, defs.T_map)
   146      run_skipping_emu(t, []byte{3, 6}                                                 , EEOF, defs.T_map)
   147      run_skipping_emu(t, []byte{3, 6, 0}                                              , EEOF, defs.T_map)
   148      run_skipping_emu(t, []byte{3, 6, 0, 0}                                           , EEOF, defs.T_map)
   149      run_skipping_emu(t, []byte{3, 6, 0, 0, 0}                                        , EEOF, defs.T_map)
   150      run_skipping_emu(t, []byte{3, 6, 0, 0, 0, 1}                                     , EEOF, defs.T_map)
   151      run_skipping_emu(t, []byte{3, 6, 0, 0, 0, 2, 1}                                  , EEOF, defs.T_map)
   152      run_skipping_emu(t, []byte{9, 6, 0, 0, 0, 0}                                     , ETAG, defs.T_map)
   153      run_skipping_emu(t, []byte{3, 9, 0, 0, 0, 3, 1, 2, 3, 4, 5, 6, 7, 8, 9}          , ETAG, defs.T_map)
   154      run_skipping_emu(t, []byte{9, 9, 0, 0, 0, 2, 1, 2, 3, 4, 5, 6, 7, 8, 1, 2, 3, 4} , ETAG, defs.T_map)
   155      run_skipping_emu(t, []byte("\x0b\x0b\x00\x00\x00\x01")                           , EEOF, defs.T_map)
   156  }
   157  
   158  func TestSkippingEmu_SkipSetOrListOfPrimitives(t *testing.T) {
   159      run_skipping_emu(t, []byte{ 2, 0, 0, 0, 16, 1, 2, 3, 4, 5, 6, 7, 8, 4, 3, 2, 1, 8, 7, 6, 5}, 21, defs.T_list)
   160      run_skipping_emu(t, []byte{ 3, 0, 0, 0, 16, 1, 2, 3, 4, 5, 6, 7, 8, 4, 3, 2, 1, 8, 7, 6, 5}, 21, defs.T_list)
   161      run_skipping_emu(t, []byte{ 4, 0, 0, 0,  2, 1, 2, 3, 4, 5, 6, 7, 8, 4, 3, 2, 1, 8, 7, 6, 5}, 21, defs.T_list)
   162      run_skipping_emu(t, []byte{ 6, 0, 0, 0,  8, 1, 2, 3, 4, 5, 6, 7, 8, 4, 3, 2, 1, 8, 7, 6, 5}, 21, defs.T_list)
   163      run_skipping_emu(t, []byte{ 8, 0, 0, 0,  4, 1, 2, 3, 4, 5, 6, 7, 8, 4, 3, 2, 1, 8, 7, 6, 5}, 21, defs.T_list)
   164      run_skipping_emu(t, []byte{10, 0, 0, 0,  2, 1, 2, 3, 4, 5, 6, 7, 8, 4, 3, 2, 1, 8, 7, 6, 5}, 21, defs.T_list)
   165  }
   166  
   167  func TestSkippingEmu_SkipSetOrListOfBinariesOrStrings(t *testing.T) {
   168      run_skipping_emu(t, []byte("\x0b\x00\x00\x00\x00")                             ,  5, defs.T_list)
   169      run_skipping_emu(t, []byte("\x0b\x00\x00\x00\x01\x00\x00\x00\x00")             ,  9, defs.T_list)
   170      run_skipping_emu(t, []byte("\x0b\x00\x00\x00\x01\x00\x00\x00\x0chello, world") , 21, defs.T_list)
   171  }
   172  
   173  func TestSkippingEmu_SkipSetOrListButGotErrors(t *testing.T) {
   174      run_skipping_emu(t, []byte{}                       , EEOF, defs.T_list)
   175      run_skipping_emu(t, []byte{2}                      , EEOF, defs.T_list)
   176      run_skipping_emu(t, []byte{2, 0}                   , EEOF, defs.T_list)
   177      run_skipping_emu(t, []byte{2, 0, 0}                , EEOF, defs.T_list)
   178      run_skipping_emu(t, []byte{2, 0, 0, 0}             , EEOF, defs.T_list)
   179      run_skipping_emu(t, []byte{2, 0, 0, 0, 1}          , EEOF, defs.T_list)
   180      run_skipping_emu(t, []byte{2, 0, 0, 0, 2, 1}       , EEOF, defs.T_list)
   181      run_skipping_emu(t, []byte{9, 0, 0, 0, 1, 2}       , ETAG, defs.T_list)
   182      run_skipping_emu(t, []byte("\x0b\x00\x00\x00\x01") , EEOF, defs.T_list)
   183  }
   184  
   185  func TestSkipListMap(t *testing.T) {
   186      listMap, err := hex.DecodeString("0f00010d000000020b0b00000001000000016100000001620b0b000000010000000161000000016200")
   187      if err != nil {
   188          t.Fatal(err)
   189      }
   190      var fsm _skipbuf_t
   191      var in = (*rt.GoSlice)(unsafe.Pointer(&listMap))
   192      rv := do_skip(&fsm, in.Ptr, in.Len, defs.T_struct)
   193      if rv != len(listMap) {
   194          t.Fatalf("skip failed: %d", rv)
   195      }
   196  }