Class: PacketGen::Header::IKE

Inherits:
Base show all
Defined in:
lib/packetgen/header/ike.rb,
lib/packetgen/header/ike/id.rb,
lib/packetgen/header/ike/ke.rb,
lib/packetgen/header/ike/sa.rb,
lib/packetgen/header/ike/sk.rb,
lib/packetgen/header/ike/ts.rb,
lib/packetgen/header/ike/auth.rb,
lib/packetgen/header/ike/cert.rb,
lib/packetgen/header/ike/nonce.rb,
lib/packetgen/header/ike/notify.rb,
lib/packetgen/header/ike/certreq.rb,
lib/packetgen/header/ike/payload.rb,
lib/packetgen/header/ike/vendor_id.rb

Overview

IKE is the Internet Key Exchange protocol (RFC 7296). Ony IKEv2 is supported.

A IKE header consists of a header, and a set of payloads. This class handles IKE header. For payloads, see Payload.

IKE header

The format of a IKE header is shown below:

                     1                   2                   3
 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                       IKE SA Initiator's SPI                  |
|                                                               |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                       IKE SA Responder's SPI                  |
|                                                               |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|  Next Payload | MjVer | MnVer | Exchange Type |     Flags     |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                          Message ID                           |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                            Length                             |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

A IKE header consists of:

Create a IKE header

Standalone

ike = PacketGen::Header::IKE.new

Classical IKE packet

pkt = PacketGen.gen('IP').add('UDP').add('IKE')
# access to IKE header
pkt.ike    # => PacketGen::Header::IKE

NAT-T IKE packet

