Class: Cborb::Decoding::State
- Inherits:
-
Object
- Object
- Cborb::Decoding::State
- Defined in:
- lib/cborb/decoding/state.rb
Overview
State of processing to decode
Constant Summary collapse
- CONTINUE =
Object.new
- NO_RESULT =
Object.new
Instance Method Summary collapse
-
#<<(cbor) ⇒ Object
Buffering new CBOR data.
- #accept_value(type, value) ⇒ Object
-
#consume(size) ⇒ String
Consume CBOR data.
-
#consume_byte ⇒ Integer
Consume 1 byte(uses #getbyte instead of #read).
- #finished? ⇒ Boolean
-
#initialize ⇒ State
constructor
A new instance of State.
-
#push_stack(type, im_data = nil) ⇒ Object
Push type that has following data(e.g. Array) to stack.
- #remaining_bytes ⇒ String
- #result ⇒ Object
-
#stack_top ⇒ Class
Class constant that inherits Cborb::Decoding::Types::Type on top of stack.
Constructor Details
#initialize ⇒ State
Returns a new instance of State.
7 8 9 10 11 12 13 14 15 16 |
# File 'lib/cborb/decoding/state.rb', line 7 def initialize @buffer = Cborb::Decoding::SimpleBuffer.new @stack = [[Cborb::Decoding::Types::Root, nil]] @result = NO_RESULT # This fiber decodes CBOR. # If buffer becomes empty, this fiber is stopped(#consume) # When new CBOR data is buffered(#<<), that is resumed. @decoding_fiber = Fiber.new { loop_consuming } end |
Instance Method Details
#<<(cbor) ⇒ Object
Buffering new CBOR data
21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
# File 'lib/cborb/decoding/state.rb', line 21 def <<(cbor) @buffer.write(cbor) @decoding_fiber.resume rescue FiberError => e msg = e. # umm... if msg.include?("dead") raise Cborb::InvalidByteSequenceError elsif msg.include?("threads") raise Cborb::DecodingError, "Can't decode across threads" else raise end end |
#accept_value(type, value) ⇒ Object
87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 |
# File 'lib/cborb/decoding/state.rb', line 87 def accept_value(type, value) loop do stacked_type, im_data = @stack.last value = stacked_type.accept(im_data, type, value) type = stacked_type if value.eql?(CONTINUE) break else @stack.pop if @stack.empty? @result = value break end end end end |
#consume(size) ⇒ String
Consume CBOR data. This method will be called only in fiber.
43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 |
# File 'lib/cborb/decoding/state.rb', line 43 def consume(size) data = @buffer.read(size).to_s # If buffered data is not enought, yield fiber until new data will be buffered. if data.size < size @buffer.reset! while data.size != size Fiber.yield data += @buffer.read(size - data.size) end end data end |
#consume_byte ⇒ Integer
Consume 1 byte(uses #getbyte instead of #read)
62 63 64 65 66 67 68 69 70 71 72 73 74 75 |
# File 'lib/cborb/decoding/state.rb', line 62 def consume_byte ib = @buffer.getbyte if ib.nil? @buffer.reset! while ib.nil? Fiber.yield ib = @buffer.getbyte end end ib end |
#finished? ⇒ Boolean
111 112 113 |
# File 'lib/cborb/decoding/state.rb', line 111 def finished? !@result.eql?(NO_RESULT) end |
#push_stack(type, im_data = nil) ⇒ Object
Push type that has following data(e.g. Array) to stack
81 82 83 |
# File 'lib/cborb/decoding/state.rb', line 81 def push_stack(type, im_data = nil) @stack << [type, im_data] end |
#remaining_bytes ⇒ String
121 122 123 124 125 126 127 |
# File 'lib/cborb/decoding/state.rb', line 121 def remaining_bytes if finished? @buffer.peek else "" end end |
#result ⇒ Object
116 117 118 |
# File 'lib/cborb/decoding/state.rb', line 116 def result finished? ? @result : nil end |
#stack_top ⇒ Class
Returns Class constant that inherits Cborb::Decoding::Types::Type on top of stack.
106 107 108 |
# File 'lib/cborb/decoding/state.rb', line 106 def stack_top @stack.last.first end |