RFC 4465 - Signaling Compression (SigComp) Torture Tests(3)

时间:2006-11-02 来源: 作者: 点击:
;$next_addressgivesjumpto ;address_a :address_g END-MESSAGE(0,0,0,0,0,0,0) Theoutputofthecodeis0x00010102020303040405050607070708 08080909,andatotalof131UDVMcyclesareused. 2.15.StateCreation Thissect
  
                                   ; $next_address gives jump to
                                   ; address_a

   :address_g

   END-MESSAGE (0, 0, 0, 0, 0, 0, 0)

   The output of the code is 0x0001 0102 0203 0304 0405 0506 0707 0708
   0808 0909, and a total of 131 UDVM cycles are used.

2.15.  State Creation

   This section gives assembly code to test the STATE-CREATE and STATE-
   FREE instructions.  The code is designed to test that the following
   boundary cases have been correctly implemented:

   1.  An item of state is created that duplicates an existing state
       item.

   2.  An item of state is freed when the state has not been created.

   3.  An item of state is created and then freed by the same message.

   4.  The STATE-FREE instruction frees a state item by sending fewer
       bytes of the state_identifier than the minimum_access_length.

   5.  The STATE-FREE instruction has partial_identifier_length operand
       shorter than 6 or longer than 20.

   6.  The STATE-FREE instruction specifies a partial_identifier that
       matches with two state items in the compartment.

   7.  The bytes of the identifier are written to the position specified
       in the STATE-FREE instruction after the STATE-FREE instruction
       has been run (and before END-MESSAGE).

   at (64)

   :byte_copy_left                 pad (2)
   :byte_copy_right                pad (2)
   :states                         pad (1)
   :states_lsb                     pad (1)
   :min_len                        pad (1)
   :min_len_lsb                    pad (1)

   :state_identifier       pad (20)

   set (state_length, 10)

   at (127)
   :decompression_failure
   at (128)

   INPUT-BYTES (1, states_lsb, decompression_failure)

   :test_one
   LSHIFT ($states, 11)
   COMPARE ($states, 32768, test_two, create_state_a2, create_state_a2)

   :create_state_a2
   STATE-CREATE (state_length, state_address2, 0, 20, 0)

   :test_two
   LSHIFT ($states, 1)
   COMPARE ($states, 32768, test_three, create_state_a, create_state_a)

   :create_state_a
   STATE-CREATE (state_length, state_address, 0, 20, 0)

   :test_three
   LSHIFT ($states, 1)
   COMPARE ($states, 32768, test_four, free_state, free_state)

   :free_state
   INPUT-BYTES (1, min_len_lsb, decompression_failure)
   STATE-FREE (state_identifier, $min_len)
   COPY (identifier1, $min_len, state_identifier)

   :test_four

   LSHIFT ($states, 1)
   COMPARE ($states, 32768, test_five, free_state2, free_state2)

   :free_state2
   STATE-FREE (identifier1, 6)

   :test_five
   LSHIFT ($states, 1)
   COMPARE ($states, 32768, end, create_state_b, create_state_b)

   :create_state_b
   END-MESSAGE (0, 0, state_length, state_address, 0, 20, 0)

   :end
   END-MESSAGE (0, 0, 0, 0, 0, 0, 0)

   :identifier1
   byte (67, 122, 232, 10, 15, 220, 30, 106, 135, 193, 182, 42, 118,
   118, 185, 115, 49, 140, 14, 245)

   at (256)
   :state_address
   byte (192, 204, 63, 238, 121, 188, 252, 143, 209, 8)

   :state_address2
   byte (101, 232, 3, 82, 238, 41, 119, 23, 223, 87)

   Upon reaching the END-MESSAGE instruction, the UDVM does not output
   any decompressed data, but instead may make one or more state
   creation or state free requests to the state handler.  Assuming that
   the application does not veto the state creation request (and that
   sufficient state memory is available) the code results in 0, 1, or 2
   state items being present in the compartment.

   The following table lists ten different compressed messages, the
   states created and freed by each, the number of states left after
   each message, and the number of UDVM cycles used.  There are 3 state
   creation instructions:

      create state_a, which has hash identifier1
      create state_b (in END-MESSAGE), which is identical to state_a

      create state_a2, which has a different identifier, but the first 6
      bytes are the same as those of identifier1.

   Message:   Effect:                           # state items:  #cycles:
   0x01       create state_b                             1           23
   0x02       free (id1, 6) = state_b                    0           14
   0x03       free (id1, 6) = state_b; create state_b    1           24

   0x0405     free (id1, 5)                       Decompression failure
   0x0415     free (id1, 21)                      Decompression failure

   0x0406     free (id1, 6) = state_b                    0           23

   0x09       create state_a; create state_b             1           34

   0x1e06     create state_a2; create state_a;
              free (id1, 6) = matches both so no free;
              free (id1, 6) = matches both so no free;   2           46

   0x1e07     create state_a2; create state_a;
              free (id1, 7) = state_a;
              free (id1, 6) = state_a2                   0           47

   0x1e14     create state_a2; create state_a;
              free (id1, 20) = state_a;
              free (id1, 6) = state_a2                   0           60