# NonESPMarker is used to insert a 32-bit null field between UDP header
# and IKE one to differentiate it from ESP-in-UDP (see RFC 3948)
pkt = PacketGen.gen('IP').add('UDP').add('NonESPMarker').add('IKE)

Since:

  • 2.0.0

Defined Under Namespace

Classes: Attribute, Attributes, Auth, Cert, CertReq, IDi, IDr, KE, Nonce, Notify, Payload, SA, SAProposal, SAProposals, SK, TSi, TSr, TrafficSelector, TrafficSelectors, Transform, Transforms, VendorID

Constant Summary collapse

UDP_PORT1 =

Classical well-known UDP port for IKE

Since:

  • 2.0.0

500
UDP_PORT2 =

Well-known UDP port for IKE when NAT is detected

Since:

  • 2.0.0

4500
PROTO_IKE =

Since:

  • 2.0.0

1
PROTO_AH =

Since:

  • 2.0.0

2
PROTO_ESP =

Since:

  • 2.0.0

3
EXCHANGE_TYPES =

Since:

  • 2.0.0

{
  'IKE_SA_INIT'     => 34,
  'IKE_AUTH'        => 35,
  'CREATE_CHILD_SA' => 36,
  'INFORMATIONAL'   => 37
}.freeze

Instance Attribute Summary collapse

Attributes inherited from Base

#packet

Instance Method Summary collapse

Methods inherited from Base

bind, bind_header, calculate_and_set_length, #header_id, inherited, #ip_header, known_headers, #ll_header, #method_name, #parse?, #protocol_name, protocol_name

Methods inherited from Types::Fields

#[], #[]=, #bits_on, #body=, define_bit_fields_on, define_field, define_field_after, define_field_before, delete_field, fields, #fields, #force_binary, inherited, #is_optional?, #is_present?, #offset_of, #optional?, #optional_fields, #present?, #read, remove_bit_fields_on, remove_field, #sz, #to_h, #to_s, update_field

Constructor Details

#initialize(options = {}) ⇒ IKE

Returns a new instance of IKE.

Parameters:

  • options (Hash) (defaults to: {})

See Also:

Since:

  • 2.0.0



155
156
157
158
159
160
# File 'lib/packetgen/header/ike.rb', line 155

def initialize(options={})
  super
  calc_length unless options[:length]
  self.type = options[:type] if options[:type]
  self.type = options[:exchange_type] if options[:exchange_type]
end

Instance Attribute Details

#exchange_typeInteger (readonly) Also known as: type

8-bit exchange type

Returns:

  • (Integer)


112
# File 'lib/packetgen/header/ike.rb', line 112

define_field :exchange_type, Types::Int8Enum, enum: EXCHANGE_TYPES

#flag_iBoolean

bit set in message sent by the original initiator

Returns:

  • (Boolean)


151
# File 'lib/packetgen/header/ike.rb', line 151

define_bit_fields_on :flags, :rsv1, 2, :flag_r, :flag_v, :flag_i, :rsv2, 3

#flag_rBoolean

indicate this message is a response to a message containing the same Message ID

Returns:

  • (Boolean)


151
# File 'lib/packetgen/header/ike.rb', line 151

define_bit_fields_on :flags, :rsv1, 2, :flag_r, :flag_v, :flag_i, :rsv2, 3

#flag_vBoolean

version flag. Ignored by IKEv2 peers, and should be set to 0

Returns:

  • (Boolean)


151
# File 'lib/packetgen/header/ike.rb', line 151

define_bit_fields_on :flags, :rsv1, 2, :flag_r, :flag_v, :flag_i, :rsv2, 3

#flagsInteger

8-bit flags

Returns:

  • (Integer)


116
# File 'lib/packetgen/header/ike.rb', line 116

define_field :flags, Types::Int8

#init_spiInteger

64-bit initiator SPI

Returns:

  • (Integer)


96
# File 'lib/packetgen/header/ike.rb', line 96

define_field :init_spi, Types::Int64

#lengthInteger

32-bit length of total message (header + payloads)

Returns:

  • (Integer)


124
# File 'lib/packetgen/header/ike.rb', line 124

define_field :length, Types::Int32

#message_idInteger

32-bit message ID

Returns:

  • (Integer)


120
# File 'lib/packetgen/header/ike.rb', line 120

define_field :message_id, Types::Int32

#mjverInteger

4-bit major version value

Returns:

  • (Integer)


136
# File 'lib/packetgen/header/ike.rb', line 136

define_bit_fields_on :version, :mjver, 4, :mnver, 4

#mnverInteger

4-bit minor version value

Returns:

  • (Integer)


136
# File 'lib/packetgen/header/ike.rb', line 136

define_bit_fields_on :version, :mjver, 4, :mnver, 4

#nextInteger

8-bit next payload type

Returns:

  • (Integer)


104
# File 'lib/packetgen/header/ike.rb', line 104

define_field :next, Types::Int8

#resp_spiInteger

64-bit responder SPI

Returns:

  • (Integer)


100
# File 'lib/packetgen/header/ike.rb', line 100

define_field :resp_spi, Types::Int64

#rsv1Integer

Returns:

  • (Integer)


151
# File 'lib/packetgen/header/ike.rb', line 151

define_bit_fields_on :flags, :rsv1, 2, :flag_r, :flag_v, :flag_i, :rsv2, 3

#rsv2Integer

Returns:

  • (Integer)


151
# File 'lib/packetgen/header/ike.rb', line 151

define_bit_fields_on :flags, :rsv1, 2, :flag_r, :flag_v, :flag_i, :rsv2, 3

#versionInteger

8-bit IKE version

Returns:

  • (Integer)


108
# File 'lib/packetgen/header/ike.rb', line 108

define_field :version, Types::Int8, default: 0x20

Instance Method Details

#added_to_packet(packet) ⇒ void

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.

Note:

This method is used internally by PacketGen and should not be directly called

This method returns an undefined value.

Parameters:

Since:

  • 2.7.0 Set UDP sport according to bindings, only if sport is 0. Needed by new bind API.



221
222
223
224
225
226
227
228
229
# File 'lib/packetgen/header/ike.rb', line 221

def added_to_packet(packet)
  return unless packet.is? 'UDP'
  return unless packet.udp.sport.zero?
  packet.udp.sport = if packet.is?('NonESPMarker')
                       UDP_PORT2
                     else
                       UDP_PORT1
                     end
end

#calc_lengthInteger

Calculate length field

Returns:

  • (Integer)

Since:

  • 2.0.0



174
175
176
# File 'lib/packetgen/header/ike.rb', line 174

def calc_length
  Base.calculate_and_set_length self
end

#human_exchange_typeString Also known as: human_type

Get exchange type name

Returns:

  • (String)

    String

Since:

  • 2.0.0



167
168
169
# File 'lib/packetgen/header/ike.rb', line 167

def human_exchange_type
  self[:exchange_type].to_human
end

#inspectString

Returns:

  • (String)

Since:

  • 2.0.0



191
192
193
194
195
196
197
198
199
200
201
202
203
204
# File 'lib/packetgen/header/ike.rb', line 191

def inspect
  super do |attr|
    case attr
    when :flags
      str_flags = ''.dup
      %w[r v i].each do |flag|
        str_flags << (send("flag_#{flag}?") ? flag.upcase : '.')
      end
      str = Inspect.shift_level
      str << Inspect::FMT_ATTR % [self[attr].class.to_s.sub(/.*::/, ''), attr,
                                  str_flags]
    end
  end
end

#payloadsArray<Payload>

IKE payloads

Returns:

Since:

  • 2.0.0



180
181
182
183
184
185
186
187
188
# File 'lib/packetgen/header/ike.rb', line 180

def payloads
  payloads = []
  body = self.body
  while body.is_a?(Payload)
    payloads << body
    body = body.body
  end
  payloads
end

#reply!self

Toggle I and R flags.

Returns:

  • (self)

Since:

  • 2.0.0



208
209
210
211
212
# File 'lib/packetgen/header/ike.rb', line 208

def reply!
  self.flag_r = !self.flag_r?
  self.flag_i = !self.flag_i?
  self
end