Module: Diameter::Internals::AVPParser
- Defined in:
- lib/diameter/avp_parser.rb
Overview
Parser mixin, sharing functionality common to:
* parsing all the AVPs in a message
* parsing the AVPs inside a Grouped AVP
Class Method Summary collapse
-
.mandatory_bit(flags) ⇒ true, false
Is the mandatory bit (the second bit) set?.
-
.parse_avp_header(bytes) ⇒ Array(Fixnum, Fixnum, Bool, Fixnum, Fixnum)
(8 or 12), AVP code, mandatory bit, length and vendor-ID (or 0 in the case of a non-vendor-specific AVP).
-
.parse_avps_int(bytes) ⇒ Array<AVP>
private
The AVPs parsed out of the bytes.
-
.vendor_id_bit(flags) ⇒ true, false
Is the vendor-specific bit (the top bit) set?.
Class Method Details
.mandatory_bit(flags) ⇒ true, false
Is the mandatory bit (the second bit) set?
22 23 24 |
# File 'lib/diameter/avp_parser.rb', line 22 def self.mandatory_bit(flags) flags[1] == '1' end |
.parse_avp_header(bytes) ⇒ Array(Fixnum, Fixnum, Bool, Fixnum, Fixnum)
(8 or 12), AVP code, mandatory bit, length and vendor-ID (or 0 in the case of a non-vendor-specific AVP).
30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 |
# File 'lib/diameter/avp_parser.rb', line 30 def self.parse_avp_header(bytes) first_avp_header = bytes[0..8] # Parse them code, avp_flags, alength_8, alength_16 = first_avp_header.unpack('NB8Cn') mandatory = mandatory_bit(avp_flags) length = UInt24.from_u8_and_u16(alength_8, alength_16) if vendor_id_bit(avp_flags) avp_vendor_header = bytes[8..12] avp_vendor, = avp_vendor_header.unpack('N') [12, code, mandatory, length, avp_vendor] else [8, code, mandatory, length, 0] end end |
.parse_avps_int(bytes) ⇒ Array<AVP>
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Returns The AVPs parsed out of the bytes.
52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 |
# File 'lib/diameter/avp_parser.rb', line 52 def self.parse_avps_int(bytes) avps = [] position = 0 while position < bytes.length # Consume the first 8 octets avp_consumed, code, mandatory, length, avp_vendor = parse_avp_header(bytes[position..-1]) position += avp_consumed # Read the content, ensuring it aligns to a 32-byte boundary avp_content_length = length - avp_consumed avp_content = bytes[position..(position + avp_content_length) - 1] padding = 0 padding += 1 until ((avp_content_length + padding) % 4) == 0 position += avp_content_length + padding # Construct an AVP object from the parsed data parsed_avp = AVP.new(code, vendor_id: avp_vendor, mandatory: mandatory, content: avp_content) avps.push parsed_avp end avps end |
.vendor_id_bit(flags) ⇒ true, false
Is the vendor-specific bit (the top bit) set?
14 15 16 |
# File 'lib/diameter/avp_parser.rb', line 14 def self.vendor_id_bit(flags) flags[0] == '1' end |