2.16.  STATE-ACCESS

   This section gives assembly code to test the STATE-ACCESS
   instruction.  The code is designed to test that the following
   boundary cases have been correctly implemented:

   1.  A subset of the bytes contained in a state item is copied to the
       UDVM memory.

   2.  Bytes are copied from beyond the end of the state value.

   3.  The state_instruction operand is set to 0.

   4.  The state cannot be accessed because the partial state identifier
       is too short.

   5.  The state identifier is overwritten by the state item being
       accessed.

   The following bytecode needs to be run first to set up the state for
   the rest of the test.

   at (128)

   END-MESSAGE (0, 0, state_length, state_start, 0, 20, 0)

   ; The bytes between state_start and state_end are derived from
   ; translation of the following mnemonic code:
   ;
   ; at (512)
   ; OUTPUT (data, 4)
   ; END-MESSAGE (0,0,0,0,0,0,0)
   ; :data
   ; byte (116, 101, 115, 116)

   at (512)
   :state_start
   byte (34, 162, 12,4, 35, 0, 0, 0, 0, 0, 0, 0, 116, 101, 115, 116)
   :state_end

   set (state_length, (state_end - state_start))

   This is the bytecode for the rest of the test.

   at (64)

   :byte_copy_left                 pad (2)
   :byte_copy_right                pad (2)
   :type                           pad (1)
   :type_lsb                       pad (1)
   :state_value                    pad (4)

   at (127)
   :decompression_failure
   at (128)

   INPUT-BYTES (1, type_lsb, decompression_failure)
   COMPARE ($type, 1, execute_state, extract_state, error_conditions)

   :execute_state

   STATE-ACCESS (state_identifier, 20, 0, 0, 0, 512)

   :extract_state

   STATE-ACCESS (state_identifier, 20, 12, 4, state_value, 0)
   OUTPUT (state_value, 4)
   JUMP (end)

   :error_conditions

   COMPARE ($type, 3, state_not_found, id_too_short, state_too_short)

   :state_not_found

   STATE-ACCESS (128, 20, 0, 0, 0, 0)
   JUMP (end)

   :id_too_short

   STATE-ACCESS (state_identifier, 19, 6, 4, state_value, 0)
   JUMP (end)

   :state_too_short

   STATE-ACCESS (state_identifier, 20, 12, 5, state_value, 0)
   JUMP (end)

   at (484)

   :end

   END-MESSAGE (0, 0, 0, 0, 0, 0, 0)

   at (512)

   :state_identifier

   byte (0x5d, 0xf8, 0xbc, 0x3e, 0x20, 0x93, 0xb5, 0xab, 0xe1, 0xf1,
   0x70, 0x13, 0x42, 0x4c, 0xe7, 0xfe, 0x05, 0xe0, 0x69, 0x39)

   If the compressed message is 0x00, then the output of the code is
   0x7465 7374, and a total of 26 UDVM cycles are used.  If the
   compressed message is 0x01, then the output of the code is also
   0x7465 7374 but in this case using a total of 15 UDVM cycles.  If the
   compressed message is 0x02, 0x03, or 0x04, then decompression failure
   occurs.

