pio 0.5.0 → 0.6.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +13 -1
- data/README.md +25 -1
- data/examples/echo_new.rb +9 -0
- data/examples/echo_read.rb +4 -0
- data/lib/pio.rb +1 -0
- data/lib/pio/echo.rb +25 -0
- data/lib/pio/echo/format.rb +18 -0
- data/lib/pio/echo/message.rb +39 -0
- data/lib/pio/echo/reply.rb +16 -0
- data/lib/pio/echo/request.rb +16 -0
- data/lib/pio/hello/format.rb +1 -1
- data/lib/pio/version.rb +1 -1
- data/spec/pio/echo/reply_spec.rb +20 -0
- data/spec/pio/echo/request_spec.rb +47 -0
- data/spec/pio/echo_spec.rb +43 -0
- data/spec/pio/hello_spec.rb +7 -0
- metadata +15 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 24250e762b41db6e78d190ece32de1a57bbba89c
|
4
|
+
data.tar.gz: df8706edd1b12d95750bb240b21ea93021b09d1d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 008fe84cace5c6050f941180a8122dbcfbcdb475936efef993002dc33b6f939149d000c7d5955c9396defaef49a6e6a85e6d6c5f1ca460fa50b772e8ed5ae182
|
7
|
+
data.tar.gz: af12f5c7bca4549a0c2ce34531def8ece2d530b88ef091763f84c782d0fbaa5c8081936982c074325391e4bed7d43b22b7b014362e6a9f72ac76ae04e2b95f2d
|
data/CHANGELOG.md
CHANGED
@@ -1,11 +1,23 @@
|
|
1
1
|
# Changelog
|
2
2
|
|
3
|
+
## 0.6.0 (4/15/2014)
|
4
|
+
|
5
|
+
### New features
|
6
|
+
* Added new class `Pio::Echo`, `Pio::Echo::Request` and `Pio::Echo::Reply`.
|
7
|
+
|
8
|
+
|
9
|
+
## 0.5.1 (4/15/2014)
|
10
|
+
|
11
|
+
### Bugs fixed
|
12
|
+
* Set hello message type = 0.
|
13
|
+
|
14
|
+
|
3
15
|
## 0.5.0 (4/14/2014)
|
4
16
|
|
17
|
+
### New features
|
5
18
|
* Added new class `Pio::Hello`.
|
6
19
|
|
7
20
|
### Misc
|
8
|
-
|
9
21
|
* Added new rake task `cucumber`.
|
10
22
|
* Added new rake task `dump_pcap`.
|
11
23
|
|
data/README.md
CHANGED
@@ -16,8 +16,9 @@ supports the following packet formats:
|
|
16
16
|
- ARP
|
17
17
|
- LLDP
|
18
18
|
- DHCP
|
19
|
-
- OpenFlow 1.0
|
19
|
+
- OpenFlow 1.0
|
20
20
|
- Hello
|
21
|
+
- Echo Request and Reply
|
21
22
|
- (…currently there are just a few formats supported but I'm sure this list will grow)
|
22
23
|
|
23
24
|
## Features Overview
|
@@ -178,6 +179,29 @@ below:
|
|
178
179
|
hello = Pio::Hello.new(transaction_id: 123)
|
179
180
|
hello.to_binary # => HELLO message in binary format.
|
180
181
|
|
182
|
+
## Echo
|
183
|
+
|
184
|
+
To parse an OpenFlow 1.0 ECHO message, use the API `Pio::Echo.read`
|
185
|
+
and you can access each field of the parsed ECHO message.
|
186
|
+
|
187
|
+
require 'pio'
|
188
|
+
|
189
|
+
echo = Pio::Echo.read(binary_data)
|
190
|
+
echo.xid # => 123
|
191
|
+
|
192
|
+
Also you can use `Pio::Echo::Request#new` or `Pio::Echo::Reply#new` to
|
193
|
+
generate an Echo Request/Reply message like below:
|
194
|
+
|
195
|
+
require 'pio'
|
196
|
+
|
197
|
+
request = Pio::Echo::Request.new
|
198
|
+
request.to_binary # => ECHO Request message in binary format.
|
199
|
+
|
200
|
+
# The ECHO xid (transaction_id)
|
201
|
+
# should be same as that of the request.
|
202
|
+
reply = Pio::Echo::Reply.new(xid: request.xid)
|
203
|
+
reply.to_binary # => ECHO Reply message in binary format.
|
204
|
+
|
181
205
|
## Installation
|
182
206
|
|
183
207
|
The simplest way to install Pio is to use [Bundler](http://gembundler.com/).
|
@@ -0,0 +1,9 @@
|
|
1
|
+
require 'pio'
|
2
|
+
|
3
|
+
request = Pio::Echo::Request.new
|
4
|
+
request.to_binary # => ECHO Request message in binary format.
|
5
|
+
|
6
|
+
# The ECHO xid (transaction_id)
|
7
|
+
# should be same as that of the request.
|
8
|
+
reply = Pio::Echo::Reply.new(xid: request.xid)
|
9
|
+
reply.to_binary # => ECHO Reply message in binary format.
|
data/lib/pio.rb
CHANGED
data/lib/pio/echo.rb
ADDED
@@ -0,0 +1,25 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'pio/echo/format'
|
4
|
+
require 'pio/echo/reply'
|
5
|
+
require 'pio/echo/request'
|
6
|
+
|
7
|
+
module Pio
|
8
|
+
# OpenFlow Echo Request and Reply message parser.
|
9
|
+
class Echo
|
10
|
+
REQUEST = 2
|
11
|
+
REPLY = 3
|
12
|
+
|
13
|
+
def self.read(raw_data)
|
14
|
+
echo = Echo::Format.read(raw_data)
|
15
|
+
case echo.message_type
|
16
|
+
when REQUEST
|
17
|
+
Echo::Request.create_from(echo)
|
18
|
+
when REPLY
|
19
|
+
Echo::Reply.create_from(echo)
|
20
|
+
else
|
21
|
+
fail 'Unknown Echo message type.'
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'bindata'
|
4
|
+
|
5
|
+
module Pio
|
6
|
+
class Echo
|
7
|
+
# OpenFlow 1.0 Echo message format.
|
8
|
+
class Format < BinData::Record
|
9
|
+
endian :big
|
10
|
+
|
11
|
+
uint8 :version, value: 1
|
12
|
+
uint8 :message_type
|
13
|
+
uint16 :message_length, value: -> { 8 + data.length }
|
14
|
+
uint32 :transaction_id, initial_value: 0
|
15
|
+
string :data
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'forwardable'
|
4
|
+
require 'bindata'
|
5
|
+
|
6
|
+
module Pio
|
7
|
+
class Echo
|
8
|
+
# Base class of Echo request and reply.
|
9
|
+
class Message
|
10
|
+
extend Forwardable
|
11
|
+
|
12
|
+
def_delegators :@echo, :version
|
13
|
+
def_delegators :@echo, :message_type
|
14
|
+
def_delegators :@echo, :message_length
|
15
|
+
def_delegators :@echo, :transaction_id
|
16
|
+
def_delegator :@echo, :transaction_id, :xid
|
17
|
+
def_delegators :@echo, :data
|
18
|
+
def_delegator :@echo, :to_binary_s, :to_binary
|
19
|
+
|
20
|
+
def self.create_from(echo)
|
21
|
+
message = allocate
|
22
|
+
message.instance_variable_set :@echo, echo
|
23
|
+
message
|
24
|
+
end
|
25
|
+
|
26
|
+
def initialize(message_type, user_options = {})
|
27
|
+
@options = user_options.dup.merge(message_type: message_type)
|
28
|
+
handle_option_aliases
|
29
|
+
@echo = Format.new(@options)
|
30
|
+
end
|
31
|
+
|
32
|
+
private
|
33
|
+
|
34
|
+
def handle_option_aliases
|
35
|
+
@options[:transaction_id] ||= @options[:xid]
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'pio/echo/format'
|
4
|
+
require 'pio/echo/message'
|
5
|
+
|
6
|
+
module Pio
|
7
|
+
# OpenFlow Echo Request and Reply message parser.
|
8
|
+
class Echo
|
9
|
+
# OpenFlow 1.0 Echo Reply message.
|
10
|
+
class Reply < Message
|
11
|
+
def initialize(user_options = {})
|
12
|
+
super REPLY, user_options
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'pio/echo/format'
|
4
|
+
require 'pio/echo/message'
|
5
|
+
|
6
|
+
module Pio
|
7
|
+
# OpenFlow Echo Request and Reply message parser.
|
8
|
+
class Echo
|
9
|
+
# OpenFlow 1.0 Echo Request message.
|
10
|
+
class Request < Message
|
11
|
+
def initialize(user_options = {})
|
12
|
+
super REQUEST, user_options
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
data/lib/pio/hello/format.rb
CHANGED
data/lib/pio/version.rb
CHANGED
@@ -0,0 +1,20 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'pio'
|
4
|
+
|
5
|
+
describe Pio::Echo::Reply do
|
6
|
+
describe '.new' do
|
7
|
+
context 'with no additional data' do
|
8
|
+
When(:echo_reply) do
|
9
|
+
Pio::Echo::Reply.new(xid: 123)
|
10
|
+
end
|
11
|
+
|
12
|
+
Then { echo_reply.class == Pio::Echo::Reply }
|
13
|
+
Then { echo_reply.version == 1 }
|
14
|
+
Then { echo_reply.message_type == Pio::Echo::REPLY }
|
15
|
+
Then { echo_reply.message_length == 8 }
|
16
|
+
Then { echo_reply.xid == 123 }
|
17
|
+
Then { echo_reply.data == '' }
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'pio'
|
4
|
+
|
5
|
+
describe Pio::Echo::Request do
|
6
|
+
describe '.new' do
|
7
|
+
Given(:echo_request) do
|
8
|
+
Pio::Echo::Request.new(user_options)
|
9
|
+
end
|
10
|
+
|
11
|
+
context 'with no arguments' do
|
12
|
+
When(:user_options) { {} }
|
13
|
+
|
14
|
+
Then { echo_request.class == Pio::Echo::Request }
|
15
|
+
Then { echo_request.version == 1 }
|
16
|
+
Then { echo_request.message_type == Pio::Echo::REQUEST }
|
17
|
+
Then { echo_request.message_length == 8 }
|
18
|
+
Then { echo_request.transaction_id == 0 }
|
19
|
+
Then { echo_request.xid == 0 }
|
20
|
+
Then { echo_request.data == '' }
|
21
|
+
end
|
22
|
+
|
23
|
+
context 'with transaction_id: 123' do
|
24
|
+
When(:user_options) { { transaction_id: 123 } }
|
25
|
+
|
26
|
+
Then { echo_request.class == Pio::Echo::Request }
|
27
|
+
Then { echo_request.version == 1 }
|
28
|
+
Then { echo_request.message_type == Pio::Echo::REQUEST }
|
29
|
+
Then { echo_request.message_length == 8 }
|
30
|
+
Then { echo_request.transaction_id == 123 }
|
31
|
+
Then { echo_request.xid == 123 }
|
32
|
+
Then { echo_request.data == '' }
|
33
|
+
end
|
34
|
+
|
35
|
+
context 'with xid: 123' do
|
36
|
+
When(:user_options) { { xid: 123 } }
|
37
|
+
|
38
|
+
Then { echo_request.class == Pio::Echo::Request }
|
39
|
+
Then { echo_request.version == 1 }
|
40
|
+
Then { echo_request.message_type == Pio::Echo::REQUEST }
|
41
|
+
Then { echo_request.message_length == 8 }
|
42
|
+
Then { echo_request.transaction_id == 123 }
|
43
|
+
Then { echo_request.xid == 123 }
|
44
|
+
Then { echo_request.data == '' }
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
@@ -0,0 +1,43 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'pio'
|
4
|
+
|
5
|
+
describe Pio::Echo do
|
6
|
+
describe '.read' do
|
7
|
+
context 'with an Echo Request message' do
|
8
|
+
Given(:echo_request_dump) do
|
9
|
+
[1, 2, 0, 8, 0, 0, 0, 0].pack('C*')
|
10
|
+
end
|
11
|
+
|
12
|
+
When(:echo_request) do
|
13
|
+
Pio::Echo.read echo_request_dump
|
14
|
+
end
|
15
|
+
|
16
|
+
Then { echo_request.class == Pio::Echo::Request }
|
17
|
+
Then { echo_request.version == 1 }
|
18
|
+
Then { echo_request.message_type == Pio::Echo::REQUEST }
|
19
|
+
Then { echo_request.message_length == 8 }
|
20
|
+
Then { echo_request.xid == 0 }
|
21
|
+
Then { echo_request.data == '' }
|
22
|
+
Then { echo_request.to_binary == echo_request_dump }
|
23
|
+
end
|
24
|
+
|
25
|
+
context 'with an Echo Reply message' do
|
26
|
+
Given(:echo_reply_dump) do
|
27
|
+
[1, 3, 0, 8, 0, 0, 0, 0].pack('C*')
|
28
|
+
end
|
29
|
+
|
30
|
+
When(:echo_reply) do
|
31
|
+
Pio::Echo.read echo_reply_dump
|
32
|
+
end
|
33
|
+
|
34
|
+
Then { echo_reply.class == Pio::Echo::Reply }
|
35
|
+
Then { echo_reply.version == 1 }
|
36
|
+
Then { echo_reply.message_type == Pio::Echo::REPLY }
|
37
|
+
Then { echo_reply.message_length == 8 }
|
38
|
+
Then { echo_reply.xid == 0 }
|
39
|
+
Then { echo_reply.data == '' }
|
40
|
+
Then { echo_reply.to_binary == echo_reply_dump }
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
data/spec/pio/hello_spec.rb
CHANGED
@@ -16,6 +16,13 @@ describe Pio::Hello do
|
|
16
16
|
Then { hello.xid == 0 }
|
17
17
|
Then { hello.body.empty? }
|
18
18
|
end
|
19
|
+
|
20
|
+
context 'with an features-request message' do
|
21
|
+
Given(:features_request_dump) { [1, 5, 0, 8, 0, 0, 0, 0].pack('C*') }
|
22
|
+
|
23
|
+
When(:result) { Pio::Hello.read(features_request_dump) }
|
24
|
+
Then { result == Failure(BinData::ValidityError) }
|
25
|
+
end
|
19
26
|
end
|
20
27
|
|
21
28
|
describe '.new' do
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: pio
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.6.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Yasuhito Takamiya
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2014-04-
|
11
|
+
date: 2014-04-15 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bindata
|
@@ -58,6 +58,8 @@ files:
|
|
58
58
|
- examples/arp_read.rb
|
59
59
|
- examples/dhcp_new.rb
|
60
60
|
- examples/dhcp_read.rb
|
61
|
+
- examples/echo_new.rb
|
62
|
+
- examples/echo_read.rb
|
61
63
|
- examples/hello_new.rb
|
62
64
|
- examples/hello_read.rb
|
63
65
|
- examples/icmp_new.rb
|
@@ -101,6 +103,11 @@ files:
|
|
101
103
|
- lib/pio/dhcp/optional_tlv.rb
|
102
104
|
- lib/pio/dhcp/parameter_list.rb
|
103
105
|
- lib/pio/dhcp/request.rb
|
106
|
+
- lib/pio/echo.rb
|
107
|
+
- lib/pio/echo/format.rb
|
108
|
+
- lib/pio/echo/message.rb
|
109
|
+
- lib/pio/echo/reply.rb
|
110
|
+
- lib/pio/echo/request.rb
|
104
111
|
- lib/pio/hello.rb
|
105
112
|
- lib/pio/hello/format.rb
|
106
113
|
- lib/pio/icmp.rb
|
@@ -146,6 +153,9 @@ files:
|
|
146
153
|
- spec/pio/dhcp/offer_spec.rb
|
147
154
|
- spec/pio/dhcp/request_spec.rb
|
148
155
|
- spec/pio/dhcp_spec.rb
|
156
|
+
- spec/pio/echo/reply_spec.rb
|
157
|
+
- spec/pio/echo/request_spec.rb
|
158
|
+
- spec/pio/echo_spec.rb
|
149
159
|
- spec/pio/hello_spec.rb
|
150
160
|
- spec/pio/icmp/reply_spec.rb
|
151
161
|
- spec/pio/icmp/request_spec.rb
|
@@ -186,6 +196,7 @@ test_files:
|
|
186
196
|
- spec/pio/dhcp/offer_spec.rb
|
187
197
|
- spec/pio/dhcp/ack_spec.rb
|
188
198
|
- spec/pio/dhcp/discover_spec.rb
|
199
|
+
- spec/pio/echo_spec.rb
|
189
200
|
- spec/pio/arp/request_spec.rb
|
190
201
|
- spec/pio/arp/reply/options_spec.rb
|
191
202
|
- spec/pio/arp/request/options_spec.rb
|
@@ -198,6 +209,8 @@ test_files:
|
|
198
209
|
- spec/pio/dhcp_spec.rb
|
199
210
|
- spec/pio/lldp_spec.rb
|
200
211
|
- spec/pio/arp_spec.rb
|
212
|
+
- spec/pio/echo/request_spec.rb
|
213
|
+
- spec/pio/echo/reply_spec.rb
|
201
214
|
- spec/spec_helper.rb
|
202
215
|
- features/pcap/dhcp.pcap
|
203
216
|
- features/pcap/arp.pcap
|