3.  Torture Tests for Dispatcher

   The following sections give code to test the various functions of the
   SigComp dispatcher.

3.1.  Useful Values

   This section gives assembly code to test that the SigComp "Useful
   Values" are correctly initialized in the UDVM memory.  It also tests
   that the UDVM is correctly terminated if the bytecode uses too many
   UDVM cycles or tries to write beyond the end of the available memory.

   The code tests that the following boundary cases have been correctly
   implemented:

   1.  The bytecode uses exactly as many UDVM cycles as are available
       (in which case no problems should arise) or one cycle too many
       (in which case decompression failure should occur).  A liberal
       implementation could allow more cycles to be used than are
       strictly available, in which case decompression failure will not
       occur.  This is an implementation choice.  If this choice is
       made, the implementer must be sure that the cycles are checked
       eventually and that decompression failure does occur when
       bytecode uses an excessive number of cycles.  This is tested in
       Section 3.2.

   2.  The bytecode writes to the highest memory address available (in
       which case no problems should arise) or to the memory address
       immediately following the highest available address (in which
       case decompression failure must occur).

   :udvm_memory_size               pad (2)
   :cycles_per_bit                 pad (2)
   :sigcomp_version                pad (2)
   :partial_state_id_length        pad (2)
   :state_length                   pad (2)

   at (64)

   :byte_copy_left                 pad (2)
   :byte_copy_right                pad (2)
   :remaining_cycles               pad (2)
   :check_memory                   pad (1)
   :check_memory_lsb               pad (1)
   :check_cycles                   pad (1)
   :check_cycles_lsb               pad (1)

   at (127)
   :decompression_failure
   at (128)
                               ; Set up a 1-byte buffer
   LOAD (byte_copy_left, 32)
   LOAD (byte_copy_right, 33)

   :test_version

   ; Input a byte containing the version of SigComp being run
   INPUT-BYTES (1, check_memory_lsb, decompression_failure)
   COMPARE ($sigcomp_version, $check_memory, decompression_failure,
   test_state_access, decompression_failure)

   :test_state_access

   COMPARE ($partial_state_id_length, 0, decompression_failure,
   test_length_equals_zero, test_state_length)

   :test_length_equals_zero
                               ; No state was accessed so state_length
                               ; should be zero (first message)
   COMPARE ($state_length, 0, decompression_failure, end,
   decompression_failure)

   :test_state_length
                               ; State was accessed so state_length
                               ; should be 960
   COMPARE ($state_length, 960, decompression_failure, test_udvm_memory,
   decompression_failure)

   :test_udvm_memory
                               ; Copy one byte to
                               ; udvm_memory_size + input - 1
                               ; Succeed when input byte is 0x00
                               ; Fail when input byte is 0x01

   INPUT-BYTES (1, check_memory_lsb, decompression_failure)
   ADD ($check_memory, $udvm_memory_size)
   SUBTRACT ($check_memory, 1)
   COPY (32, 1, $check_memory)

   :test_udvm_cycles

   INPUT-BYTES (1, check_cycles_lsb, decompression_failure)

   ; Work out the total number of cycles available to the UDVM
   ; total_UDVM_cycles = cycles_per_bit * (8 * message_size + 1000)
   ;
   ;       = cycles_per_bit * (8 * (partial_state_id_length + 3) + 1000)

   LOAD (remaining_cycles, $partial_state_id_length)
   ADD ($remaining_cycles, 3)
   MULTIPLY ($remaining_cycles, 8)
   ADD ($remaining_cycles, 1000)

   MULTIPLY ($remaining_cycles, $cycles_per_bit)

   ADD ($remaining_cycles, $check_cycles)

   set (cycles_used_by_bytecode, 856)

   SUBTRACT ($remaining_cycles, cycles_used_by_bytecode)
   COPY (32, $remaining_cycles, 32)
                   ; Copy to use up all cycles available + input byte
                   ; Succeeds when input byte = 0x00
                   ; Fail when input byte = 0x01

   :end
                               ; Create 960 bytes of state for future
                               ; reference
   END-MESSAGE (0, 0, 960, 64, 128, 6, 0)

   The bytecode must be executed a total of four times in order to fully
   test the SigComp Useful Values.  In the first case, the bytecode is
   uploaded as part of the SigComp message with a 1-byte compressed
   message corresponding to the version of SigComp being run.  This
   causes the UDVM to request creation of a new state item and uses a
   total of 968 UDVM cycles.

   Subsequent tests access this state by uploading the state identifier
   as part of the SigComp message.  Note that the SigComp message should
   not contain a returned feedback item (as this would cause the
   bytecode to calculate the total number of available UDVM cycles
   incorrectly).

   A 3-byte compressed message is required for the second and subsequent
   cases, the first byte of which is the version of SigComp in use,
   0xnn.  If the message is 0xnn0000, then the UDVM should successfully
   terminate using exactly the number of available UDVM cycles.
   However, if the message is 0xnn0001, then the UDVM should use too
   many cycles and hence terminate with decompression failure.
   Furthermore, if the message is 0xnn0100, then decompression failure
   must occur because the UDVM attempts to write beyond its available
   memory.

3.2.  Cycles Checking

   As discussed in Section 3.1, it is possible to write an
   implementation that takes a liberal approach to checking the cycles
   used and allows some extra cycles.  The implementer must be sure that
   decompression failure does not occur too early and that in the case
   of excessive use of cycles, decompression failure does eventually
   occur.  This test checks that:

   1.  Decompression failure occurs eventually when there is an infinite
       loop.

   at (64)
   :byte_copy_left           pad (2)
   :byte_copy_right          pad (2)
   :value                    pad (2)
   :copy_next                pad (2)

   at(128)
   MULTILOAD (byte_copy_left, 4, 32, 41, 0, 34)
                                   ; Set up a 10-byte buffer

                                   ; Set the value to copy
                                   ; Copy it 100 times,
                                   ; output the value,
                                   ; increment the counter
   :loop
   COPY (value, 2, $byte_copy_left)
   COPY-OFFSET (2, 100, $copy_next)
   OUTPUT (value, 2)
   ADD ($value, 1)
   JUMP (loop)

   If the cycles are counted exactly and cycles per bit (cpb) = 16, then
   decompression failure will occur at COPY-OFFSET when value = 180 =
   0xB4.  If cpb = 32, then decompression failure will occur when value
   = 361 = 0x0169.  If they are not counted exactly, then decompression
   failure MUST occur eventually.

3.3.  Message-based Transport

   This section provides a set of messages to test the SigComp header
   over a message-based transport such as UDP.  The messages test that
   the following boundary cases have been correctly implemented:

   1.  The UDVM bytecode is copied to different areas of the UDVM
       memory.

   2.  The decompression memory size is set to an incorrect value.

   3.  The SigComp message is too short.

   4.  The destination address is invalid.

   The basic version of the code used in the test is given below.  Note
   that the code is designed to calculate the decompression memory size
   based on the Useful Values provided to the UDVM:

   :udvm_memory_size               pad (2)
   :cycles_per_bit                 pad (2)
   :sigcomp_version                pad (2)
   :partial_state_id_length        pad (2)
   :state_length                   pad (2)

   at (128)

   :code_start

   ; udvm_memory_size for message-based transport
   ;    = DMS - total_message_size

   ADD ($udvm_memory_size, total_message_size)
   OUTPUT (udvm_memory_size, 2)
   END-MESSAGE (0, 0, 0, 0, 0, 0, 1)

   :code_end

   set (header_size, 3)
   set (code_size, (code_end - code_start))
   set (total_message_size, (header_size + code_size))

   A number of complete SigComp messages are given below, each
   containing some or all of the above code.  In each case, it is
   indicated whether the message will successfully output the
   decompression memory size or whether it will cause a decompression
   failure to occur (together with the reason for the failure):

   SigComp message:                Effect:

   0xf8                            Fails (message too short)

   0xf800                          Fails (message too short)

   0xf800 e106 0011 2200 0223      Outputs the decompression_memory_size
   0x0000 0000 0000 01

   0xf800 f106 0011 2200 0223      Fails (message too short)
   0x0000 0000 0000 01

   0xf800 e006 0011 2200 0223      Fails (invalid destination address)
   0x0000 0000 0000 01

   0xf800 ee06 0011 2200 0223      Outputs the decompression_memory_size
   0x0000 0000 0000 01

   The messages should be decompressed in the order given to check that
   an error in one message does not interfere with the successful
   decompression of subsequent messages.

   The two messages that successfully decompress each use a total of 5
   UDVM cycles.

3.4.  Stream-based Transport

   This section provides a byte stream to test the SigComp header and
   delimiters over a stream-based transport such as TCP.  The byte
   stream tests all of the boundary cases covered in Section 3.2, as
   well as the following cases specific to stream-based transports:

   1.  Quoted bytes are used by the record marking scheme.

   2.  Multiple delimiters are used between the same pair of messages.

   3.  Unnecessary delimiters are included at the start of the stream.

   The basic version of the code used in the test is given below.  Note
   that the code is designed to calculate the decompression memory size
   based on the Useful Values provided to the UDVM:

   :udvm_memory_size               pad (2)
   :cycles_per_bit                 pad (2)
   :sigcomp_version                pad (2)
   :partial_state_id_length        pad (2)
   :state_length                   pad (2)

   at (128)

   ; udvm_memory_size for stream based transport = DMS / 2

   MULTIPLY ($udvm_memory_size, 2)
   OUTPUT (udvm_memory_size, 2)
   OUTPUT (test_record_marking, 5)
   END-MESSAGE (0, 0, 0, 0, 0, 0, 0)

   :test_record_marking

   byte (255, 255, 255, 255, 255)

   The above assembly code has been compiled and used to generate the
   following byte stream:

   0xffff f801 7108 0002 2200 0222 a092 0523 0000 0000 0000 00ff 00ff
   0x03ff ffff ffff ffff f801 7e08 0002 2200 0222 a3d2 0523 0000 0000
   0x0000 00ff 04ff ffff ffff ffff ffff ff

   Note that this byte stream can be divided into five distinct portions
   (two SigComp messages and three sets of delimiters) as illustrated
   below:

   Portion of byte stream:                                Meaning:

   0xffff                                                 Delimiter

   0xf801 7108 0002 2200 0222 a092 0523                   First message
   0x0000 0000 0000 00ff 00ff 03ff ffff

   0xffff ffff                                            Delimiter

   0xf801 7e08 0002 2200 0222 a3d2 0523                   Second message
   0x0000 0000 0000 00ff 04ff ffff ff

   0xffff ffff ffff                                       Delimiter

   When the complete byte stream is supplied to the decompressor
   dispatcher, the record marking scheme must use the delimiters to
   partition the stream into two distinct SigComp messages.  Both of
   these messages successfully output the decompression memory size (as
   a 2-byte value), followed by 5 consecutive 0xff bytes to test that
   the record marking scheme is working correctly.  A total of 11 UDVM
   cycles are used in each case.

   It must also be checked that the dispatcher can handle the same error
   cases as covered in Section 3.2.  Each of the following byte streams
   should cause a decompression failure to occur for the reason stated:

   Byte stream:                                      Reason for failure:

   0xf8ff ff                                         Message too short

   0xf800 ffff                                       Message too short

   0xf801 8108 0002 2200 0222 a092 0523 ffff         Message too short
   0x0000 0000 0000 00ff 00ff 03ff ffff

   0xf801 7008 0002 2200 0222 a092 0523 ffff         Invalid destination
   0x0000 0000 0000 00ff 04ff ffff ff

3.5.  Input Past the End of a Message

   This section gives assembly code to test that the implementation
   correctly handles input past the end of a SigComp message.  The code
   is designed to test that the following boundary cases have been
   correctly implemented:
------分隔线----------------------------
顶一下
(0)
0%
踩一下
(0)
0%
------分隔线----------------------------
最新评论 查看所有评论
发表评论 查看所有评论
请自觉遵守互联网相关的政策法规,严禁发布色情、暴力、反动的言论。
评价:
表情:
用户名: 密码: 验证码:
推荐内容