cosmos 3.1.2 → 3.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Gemfile +3 -0
- data/Manifest.txt +17 -1
- data/autohotkey/tools/test_runner2.ahk +1 -0
- data/autohotkey/tools/tlm_grapher.ahk +13 -1
- data/data/crc.txt +39 -30
- data/demo/config/data/crc.txt +3 -3
- data/demo/config/targets/TEMPLATED/lib/templated_interface.rb +3 -1
- data/demo/config/tools/cmd_tlm_server/cmd_tlm_server.txt +7 -1
- data/demo/config/tools/cmd_tlm_server/cmd_tlm_server2.txt +6 -1
- data/lib/cosmos.rb +2 -2
- data/lib/cosmos/gui/dialogs/about_dialog.rb +18 -5
- data/lib/cosmos/gui/dialogs/tlm_details_dialog.rb +0 -7
- data/lib/cosmos/gui/line_graph/overview_graph.rb +12 -2
- data/lib/cosmos/gui/utilities/script_module_gui.rb +11 -3
- data/lib/cosmos/interfaces/interface.rb +12 -0
- data/lib/cosmos/interfaces/stream_interface.rb +1 -21
- data/lib/cosmos/interfaces/tcpip_server_interface.rb +10 -0
- data/lib/cosmos/io/json_drb_object.rb +75 -56
- data/lib/cosmos/io/tcpip_server.rb +1 -11
- data/lib/cosmos/packet_logs.rb +1 -0
- data/lib/cosmos/packet_logs/ccsds_log_reader.rb +103 -0
- data/lib/cosmos/packets/packet.rb +70 -1
- data/lib/cosmos/packets/packet_config.rb +59 -611
- data/lib/cosmos/packets/parsers/format_string_parser.rb +58 -0
- data/lib/cosmos/packets/parsers/limits_parser.rb +146 -0
- data/lib/cosmos/packets/parsers/limits_response_parser.rb +52 -0
- data/lib/cosmos/packets/parsers/macro_parser.rb +116 -0
- data/lib/cosmos/packets/parsers/packet_item_parser.rb +215 -0
- data/lib/cosmos/packets/parsers/packet_parser.rb +123 -0
- data/lib/cosmos/packets/parsers/processor_parser.rb +63 -0
- data/lib/cosmos/packets/parsers/state_parser.rb +116 -0
- data/lib/cosmos/packets/structure.rb +59 -22
- data/lib/cosmos/packets/structure_item.rb +1 -1
- data/lib/cosmos/script/script.rb +4 -5
- data/lib/cosmos/streams/serial_stream.rb +5 -0
- data/lib/cosmos/streams/stream.rb +8 -2
- data/lib/cosmos/streams/stream_protocol.rb +1 -0
- data/lib/cosmos/streams/tcpip_client_stream.rb +37 -7
- data/lib/cosmos/streams/tcpip_socket_stream.rb +9 -6
- data/lib/cosmos/system/target.rb +3 -6
- data/lib/cosmos/tools/cmd_tlm_server/cmd_tlm_server_config.rb +57 -48
- data/lib/cosmos/tools/cmd_tlm_server/interface_thread.rb +7 -3
- data/lib/cosmos/tools/limits_monitor/limits_monitor.rb +1 -1
- data/lib/cosmos/tools/tlm_grapher/tabbed_plots_tool/tabbed_plots_realtime_thread.rb +7 -1
- data/lib/cosmos/tools/tlm_viewer/tlm_viewer.rb +1 -2
- data/lib/cosmos/top_level.rb +22 -11
- data/lib/cosmos/utilities/message_log.rb +14 -9
- data/lib/cosmos/version.rb +5 -5
- data/spec/interfaces/cmd_tlm_server_interface_spec.rb +16 -16
- data/spec/interfaces/linc_interface_spec.rb +3 -0
- data/spec/interfaces/tcpip_client_interface_spec.rb +1 -0
- data/spec/interfaces/tcpip_server_interface_spec.rb +9 -0
- data/spec/io/json_drb_object_spec.rb +1 -1
- data/spec/io/serial_driver_spec.rb +0 -1
- data/spec/packet_logs/packet_log_writer_spec.rb +5 -3
- data/spec/packets/packet_config_spec.rb +22 -837
- data/spec/packets/packet_item_spec.rb +10 -10
- data/spec/packets/packet_spec.rb +239 -1
- data/spec/packets/parsers/format_string_parser_spec.rb +122 -0
- data/spec/packets/parsers/limits_parser_spec.rb +282 -0
- data/spec/packets/parsers/limits_response_parser_spec.rb +149 -0
- data/spec/packets/parsers/macro_parser_spec.rb +184 -0
- data/spec/packets/parsers/packet_item_parser_spec.rb +306 -0
- data/spec/packets/parsers/packet_parser_spec.rb +99 -0
- data/spec/packets/parsers/processor_parser_spec.rb +114 -0
- data/spec/packets/parsers/state_parser_spec.rb +156 -0
- data/spec/packets/structure_item_spec.rb +14 -14
- data/spec/packets/structure_spec.rb +162 -16
- data/spec/streams/fixed_stream_protocol_spec.rb +7 -4
- data/spec/streams/length_stream_protocol_spec.rb +3 -0
- data/spec/streams/preidentified_stream_protocol_spec.rb +3 -0
- data/spec/streams/serial_stream_spec.rb +12 -0
- data/spec/streams/stream_protocol_spec.rb +14 -0
- data/spec/streams/stream_spec.rb +1 -0
- data/spec/streams/tcpip_client_stream_spec.rb +3 -0
- data/spec/streams/tcpip_socket_stream_spec.rb +15 -3
- data/spec/streams/template_stream_protocol_spec.rb +5 -0
- data/spec/streams/terminated_stream_protocol_spec.rb +4 -0
- data/spec/tools/cmd_tlm_server/cmd_tlm_server_config_spec.rb +21 -1
- data/spec/tools/cmd_tlm_server/interface_thread_spec.rb +1 -1
- data/spec/tools/cmd_tlm_server/interfaces_spec.rb +1 -1
- metadata +19 -3
@@ -32,6 +32,7 @@ module Cosmos
|
|
32
32
|
@filename = ''
|
33
33
|
@file = nil
|
34
34
|
@start_time = nil
|
35
|
+
@mutex = Mutex.new
|
35
36
|
end
|
36
37
|
|
37
38
|
# Ensures the log file is opened and ready to write. It then writes the
|
@@ -39,34 +40,38 @@ module Cosmos
|
|
39
40
|
#
|
40
41
|
# @param message [String] Message to write to the log
|
41
42
|
def write(message)
|
42
|
-
|
43
|
-
|
44
|
-
|
43
|
+
@mutex.synchronize do
|
44
|
+
if @file.nil? or @file.closed? or (not File.exist?(@filename))
|
45
|
+
start(false)
|
46
|
+
end
|
45
47
|
|
46
|
-
|
47
|
-
|
48
|
-
#@file.flush
|
48
|
+
@file.write(message)
|
49
|
+
end
|
49
50
|
end
|
50
51
|
|
51
52
|
# Closes the message log and marks it read only
|
52
|
-
def stop
|
53
|
+
def stop(take_mutex = true)
|
54
|
+
@mutex.lock if take_mutex
|
53
55
|
if @file and not @file.closed?
|
54
56
|
@file.close
|
55
57
|
Cosmos.set_working_dir do
|
56
58
|
File.chmod(0444, @filename)
|
57
59
|
end
|
58
60
|
end
|
61
|
+
@mutex.unlock if take_mutex
|
59
62
|
end
|
60
63
|
|
61
64
|
# Creates a new message log and sets the filename
|
62
|
-
def start
|
65
|
+
def start(take_mutex = true)
|
66
|
+
@mutex.lock if take_mutex
|
63
67
|
# Prevent starting files too fast
|
64
68
|
sleep(0.1) until !File.exist?(File.join(@log_dir, File.build_timestamped_filename([@tool_name, 'messages'])))
|
65
|
-
stop()
|
69
|
+
stop(false)
|
66
70
|
Cosmos.set_working_dir do
|
67
71
|
@filename = File.join(@log_dir, File.build_timestamped_filename([@tool_name, 'messages']))
|
68
72
|
@file = File.open(@filename, 'a')
|
69
73
|
end
|
74
|
+
@mutex.unlock if take_mutex
|
70
75
|
end
|
71
76
|
|
72
77
|
end # class MessageLog
|
data/lib/cosmos/version.rb
CHANGED
@@ -1,12 +1,12 @@
|
|
1
1
|
# encoding: ascii-8bit
|
2
2
|
|
3
|
-
COSMOS_VERSION = '3.
|
3
|
+
COSMOS_VERSION = '3.2.0'
|
4
4
|
module Cosmos
|
5
5
|
module Version
|
6
6
|
MAJOR = '3'
|
7
|
-
MINOR = '
|
8
|
-
PATCH = '
|
9
|
-
BUILD = '
|
7
|
+
MINOR = '2'
|
8
|
+
PATCH = '0'
|
9
|
+
BUILD = '29c04013a08ebeab57b88412820e0cd79782c49f'
|
10
10
|
end
|
11
|
-
VERSION = '3.
|
11
|
+
VERSION = '3.2.0'
|
12
12
|
end
|
@@ -44,31 +44,31 @@ module Cosmos
|
|
44
44
|
sleep 0.1 # Give the server time to really stop all the Threads
|
45
45
|
end
|
46
46
|
|
47
|
-
specify { @ctsi.methods.
|
47
|
+
specify { expect(@ctsi.methods).to include(:cmd) }
|
48
48
|
|
49
49
|
describe "connect, connected?, disconnect" do
|
50
|
-
it "
|
50
|
+
it "subscribes to the server" do
|
51
51
|
expect { @ctsi.connect }.to_not raise_error
|
52
|
-
@ctsi.connected
|
52
|
+
expect(@ctsi.connected?).to be true
|
53
53
|
expect { @ctsi.disconnect}.to_not raise_error
|
54
|
-
@ctsi.connected
|
54
|
+
expect(@ctsi.connected?).to be false
|
55
55
|
end
|
56
56
|
end
|
57
57
|
|
58
58
|
describe "write_raw_allowed?" do
|
59
|
-
it "
|
60
|
-
@ctsi.write_raw_allowed
|
59
|
+
it "returns false" do
|
60
|
+
expect(@ctsi.write_raw_allowed?).to be false
|
61
61
|
end
|
62
62
|
end
|
63
63
|
|
64
64
|
describe "write_raw" do
|
65
|
-
it "
|
65
|
+
it "raises an error" do
|
66
66
|
expect { @ctsi.write_raw(nil) }.to raise_error(/write_raw not implemented/)
|
67
67
|
end
|
68
68
|
end
|
69
69
|
|
70
70
|
describe "read" do
|
71
|
-
it "
|
71
|
+
it "returns the COSMOS VERSION packet and then COSMOS LIMITS_CHANGE" do
|
72
72
|
@ctsi.connect
|
73
73
|
|
74
74
|
pkt = Packet.new("TGT","PKT")
|
@@ -78,25 +78,25 @@ module Cosmos
|
|
78
78
|
@cts.limits_change_callback(pkt, pi, :RED, 100, true)
|
79
79
|
|
80
80
|
result = @ctsi.read
|
81
|
-
result.read('CTDB').
|
81
|
+
expect(result.read('CTDB')).to eql "Demo Version"
|
82
82
|
|
83
83
|
result = @ctsi.read
|
84
|
-
result.read('TARGET').
|
85
|
-
result.read('PACKET').
|
86
|
-
result.read('ITEM').
|
87
|
-
result.read('OLD_STATE').
|
88
|
-
result.read('NEW_STATE').
|
84
|
+
expect(result.read('TARGET')).to eql "TGT"
|
85
|
+
expect(result.read('PACKET')).to eql "PKT"
|
86
|
+
expect(result.read('ITEM')).to eql "ITEM"
|
87
|
+
expect(result.read('OLD_STATE')).to eql "RED"
|
88
|
+
expect(result.read('NEW_STATE')).to eql "GREEN"
|
89
89
|
end
|
90
90
|
end
|
91
91
|
|
92
92
|
describe "write" do
|
93
|
-
it "
|
93
|
+
it "raises an error if the packet is not identified" do
|
94
94
|
pkt = Packet.new("COSMOS","STARTLOGGING")
|
95
95
|
pkt.buffer = "\x00\x00\x00\x00\x00\x00\x00\x00"
|
96
96
|
expect { @ctsi.write(pkt) }.to raise_error(/Unknown command/)
|
97
97
|
end
|
98
98
|
|
99
|
-
it "
|
99
|
+
it "raises an error if the command is not recognized" do
|
100
100
|
pkt = Packet.new("COSMOS","DOSOMETHING")
|
101
101
|
pkt.buffer = "\x00\x00\x00\x00\x00\x00\x00\x00"
|
102
102
|
expect { @ctsi.write(pkt) }.to raise_error(/Unknown command/)
|
@@ -22,6 +22,7 @@ module Cosmos
|
|
22
22
|
describe "connect" do
|
23
23
|
it "should pass a new TcpipClientStream to the stream protocol" do
|
24
24
|
stream = double("stream")
|
25
|
+
allow(stream).to receive(:connect)
|
25
26
|
expect(TcpipClientStream).to receive(:new) { stream }
|
26
27
|
expect(stream).to receive(:connected?) { true }
|
27
28
|
expect(stream).to receive(:raw_logger_pair=) { nil }
|
@@ -36,6 +37,7 @@ module Cosmos
|
|
36
37
|
describe "write" do
|
37
38
|
before(:each) do
|
38
39
|
stream = double("stream")
|
40
|
+
allow(stream).to receive(:connect)
|
39
41
|
expect(TcpipClientStream).to receive(:new) { stream }
|
40
42
|
allow(stream).to receive(:connected?) { true }
|
41
43
|
allow(stream).to receive(:write)
|
@@ -159,6 +161,7 @@ module Cosmos
|
|
159
161
|
describe "read" do
|
160
162
|
before(:each) do
|
161
163
|
stream = double("stream")
|
164
|
+
allow(stream).to receive(:connect)
|
162
165
|
expect(TcpipClientStream).to receive(:new) { stream }
|
163
166
|
allow(stream).to receive(:connected?) { true }
|
164
167
|
allow(stream).to receive(:write)
|
@@ -40,6 +40,7 @@ module Cosmos
|
|
40
40
|
describe "connect" do
|
41
41
|
it "should pass a new TcpipClientStream to the stream protocol" do
|
42
42
|
stream = double("stream")
|
43
|
+
allow(stream).to receive(:connect)
|
43
44
|
expect(TcpipClientStream).to receive(:new) { stream }
|
44
45
|
expect(stream).to receive(:connected?) { true }
|
45
46
|
expect(stream).to receive(:raw_logger_pair=) { nil }
|
@@ -146,6 +146,15 @@ module Cosmos
|
|
146
146
|
expect { i.write_raw('') }.to raise_error("TEST")
|
147
147
|
end
|
148
148
|
end
|
149
|
+
|
150
|
+
describe "set_option" do
|
151
|
+
it "should set the listen address for the tcpip_server" do
|
152
|
+
expect(@stream).to receive(:listen_address=).with('127.0.0.1')
|
153
|
+
i = TcpipServerInterface.new('8888','8889','5','5','burst')
|
154
|
+
i.set_option('LISTEN_ADDRESS', ['127.0.0.1'])
|
155
|
+
end
|
156
|
+
end
|
157
|
+
|
149
158
|
end
|
150
159
|
end
|
151
160
|
|
@@ -40,7 +40,7 @@ module Cosmos
|
|
40
40
|
it "should raise an exception if the remote connection can't be made" do
|
41
41
|
json = JsonDRb.new
|
42
42
|
json.start_service('127.0.0.1', 7777, self)
|
43
|
-
|
43
|
+
allow_any_instance_of(Socket).to receive(:connect_nonblock) { raise "Error" }
|
44
44
|
obj = JsonDRbObject.new("localhost", 7777)
|
45
45
|
expect { obj.my_method(10) }.to raise_error(DRb::DRbConnError)
|
46
46
|
obj.disconnect
|
@@ -130,9 +130,11 @@ module Cosmos
|
|
130
130
|
Dir[File.join(@log_path,"*.bin")].length.should eql 2
|
131
131
|
# Check that the log files have timestamps which are 3 (or 4) seconds apart
|
132
132
|
files = Dir[File.join(@log_path,"*tlm.bin")].sort
|
133
|
-
|
134
|
-
|
135
|
-
(
|
133
|
+
split1 = files[0].split('_')
|
134
|
+
split2 = files[1].split('_')
|
135
|
+
log1_time = Time.new(split1[-7].to_i, split1[-6].to_i, split1[-5].to_i, split1[-4].to_i, split1[-3].to_i, split1[-2].to_i)
|
136
|
+
log2_time = Time.new(split2[-7].to_i, split2[-6].to_i, split2[-5].to_i, split2[-4].to_i, split2[-3].to_i, split2[-2].to_i)
|
137
|
+
(log2_time - log1_time).should be_within(2).of(3)
|
136
138
|
plw.shutdown
|
137
139
|
# Monkey patch the constant back to the default
|
138
140
|
PacketLogWriter.__send__(:remove_const,:CYCLE_TIME_INTERVAL)
|
@@ -30,115 +30,12 @@ module Cosmos
|
|
30
30
|
tf.unlink
|
31
31
|
end
|
32
32
|
|
33
|
-
it "should complain about overlapping items" do
|
34
|
-
tf = Tempfile.new('unittest')
|
35
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
36
|
-
tf.puts ' ITEM item1 0 8 UINT'
|
37
|
-
tf.puts ' ITEM item2 0 8 UINT'
|
38
|
-
tf.close
|
39
|
-
@pc.process_file(tf.path, "TGT1")
|
40
|
-
@pc.warnings[0].should eql "Bit definition overlap at bit offset 0 for Telemetry packet TGT1 PKT1 items ITEM2 and ITEM1"
|
41
|
-
tf.unlink
|
42
|
-
end
|
43
|
-
|
44
|
-
it "should not complain with non-overlapping negative offsets" do
|
45
|
-
tf = Tempfile.new('unittest')
|
46
|
-
tf.puts 'TELEMETRY tgt1 pkt2 LITTLE_ENDIAN "Description"'
|
47
|
-
tf.puts ' ITEM item1 0 8 UINT'
|
48
|
-
tf.puts ' ITEM item2 8 -16 BLOCK'
|
49
|
-
tf.puts ' ITEM item3 -16 16 UINT'
|
50
|
-
tf.close
|
51
|
-
@pc.process_file(tf.path, "TGT1")
|
52
|
-
@pc.warnings[0].should be_nil
|
53
|
-
tf.unlink
|
54
|
-
end
|
55
|
-
|
56
|
-
it "should complain with overlapping negative offsets" do
|
57
|
-
tf = Tempfile.new('unittest')
|
58
|
-
tf.puts 'TELEMETRY tgt1 pkt2 LITTLE_ENDIAN "Description"'
|
59
|
-
tf.puts ' ITEM item1 0 8 UINT'
|
60
|
-
tf.puts ' ITEM item2 8 -16 BLOCK'
|
61
|
-
tf.puts ' ITEM item3 -17 16 UINT'
|
62
|
-
tf.close
|
63
|
-
@pc.process_file(tf.path, "TGT1")
|
64
|
-
@pc.warnings[0].should eql "Bit definition overlap at bit offset -17 for Telemetry packet TGT1 PKT2 items ITEM3 and ITEM2"
|
65
|
-
tf.unlink
|
66
|
-
end
|
67
|
-
|
68
|
-
it "should complain about intersecting items" do
|
69
|
-
tf = Tempfile.new('unittest')
|
70
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
71
|
-
tf.puts ' ITEM item1 0 32 UINT'
|
72
|
-
tf.puts ' ITEM item2 16 32 UINT'
|
73
|
-
tf.close
|
74
|
-
@pc.process_file(tf.path, "TGT1")
|
75
|
-
@pc.warnings[0].should eql "Bit definition overlap at bit offset 16 for Telemetry packet TGT1 PKT1 items ITEM2 and ITEM1"
|
76
|
-
tf.unlink
|
77
|
-
end
|
78
|
-
|
79
|
-
it "should complain about array overlapping items" do
|
80
|
-
tf = Tempfile.new('unittest')
|
81
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
82
|
-
tf.puts ' ARRAY_ITEM item1 0 8 UINT 32'
|
83
|
-
tf.puts ' ARRAY_ITEM item2 0 8 UINT 32'
|
84
|
-
tf.close
|
85
|
-
@pc.process_file(tf.path, "TGT1")
|
86
|
-
@pc.warnings[0].should eql "Bit definition overlap at bit offset 0 for Telemetry packet TGT1 PKT1 items ITEM2 and ITEM1"
|
87
|
-
tf.unlink
|
88
|
-
end
|
89
|
-
|
90
|
-
it "should not complain with array non-overlapping negative offsets" do
|
91
|
-
tf = Tempfile.new('unittest')
|
92
|
-
tf.puts 'TELEMETRY tgt1 pkt2 LITTLE_ENDIAN "Description"'
|
93
|
-
tf.puts ' ITEM item1 0 8 UINT'
|
94
|
-
tf.puts ' ARRAY_ITEM item2 8 8 INT -16'
|
95
|
-
tf.puts ' ITEM item3 -16 16 UINT'
|
96
|
-
tf.close
|
97
|
-
@pc.process_file(tf.path, "TGT1")
|
98
|
-
@pc.warnings[0].should be_nil
|
99
|
-
tf.unlink
|
100
|
-
end
|
101
|
-
|
102
|
-
it "should complain with array overlapping negative offsets" do
|
103
|
-
tf = Tempfile.new('unittest')
|
104
|
-
tf.puts 'TELEMETRY tgt1 pkt2 LITTLE_ENDIAN "Description"'
|
105
|
-
tf.puts ' ITEM item1 0 8 UINT'
|
106
|
-
tf.puts ' ARRAY_ITEM item2 8 8 INT -16'
|
107
|
-
tf.puts ' ITEM item3 -17 16 UINT'
|
108
|
-
tf.close
|
109
|
-
@pc.process_file(tf.path, "TGT1")
|
110
|
-
@pc.warnings[0].should eql "Bit definition overlap at bit offset -17 for Telemetry packet TGT1 PKT2 items ITEM3 and ITEM2"
|
111
|
-
tf.unlink
|
112
|
-
end
|
113
|
-
|
114
|
-
it "should complain about array intersecting items" do
|
115
|
-
tf = Tempfile.new('unittest')
|
116
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
117
|
-
tf.puts ' ARRAY_ITEM item1 0 8 UINT 32'
|
118
|
-
tf.puts ' ARRAY_ITEM item2 16 8 UINT 32'
|
119
|
-
tf.close
|
120
|
-
@pc.process_file(tf.path, "TGT1")
|
121
|
-
@pc.warnings[0].should eql "Bit definition overlap at bit offset 16 for Telemetry packet TGT1 PKT1 items ITEM2 and ITEM1"
|
122
|
-
tf.unlink
|
123
|
-
end
|
124
|
-
|
125
|
-
it "should not complain about nonoverlapping little endian bitfields" do
|
126
|
-
tf = Tempfile.new('unittest')
|
127
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
128
|
-
tf.puts ' ITEM item1 12 12 UINT'
|
129
|
-
tf.puts ' ITEM item2 16 16 UINT'
|
130
|
-
tf.close
|
131
|
-
@pc.process_file(tf.path, "TGT1")
|
132
|
-
@pc.warnings[0].should be_nil
|
133
|
-
tf.unlink
|
134
|
-
end
|
135
|
-
|
136
33
|
context "with all telemetry keywords" do
|
137
34
|
before(:all) do
|
138
35
|
# top level keywords
|
139
|
-
@top_keywords = %w(
|
36
|
+
@top_keywords = %w(SELECT_COMMAND SELECT_TELEMETRY LIMITS_GROUP LIMITS_GROUP_ITEM)
|
140
37
|
# Keywords that require a current packet from TELEMETRY keyword
|
141
|
-
@tlm_keywords = %w(SELECT_ITEM ITEM ID_ITEM ARRAY_ITEM APPEND_ITEM APPEND_ID_ITEM APPEND_ARRAY_ITEM
|
38
|
+
@tlm_keywords = %w(SELECT_ITEM ITEM ID_ITEM ARRAY_ITEM APPEND_ITEM APPEND_ID_ITEM APPEND_ARRAY_ITEM PROCESSOR META)
|
142
39
|
# Keywords that require both a current packet and current item
|
143
40
|
@item_keywords = %w(STATE READ_CONVERSION WRITE_CONVERSION POLY_READ_CONVERSION POLY_WRITE_CONVERSION SEG_POLY_READ_CONVERSION SEG_POLY_WRITE_CONVERSION GENERIC_READ_CONVERSION_START GENERIC_WRITE_CONVERSION_START LIMITS LIMITS_RESPONSE UNITS FORMAT_STRING DESCRIPTION META)
|
144
41
|
end
|
@@ -177,7 +74,6 @@ module Cosmos
|
|
177
74
|
end
|
178
75
|
|
179
76
|
@tlm_keywords.each do |keyword|
|
180
|
-
next if %w(MACRO_APPEND_END).include? keyword
|
181
77
|
tf = Tempfile.new('unittest')
|
182
78
|
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
183
79
|
tf.puts keyword
|
@@ -202,8 +98,8 @@ module Cosmos
|
|
202
98
|
@top_keywords.each do |keyword|
|
203
99
|
tf = Tempfile.new('unittest')
|
204
100
|
case keyword
|
205
|
-
when "
|
206
|
-
tf.puts '
|
101
|
+
when "SELECT_COMMAND"
|
102
|
+
tf.puts 'SELECT_COMMAND tgt1 pkt1 extra'
|
207
103
|
when "SELECT_TELEMETRY"
|
208
104
|
tf.puts 'SELECT_TELEMETRY tgt1 pkt1 extra'
|
209
105
|
when 'LIMITS_GROUP'
|
@@ -217,7 +113,7 @@ module Cosmos
|
|
217
113
|
end
|
218
114
|
|
219
115
|
@tlm_keywords.each do |keyword|
|
220
|
-
next if %w(
|
116
|
+
next if %w(PROCESSOR META).include? keyword
|
221
117
|
tf = Tempfile.new('unittest')
|
222
118
|
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
223
119
|
case keyword
|
@@ -236,10 +132,6 @@ module Cosmos
|
|
236
132
|
when "SELECT_ITEM"
|
237
133
|
tf.puts 'ITEM myitem 0 8 UINT'
|
238
134
|
tf.puts 'SELECT_ITEM myitem extra'
|
239
|
-
when "MACRO_APPEND_START"
|
240
|
-
tf.puts 'MACRO_APPEND_START 0 1 "%s_%d" extra'
|
241
|
-
when "ACRO_APPEND_END"
|
242
|
-
tf.puts 'MACRO_APPEND_END extra'
|
243
135
|
end
|
244
136
|
tf.close
|
245
137
|
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /Too many parameters for #{keyword}/)
|
@@ -271,47 +163,6 @@ module Cosmos
|
|
271
163
|
end
|
272
164
|
end
|
273
165
|
|
274
|
-
context "with COMMAND or TELEMETRY" do
|
275
|
-
it "should complain about invalid endianness" do
|
276
|
-
%w(COMMAND TELEMETRY).each do |keyword|
|
277
|
-
tf = Tempfile.new('unittest')
|
278
|
-
tf.puts keyword + ' tgt1 pkt1 MIDDLE_ENDIAN "Packet"'
|
279
|
-
tf.close
|
280
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid endianness MIDDLE_ENDIAN. Must be BIG_ENDIAN or LITTLE_ENDIAN.")
|
281
|
-
tf.unlink
|
282
|
-
end
|
283
|
-
end
|
284
|
-
|
285
|
-
it "should process target, packet, endianness, description" do
|
286
|
-
%w(COMMAND TELEMETRY).each do |keyword|
|
287
|
-
tf = Tempfile.new('unittest')
|
288
|
-
tf.puts keyword + ' tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
289
|
-
tf.close
|
290
|
-
@pc.process_file(tf.path, "TGT1")
|
291
|
-
pkt = @pc.commands["TGT1"]["PKT1"] if keyword == 'COMMAND'
|
292
|
-
pkt = @pc.telemetry["TGT1"]["PKT1"] if keyword == 'TELEMETRY'
|
293
|
-
pkt.target_name.should eql "TGT1"
|
294
|
-
pkt.packet_name.should eql "PKT1"
|
295
|
-
pkt.default_endianness.should eql :LITTLE_ENDIAN
|
296
|
-
pkt.description.should eql "Packet"
|
297
|
-
tf.unlink
|
298
|
-
end
|
299
|
-
end
|
300
|
-
|
301
|
-
it "should substitute the target name" do
|
302
|
-
%w(COMMAND TELEMETRY).each do |keyword|
|
303
|
-
tf = Tempfile.new('unittest')
|
304
|
-
tf.puts keyword + ' tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
305
|
-
tf.close
|
306
|
-
@pc.process_file(tf.path, "NEW")
|
307
|
-
pkt = @pc.commands["NEW"]["PKT1"] if keyword == 'COMMAND'
|
308
|
-
pkt = @pc.telemetry["NEW"]["PKT1"] if keyword == 'TELEMETRY'
|
309
|
-
pkt.target_name.should eql "NEW"
|
310
|
-
tf.unlink
|
311
|
-
end
|
312
|
-
end
|
313
|
-
end
|
314
|
-
|
315
166
|
context "with SELECT_COMMAND or SELECT_TELEMETRY" do
|
316
167
|
it "should complain if the packet is not found" do
|
317
168
|
%w(SELECT_COMMAND SELECT_TELEMETRY).each do |keyword|
|
@@ -442,176 +293,21 @@ module Cosmos
|
|
442
293
|
end
|
443
294
|
end
|
444
295
|
|
445
|
-
context "with
|
446
|
-
it "
|
447
|
-
tf = Tempfile.new('unittest')
|
448
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
449
|
-
tf.puts ' ITEM ITEM1 8 0 DERIVED'
|
450
|
-
tf.close
|
451
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /DERIVED items must have bit_offset of zero/)
|
452
|
-
tf.unlink
|
453
|
-
|
454
|
-
tf = Tempfile.new('unittest')
|
455
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
456
|
-
tf.puts ' ITEM ITEM1 0 8 DERIVED'
|
457
|
-
tf.close
|
458
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /DERIVED items must have bit_size of zero/)
|
459
|
-
tf.unlink
|
460
|
-
|
296
|
+
context "with MACRO_APPEND" do
|
297
|
+
it "creates a range of items" do
|
461
298
|
tf = Tempfile.new('unittest')
|
462
299
|
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
463
|
-
tf.puts '
|
464
|
-
tf.
|
465
|
-
|
466
|
-
@pc.telemetry["TGT1"]["PKT1"].items.keys.should include('ITEM1')
|
467
|
-
tf.unlink
|
468
|
-
end
|
469
|
-
|
470
|
-
it "should accept types INT UINT FLOAT STRING BLOCK" do
|
471
|
-
tf = Tempfile.new('unittest')
|
472
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
473
|
-
tf.puts ' ID_ITEM ITEM1 0 32 INT 0'
|
474
|
-
tf.puts ' ITEM ITEM2 0 32 UINT'
|
475
|
-
tf.puts ' ARRAY_ITEM ITEM3 0 32 FLOAT 64'
|
476
|
-
tf.puts ' APPEND_ID_ITEM ITEM4 32 STRING "ABCD"'
|
477
|
-
tf.puts ' APPEND_ITEM ITEM5 32 BLOCK'
|
478
|
-
tf.puts ' APPEND_ARRAY_ITEM ITEM6 32 BLOCK 64'
|
479
|
-
tf.close
|
480
|
-
@pc.process_file(tf.path, "TGT1")
|
481
|
-
@pc.telemetry["TGT1"]["PKT1"].items.keys.should include('ITEM1','ITEM2','ITEM3','ITEM4','ITEM5','ITEM6')
|
482
|
-
id_items = []
|
483
|
-
id_items << @pc.telemetry["TGT1"]["PKT1"].items["ITEM1"]
|
484
|
-
id_items << @pc.telemetry["TGT1"]["PKT1"].items["ITEM4"]
|
485
|
-
@pc.telemetry["TGT1"]["PKT1"].id_items.should eql id_items
|
486
|
-
tf.unlink
|
487
|
-
end
|
488
|
-
|
489
|
-
it "should support arbitrary endianness per item" do
|
490
|
-
tf = Tempfile.new('unittest')
|
491
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
492
|
-
tf.puts ' ID_ITEM ITEM1 0 32 UINT 0 "" LITTLE_ENDIAN'
|
493
|
-
tf.puts ' ITEM ITEM2 0 32 UINT "" LITTLE_ENDIAN'
|
494
|
-
tf.puts ' ARRAY_ITEM ITEM3 0 32 UINT 64 "" LITTLE_ENDIAN'
|
495
|
-
tf.puts ' APPEND_ID_ITEM ITEM4 32 UINT 1 "" LITTLE_ENDIAN'
|
496
|
-
tf.puts ' APPEND_ITEM ITEM5 32 UINT "" LITTLE_ENDIAN'
|
497
|
-
tf.puts ' APPEND_ARRAY_ITEM ITEM6 32 UINT 64 "" LITTLE_ENDIAN'
|
498
|
-
tf.puts ' ID_ITEM ITEM10 224 32 UINT 0 "" BIG_ENDIAN'
|
499
|
-
tf.puts ' ITEM ITEM20 256 32 UINT "" BIG_ENDIAN'
|
500
|
-
tf.puts ' ARRAY_ITEM ITEM30 0 32 UINT 64 "" BIG_ENDIAN'
|
501
|
-
tf.puts ' APPEND_ID_ITEM ITEM40 32 UINT 1 "" BIG_ENDIAN'
|
502
|
-
tf.puts ' APPEND_ITEM ITEM50 32 UINT "" BIG_ENDIAN'
|
503
|
-
tf.puts ' APPEND_ARRAY_ITEM ITEM60 32 UINT 64 "" BIG_ENDIAN'
|
504
|
-
tf.close
|
505
|
-
@pc.process_file(tf.path, "TGT1")
|
506
|
-
packet = @pc.telemetry["TGT1"]["PKT1"]
|
507
|
-
packet.buffer = "\x00\x00\x00\x01" * 16
|
508
|
-
packet.read("ITEM1").should eql 0x01000000
|
509
|
-
packet.read("ITEM2").should eql 0x01000000
|
510
|
-
packet.read("ITEM3").should eql [0x01000000, 0x01000000]
|
511
|
-
packet.read("ITEM4").should eql 0x01000000
|
512
|
-
packet.read("ITEM5").should eql 0x01000000
|
513
|
-
packet.read("ITEM6").should eql [0x01000000, 0x01000000]
|
514
|
-
packet.read("ITEM10").should eql 0x00000001
|
515
|
-
packet.read("ITEM20").should eql 0x00000001
|
516
|
-
packet.read("ITEM30").should eql [0x00000001, 0x00000001]
|
517
|
-
packet.read("ITEM40").should eql 0x00000001
|
518
|
-
packet.read("ITEM50").should eql 0x00000001
|
519
|
-
packet.read("ITEM60").should eql [0x00000001, 0x00000001]
|
520
|
-
tf.unlink
|
521
|
-
end
|
522
|
-
end
|
523
|
-
|
524
|
-
context "with keywords including PARAMETER" do
|
525
|
-
it "should only allow DERIVED items with offset 0 and size 0" do
|
526
|
-
tf = Tempfile.new('unittest')
|
527
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
528
|
-
tf.puts ' PARAMETER ITEM1 8 0 DERIVED 0 0 0'
|
529
|
-
tf.close
|
530
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /DERIVED items must have bit_offset of zero/)
|
531
|
-
tf.unlink
|
532
|
-
|
533
|
-
tf = Tempfile.new('unittest')
|
534
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
535
|
-
tf.puts ' PARAMETER ITEM1 0 8 DERIVED 0 0 0'
|
536
|
-
tf.close
|
537
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /DERIVED items must have bit_size of zero/)
|
538
|
-
tf.unlink
|
539
|
-
|
540
|
-
tf = Tempfile.new('unittest')
|
541
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
542
|
-
tf.puts ' PARAMETER ITEM1 0 0 DERIVED 0 0 0'
|
543
|
-
tf.close
|
544
|
-
@pc.process_file(tf.path, "TGT1")
|
545
|
-
@pc.commands["TGT1"]["PKT1"].items.keys.should include('ITEM1')
|
546
|
-
tf.unlink
|
547
|
-
end
|
548
|
-
|
549
|
-
it "should not allow ID_PARAMETER with DERIVED type" do
|
550
|
-
tf = Tempfile.new('unittest')
|
551
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
552
|
-
tf.puts ' ID_PARAMETER ITEM1 0 0 DERIVED 0 0 0'
|
553
|
-
tf.close
|
554
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /DERIVED data type not allowed/)
|
555
|
-
tf.unlink
|
556
|
-
end
|
557
|
-
|
558
|
-
it "should not allow APPEND_ID_PARAMETER with DERIVED type" do
|
559
|
-
tf = Tempfile.new('unittest')
|
560
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
561
|
-
tf.puts ' APPEND_ID_PARAMETER ITEM1 0 DERIVED 0 0 0'
|
562
|
-
tf.close
|
563
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /DERIVED data type not allowed/)
|
564
|
-
tf.unlink
|
565
|
-
end
|
566
|
-
|
567
|
-
it "should accept types INT UINT FLOAT STRING BLOCK" do
|
568
|
-
tf = Tempfile.new('unittest')
|
569
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
570
|
-
tf.puts ' ID_PARAMETER ITEM1 0 32 INT 0 0 0'
|
571
|
-
tf.puts ' ID_PARAMETER ITEM2 32 32 STRING "ABCD"'
|
572
|
-
tf.puts ' PARAMETER ITEM3 64 32 UINT 0 0 0'
|
573
|
-
tf.puts ' ARRAY_PARAMETER ITEM4 96 32 FLOAT 64'
|
574
|
-
tf.puts ' APPEND_ID_PARAMETER ITEM5 32 UINT 0 0 0'
|
575
|
-
tf.puts ' APPEND_ID_PARAMETER ITEM6 32 STRING "ABCD"'
|
576
|
-
tf.puts ' APPEND_PARAMETER ITEM7 32 BLOCK "1234"'
|
577
|
-
tf.puts ' APPEND_ARRAY_PARAMETER ITEM8 32 BLOCK 64'
|
578
|
-
tf.close
|
579
|
-
@pc.process_file(tf.path, "TGT1")
|
580
|
-
@pc.commands["TGT1"]["PKT1"].items.keys.should include('ITEM1','ITEM2','ITEM3','ITEM4','ITEM5','ITEM6','ITEM7','ITEM8')
|
581
|
-
tf.unlink
|
582
|
-
end
|
583
|
-
|
584
|
-
it "should support arbitrary endianness per item" do
|
585
|
-
tf = Tempfile.new('unittest')
|
586
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
587
|
-
tf.puts ' ID_PARAMETER ITEM1 0 32 UINT 0 0 0 "" LITTLE_ENDIAN'
|
588
|
-
tf.puts ' PARAMETER ITEM2 0 32 UINT 0 0 0 "" LITTLE_ENDIAN'
|
589
|
-
tf.puts ' ARRAY_PARAMETER ITEM3 0 32 UINT 64 "" LITTLE_ENDIAN'
|
590
|
-
tf.puts ' APPEND_ID_PARAMETER ITEM4 32 UINT 0 0 0 "" LITTLE_ENDIAN'
|
591
|
-
tf.puts ' APPEND_PARAMETER ITEM5 32 UINT 0 0 0 "" LITTLE_ENDIAN'
|
592
|
-
tf.puts ' APPEND_ARRAY_PARAMETER ITEM6 32 UINT 64 "" LITTLE_ENDIAN'
|
593
|
-
tf.puts ' ID_PARAMETER ITEM10 224 32 UINT 0 0 0 "" BIG_ENDIAN'
|
594
|
-
tf.puts ' PARAMETER ITEM20 256 32 UINT 0 0 0 "" BIG_ENDIAN'
|
595
|
-
tf.puts ' ARRAY_PARAMETER ITEM30 0 32 UINT 64 "" BIG_ENDIAN'
|
596
|
-
tf.puts ' APPEND_ID_PARAMETER ITEM40 32 UINT 0 0 0 "" BIG_ENDIAN'
|
597
|
-
tf.puts ' APPEND_PARAMETER ITEM50 32 UINT 0 0 0 "" BIG_ENDIAN'
|
598
|
-
tf.puts ' APPEND_ARRAY_PARAMETER ITEM60 32 UINT 64 "" BIG_ENDIAN'
|
300
|
+
tf.puts 'MACRO_APPEND_START 1 3'
|
301
|
+
tf.puts ' APPEND_ITEM BYTE 8 UINT "Setting #x"'
|
302
|
+
tf.puts 'MACRO_APPEND_END'
|
599
303
|
tf.close
|
600
304
|
@pc.process_file(tf.path, "TGT1")
|
601
|
-
|
602
|
-
|
603
|
-
|
604
|
-
|
605
|
-
|
606
|
-
|
607
|
-
packet.read("ITEM5").should eql 0x01000000
|
608
|
-
packet.read("ITEM6").should eql [0x01000000, 0x01000000]
|
609
|
-
packet.read("ITEM10").should eql 0x00000001
|
610
|
-
packet.read("ITEM20").should eql 0x00000001
|
611
|
-
packet.read("ITEM30").should eql [0x00000001, 0x00000001]
|
612
|
-
packet.read("ITEM40").should eql 0x00000001
|
613
|
-
packet.read("ITEM50").should eql 0x00000001
|
614
|
-
packet.read("ITEM60").should eql [0x00000001, 0x00000001]
|
305
|
+
pkt = @pc.telemetry["TGT1"]["PKT1"]
|
306
|
+
expect(pkt.items.length).to eql 6 # 3 plus the RECEIVED_XXX items
|
307
|
+
expect(pkt.items.keys).to include('BYTE1','BYTE2','BYTE3')
|
308
|
+
expect(pkt.sorted_items[3].name).to eql 'BYTE1'
|
309
|
+
expect(pkt.sorted_items[4].name).to eql 'BYTE2'
|
310
|
+
expect(pkt.sorted_items[5].name).to eql 'BYTE3'
|
615
311
|
tf.unlink
|
616
312
|
end
|
617
313
|
end
|
@@ -651,56 +347,6 @@ module Cosmos
|
|
651
347
|
end
|
652
348
|
end
|
653
349
|
|
654
|
-
context "with MACRO_APPEND_START" do
|
655
|
-
it "should add items to the packet" do
|
656
|
-
tf = Tempfile.new('unittest')
|
657
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
658
|
-
tf.puts 'MACRO_APPEND_START 1 5'
|
659
|
-
tf.puts 'APPEND_ITEM BIT 16 UINT "Setting #x"'
|
660
|
-
tf.puts ' STATE BAD 0 RED'
|
661
|
-
tf.puts ' STATE GOOD 1 GREEN'
|
662
|
-
tf.puts 'MACRO_APPEND_END'
|
663
|
-
tf.close
|
664
|
-
@pc.process_file(tf.path, "TGT1")
|
665
|
-
pkt = @pc.telemetry["TGT1"]["PKT1"]
|
666
|
-
pkt.items.keys.should include('BIT1','BIT2','BIT3','BIT4','BIT5')
|
667
|
-
limits_items = []
|
668
|
-
pkt.items.each do |name, item|
|
669
|
-
limits_items << item if name =~ /BIT/
|
670
|
-
end
|
671
|
-
pkt.limits_items.should eql limits_items
|
672
|
-
tf.unlink
|
673
|
-
end
|
674
|
-
|
675
|
-
it "should array items to the packet" do
|
676
|
-
tf = Tempfile.new('unittest')
|
677
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
678
|
-
tf.puts 'MACRO_APPEND_START 1 5'
|
679
|
-
tf.puts 'APPEND_ARRAY_ITEM BIT 16 INT 64 "Int Array Parameter"'
|
680
|
-
tf.puts 'MACRO_APPEND_END'
|
681
|
-
tf.close
|
682
|
-
@pc.process_file(tf.path, "TGT1")
|
683
|
-
pkt = @pc.telemetry["TGT1"]["PKT1"]
|
684
|
-
pkt.items.keys.should include('BIT1','BIT2','BIT3','BIT4','BIT5')
|
685
|
-
pkt.limits_items.should be_empty
|
686
|
-
tf.unlink
|
687
|
-
end
|
688
|
-
|
689
|
-
it "should work with printf format strings" do
|
690
|
-
tf = Tempfile.new('unittest')
|
691
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
692
|
-
tf.puts 'MACRO_APPEND_START 1 5 "%d%s"'
|
693
|
-
tf.puts 'APPEND_ID_ITEM BIT 16 UINT 0 "Setting #x"'
|
694
|
-
tf.puts 'MACRO_APPEND_END'
|
695
|
-
tf.close
|
696
|
-
@pc.process_file(tf.path, "TGT1")
|
697
|
-
pkt = @pc.telemetry["TGT1"]["PKT1"]
|
698
|
-
pkt.items.keys.should include('1BIT','2BIT','3BIT','4BIT','5BIT')
|
699
|
-
pkt.limits_items.should be_empty
|
700
|
-
tf.unlink
|
701
|
-
end
|
702
|
-
end
|
703
|
-
|
704
350
|
context "with ALLOW_SHORT" do
|
705
351
|
it "should mark the packet as allowing short buffers" do
|
706
352
|
tf = Tempfile.new('unittest')
|
@@ -806,106 +452,6 @@ module Cosmos
|
|
806
452
|
end
|
807
453
|
end
|
808
454
|
|
809
|
-
context "with STATE" do
|
810
|
-
it "should support STRING items" do
|
811
|
-
tf = Tempfile.new('unittest')
|
812
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
813
|
-
tf.puts ' APPEND_ITEM item1 128 STRING "state item"'
|
814
|
-
tf.puts ' STATE FALSE "FALSE STRING"'
|
815
|
-
tf.puts ' STATE TRUE "TRUE STRING"'
|
816
|
-
tf.close
|
817
|
-
@pc.process_file(tf.path, "TGT1")
|
818
|
-
@pc.telemetry["TGT1"]["PKT1"].write("ITEM1", "TRUE STRING")
|
819
|
-
@pc.telemetry["TGT1"]["PKT1"].read("ITEM1").should eql "TRUE"
|
820
|
-
@pc.telemetry["TGT1"]["PKT1"].write("ITEM1", "FALSE STRING")
|
821
|
-
@pc.telemetry["TGT1"]["PKT1"].read("ITEM1").should eql "FALSE"
|
822
|
-
tf.unlink
|
823
|
-
end
|
824
|
-
|
825
|
-
it "should warn about duplicate states and replace the duplicate" do
|
826
|
-
tf = Tempfile.new('unittest')
|
827
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
828
|
-
tf.puts ' APPEND_PARAMETER item1 8 UINT 0 2 0 "state item"'
|
829
|
-
tf.puts ' STATE FALSE 0'
|
830
|
-
tf.puts ' STATE TRUE 1'
|
831
|
-
tf.puts ' STATE FALSE 2'
|
832
|
-
tf.close
|
833
|
-
@pc.process_file(tf.path, "TGT1")
|
834
|
-
@pc.warnings.should include("Duplicate state defined on line 5: STATE FALSE 2")
|
835
|
-
@pc.commands["TGT1"]["PKT1"].buffer = "\x00"
|
836
|
-
@pc.commands["TGT1"]["PKT1"].read("ITEM1").should eql 0
|
837
|
-
@pc.commands["TGT1"]["PKT1"].buffer = "\x02"
|
838
|
-
@pc.commands["TGT1"]["PKT1"].read("ITEM1").should eql "FALSE"
|
839
|
-
tf.unlink
|
840
|
-
end
|
841
|
-
|
842
|
-
context "with telemetry" do
|
843
|
-
it "should only allow GREEN YELLOW or RED" do
|
844
|
-
tf = Tempfile.new('unittest')
|
845
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
846
|
-
tf.puts ' APPEND_ITEM item1 8 UINT "state item"'
|
847
|
-
tf.puts ' STATE WORST 1 ORANGE'
|
848
|
-
tf.close
|
849
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /Invalid state color ORANGE/)
|
850
|
-
tf.unlink
|
851
|
-
end
|
852
|
-
|
853
|
-
it "should record the state values and colors" do
|
854
|
-
tf = Tempfile.new('unittest')
|
855
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
856
|
-
tf.puts ' APPEND_ITEM item1 8 UINT "state item"'
|
857
|
-
tf.puts ' STATE STATE1 1 RED'
|
858
|
-
tf.puts ' STATE STATE2 2 YELLOW'
|
859
|
-
tf.puts ' STATE STATE3 3 GREEN'
|
860
|
-
tf.puts ' STATE STATE4 4'
|
861
|
-
tf.close
|
862
|
-
@pc.process_file(tf.path, "TGT1")
|
863
|
-
index = 1
|
864
|
-
colors = [:RED, :YELLOW, :GREEN]
|
865
|
-
@pc.telemetry["TGT1"]["PKT1"].items["ITEM1"].states.each do |name,val|
|
866
|
-
name.should eql "STATE#{index}"
|
867
|
-
val.should eql index
|
868
|
-
@pc.telemetry["TGT1"]["PKT1"].items["ITEM1"].state_colors[name].should eql colors[index - 1]
|
869
|
-
|
870
|
-
index += 1
|
871
|
-
end
|
872
|
-
@pc.telemetry["TGT1"]["PKT1"].limits_items.should eql [@pc.telemetry["TGT1"]["PKT1"].items["ITEM1"]]
|
873
|
-
tf.unlink
|
874
|
-
end
|
875
|
-
end
|
876
|
-
|
877
|
-
context "with command" do
|
878
|
-
it "should only allow HAZARDOUS as the third param" do
|
879
|
-
tf = Tempfile.new('unittest')
|
880
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
881
|
-
tf.puts ' APPEND_PARAMETER item1 8 UINT 0 0 0'
|
882
|
-
tf.puts ' STATE WORST 0 RED'
|
883
|
-
tf.close
|
884
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /HAZARDOUS expected as third parameter/)
|
885
|
-
tf.unlink
|
886
|
-
end
|
887
|
-
|
888
|
-
it "should take HAZARDOUS and an optional description" do
|
889
|
-
tf = Tempfile.new('unittest')
|
890
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Description"'
|
891
|
-
tf.puts ' APPEND_PARAMETER item1 8 UINT 1 3 1'
|
892
|
-
tf.puts ' STATE GOOD 1'
|
893
|
-
tf.puts ' STATE BAD 2 HAZARDOUS'
|
894
|
-
tf.puts ' STATE WORST 3 HAZARDOUS "Hazardous description"'
|
895
|
-
tf.close
|
896
|
-
@pc.process_file(tf.path, "TGT1")
|
897
|
-
@pc.commands["TGT1"]["PKT1"].buffer = "\x01"
|
898
|
-
@pc.commands["TGT1"]["PKT1"].check_limits
|
899
|
-
@pc.commands["TGT1"]["PKT1"].items["ITEM1"].hazardous["GOOD"].should be_nil
|
900
|
-
@pc.commands["TGT1"]["PKT1"].items["ITEM1"].hazardous["BAD"].should_not be_nil
|
901
|
-
@pc.commands["TGT1"]["PKT1"].items["ITEM1"].hazardous["WORST"].should_not be_nil
|
902
|
-
@pc.commands["TGT1"]["PKT1"].items["ITEM1"].hazardous["WORST"].should eql "Hazardous description"
|
903
|
-
@pc.commands["TGT1"]["PKT1"].limits_items.should be_empty
|
904
|
-
tf.unlink
|
905
|
-
end
|
906
|
-
end
|
907
|
-
end
|
908
|
-
|
909
455
|
context "with READ_CONVERSION and WRITE_CONVERSION" do
|
910
456
|
it "should complain about missing conversion file" do
|
911
457
|
filename = File.join(File.dirname(__FILE__), "../test_only.rb")
|
@@ -993,76 +539,6 @@ module Cosmos
|
|
993
539
|
end
|
994
540
|
end
|
995
541
|
|
996
|
-
context "with PROCESSOR" do
|
997
|
-
it "should complain about missing processor file" do
|
998
|
-
filename = File.join(File.dirname(__FILE__), "../test_only.rb")
|
999
|
-
File.delete(filename) if File.exist?(filename)
|
1000
|
-
@pc = PacketConfig.new
|
1001
|
-
|
1002
|
-
tf = Tempfile.new('unittest')
|
1003
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1004
|
-
tf.puts ' PROCESSOR TEST test_only.rb'
|
1005
|
-
tf.close
|
1006
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /TestOnly class not found/)
|
1007
|
-
tf.unlink
|
1008
|
-
end
|
1009
|
-
|
1010
|
-
it "should complain about a non Cosmos::Processor class" do
|
1011
|
-
filename = File.join(File.dirname(__FILE__), "../processor1.rb")
|
1012
|
-
File.open(filename, 'w') do |file|
|
1013
|
-
file.puts "class Processor1"
|
1014
|
-
file.puts " def call(packet,buffer)"
|
1015
|
-
file.puts " end"
|
1016
|
-
file.puts "end"
|
1017
|
-
end
|
1018
|
-
load 'processor1.rb'
|
1019
|
-
File.delete(filename) if File.exist?(filename)
|
1020
|
-
|
1021
|
-
tf = Tempfile.new('unittest')
|
1022
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1023
|
-
tf.puts ' PROCESSOR P1 processor1.rb'
|
1024
|
-
tf.close
|
1025
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /processor must be a Cosmos::Processor but is a Processor1/)
|
1026
|
-
tf.unlink
|
1027
|
-
end
|
1028
|
-
|
1029
|
-
it "should parse the processor" do
|
1030
|
-
filename = File.join(File.dirname(__FILE__), "../processor2.rb")
|
1031
|
-
File.open(filename, 'w') do |file|
|
1032
|
-
file.puts "require 'cosmos/processors/processor'"
|
1033
|
-
file.puts "class Processor2 < Cosmos::Processor"
|
1034
|
-
file.puts " def call(packet,buffer)"
|
1035
|
-
file.puts " @results[:TEST] = 5"
|
1036
|
-
file.puts " end"
|
1037
|
-
file.puts "end"
|
1038
|
-
end
|
1039
|
-
load 'processor2.rb'
|
1040
|
-
|
1041
|
-
tf = Tempfile.new('unittest')
|
1042
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1043
|
-
tf.puts ' ITEM item1 0 16 INT "Integer Item"'
|
1044
|
-
tf.puts ' READ_CONVERSION processor_conversion.rb P2 TEST'
|
1045
|
-
tf.puts ' PROCESSOR P2 processor2.rb'
|
1046
|
-
tf.puts ' PROCESSOR P3 processor2.rb RAW'
|
1047
|
-
tf.close
|
1048
|
-
@pc.process_file(tf.path, "TGT1")
|
1049
|
-
@pc.telemetry["TGT1"]["PKT1"].buffer = "\x01\x01"
|
1050
|
-
@pc.telemetry["TGT1"]["PKT1"].read("ITEM1").should eql 5
|
1051
|
-
tf.unlink
|
1052
|
-
|
1053
|
-
File.delete(filename) if File.exist?(filename)
|
1054
|
-
end
|
1055
|
-
|
1056
|
-
it "should complain if applied to a command packet" do
|
1057
|
-
tf = Tempfile.new('unittest')
|
1058
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1059
|
-
tf.puts ' PROCESSOR P1 processor1.rb'
|
1060
|
-
tf.close
|
1061
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "PROCESSOR only applies to telemetry packets")
|
1062
|
-
tf.unlink
|
1063
|
-
end
|
1064
|
-
end
|
1065
|
-
|
1066
542
|
context "with POLY_READ_CONVERSION and POLY_WRITE_CONVERSION" do
|
1067
543
|
it "should perform a polynomial conversion" do
|
1068
544
|
tf = Tempfile.new('unittest')
|
@@ -1163,313 +639,22 @@ module Cosmos
|
|
1163
639
|
end
|
1164
640
|
|
1165
641
|
context "with LIMITS" do
|
1166
|
-
it "
|
1167
|
-
tf = Tempfile.new('unittest')
|
1168
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1169
|
-
tf.puts ' APPEND_PARAMETER item1 16 UINT 0 0 0 "Item"'
|
1170
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 2 6 7 3 5'
|
1171
|
-
tf.close
|
1172
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "LIMITS only applies to telemetry items")
|
1173
|
-
tf.unlink
|
1174
|
-
end
|
1175
|
-
|
1176
|
-
it "should complain if the second parameter isn't a number" do
|
1177
|
-
tf = Tempfile.new('unittest')
|
1178
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1179
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1180
|
-
tf.puts ' LIMITS DEFAULT TRUE ENABLED 1 2 6 7 3 5'
|
1181
|
-
tf.close
|
1182
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /Ensure persistence is an integer/)
|
1183
|
-
tf.unlink
|
1184
|
-
end
|
1185
|
-
|
1186
|
-
it "should complain if the third parameter isn't ENABLED or DISABLED" do
|
1187
|
-
tf = Tempfile.new('unittest')
|
1188
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1189
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1190
|
-
tf.puts ' LIMITS DEFAULT 3 TRUE 1 2 6 7 3 5'
|
1191
|
-
tf.close
|
1192
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /Initial state must be ENABLED or DISABLED/)
|
1193
|
-
tf.unlink
|
1194
|
-
end
|
1195
|
-
|
1196
|
-
it "should complain if the 4 limits are out of order" do
|
1197
|
-
tf = Tempfile.new('unittest')
|
1198
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1199
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1200
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 2 1 3 4'
|
1201
|
-
tf.close
|
1202
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid limits specified. Ensure yellow limits are within red limits.")
|
1203
|
-
tf.unlink
|
1204
|
-
|
1205
|
-
tf = Tempfile.new('unittest')
|
1206
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1207
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1208
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 5 3 7'
|
1209
|
-
tf.close
|
1210
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid limits specified. Ensure yellow limits are within red limits.")
|
1211
|
-
tf.unlink
|
1212
|
-
|
1213
|
-
tf = Tempfile.new('unittest')
|
1214
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1215
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1216
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 2 5 4'
|
1217
|
-
tf.close
|
1218
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid limits specified. Ensure yellow limits are within red limits.")
|
1219
|
-
tf.unlink
|
1220
|
-
|
1221
|
-
tf = Tempfile.new('unittest')
|
1222
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1223
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1224
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 2 3 0'
|
1225
|
-
tf.close
|
1226
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid limits specified. Ensure yellow limits are within red limits.")
|
1227
|
-
tf.unlink
|
1228
|
-
end
|
1229
|
-
|
1230
|
-
it "should complain if the 6 limits are out of order" do
|
1231
|
-
tf = Tempfile.new('unittest')
|
1232
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1233
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1234
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 2 6 7 0 5'
|
1235
|
-
tf.close
|
1236
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid limits specified. Ensure green limits are within yellow limits.")
|
1237
|
-
tf.unlink
|
1238
|
-
|
1239
|
-
tf = Tempfile.new('unittest')
|
1240
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1241
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1242
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 3 6 7 2 5'
|
1243
|
-
tf.close
|
1244
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid limits specified. Ensure green limits are within yellow limits.")
|
1245
|
-
tf.unlink
|
1246
|
-
|
1247
|
-
tf = Tempfile.new('unittest')
|
1248
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1249
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1250
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 2 6 8 3 7'
|
1251
|
-
tf.close
|
1252
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid limits specified. Ensure green limits are within yellow limits.")
|
1253
|
-
tf.unlink
|
1254
|
-
|
1255
|
-
tf = Tempfile.new('unittest')
|
1256
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1257
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1258
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 2 6 8 3 9'
|
1259
|
-
tf.close
|
1260
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid limits specified. Ensure green limits are within yellow limits.")
|
1261
|
-
tf.unlink
|
1262
|
-
|
1263
|
-
tf = Tempfile.new('unittest')
|
1264
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1265
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1266
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 2 6 8 4 3'
|
1267
|
-
tf.close
|
1268
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid limits specified. Ensure green limits are within yellow limits.")
|
1269
|
-
tf.unlink
|
1270
|
-
end
|
1271
|
-
|
1272
|
-
it "should take 4 limits values" do
|
642
|
+
it "ensures limits sets have unique names" do
|
1273
643
|
tf = Tempfile.new('unittest')
|
1274
644
|
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1275
645
|
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1276
646
|
tf.puts ' LIMITS DEFAULT 1 ENABLED 1 2 6 7'
|
647
|
+
tf.puts ' LIMITS TVAC 1 ENABLED 1 2 6 7'
|
648
|
+
tf.puts ' LIMITS DEFAULT 1 ENABLED 8 9 12 13'
|
1277
649
|
tf.close
|
1278
650
|
@pc.process_file(tf.path, "TGT1")
|
1279
651
|
item = @pc.telemetry["TGT1"]["PKT1"].items["ITEM1"]
|
1280
|
-
item.limits.values
|
1281
|
-
|
1282
|
-
@pc.telemetry["TGT1"]["PKT1"].enable_limits("ITEM1")
|
1283
|
-
@pc.telemetry["TGT1"]["PKT1"].check_limits
|
1284
|
-
item.limits.state.should eql :GREEN
|
1285
|
-
@pc.telemetry["TGT1"]["PKT1"].limits_items.should eql [item]
|
1286
|
-
tf.unlink
|
1287
|
-
end
|
1288
|
-
|
1289
|
-
it "should take 6 limits values" do
|
1290
|
-
tf = Tempfile.new('unittest')
|
1291
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1292
|
-
tf.puts ' APPEND_ITEM item1 16 UINT "Item"'
|
1293
|
-
tf.puts ' LIMITS DEFAULT 1 ENABLED 1 2 6 7 3 5'
|
1294
|
-
tf.close
|
1295
|
-
@pc.process_file(tf.path, "TGT1")
|
1296
|
-
item = @pc.telemetry["TGT1"]["PKT1"].items["ITEM1"]
|
1297
|
-
item.limits.values[:DEFAULT].should_not be_nil
|
652
|
+
expect(item.limits.values.length).to eql 2
|
653
|
+
# Verify the last defined DEFAULT limits wins
|
1298
654
|
@pc.telemetry["TGT1"]["PKT1"].buffer = "\x04"
|
1299
655
|
@pc.telemetry["TGT1"]["PKT1"].enable_limits("ITEM1")
|
1300
656
|
@pc.telemetry["TGT1"]["PKT1"].check_limits
|
1301
|
-
item.limits.state.should eql :
|
1302
|
-
@pc.telemetry["TGT1"]["PKT1"].limits_items.should eql [item]
|
1303
|
-
tf.unlink
|
1304
|
-
end
|
1305
|
-
end
|
1306
|
-
|
1307
|
-
context "with LIMITS_RESPONSE" do
|
1308
|
-
it "should complain if applied to a command PARAMETER" do
|
1309
|
-
tf = Tempfile.new('unittest')
|
1310
|
-
tf.puts 'COMMAND tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1311
|
-
tf.puts ' APPEND_PARAMETER item1 16 UINT 0 0 0 "Item"'
|
1312
|
-
tf.puts ' LIMITS_RESPONSE test.rb'
|
1313
|
-
tf.close
|
1314
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "LIMITS_RESPONSE only applies to telemetry items")
|
1315
|
-
tf.unlink
|
1316
|
-
end
|
1317
|
-
|
1318
|
-
it "should complain about missing response file" do
|
1319
|
-
filename = File.join(File.dirname(__FILE__), "../test_only.rb")
|
1320
|
-
File.delete(filename) if File.exist?(filename)
|
1321
|
-
@pc = PacketConfig.new
|
1322
|
-
|
1323
|
-
tf = Tempfile.new('unittest')
|
1324
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1325
|
-
tf.puts ' ITEM item1 0 16 INT "Integer Item"'
|
1326
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 2 6 7 3 5'
|
1327
|
-
tf.puts ' LIMITS_RESPONSE test_only.rb'
|
1328
|
-
tf.close
|
1329
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /TestOnly class not found/)
|
1330
|
-
tf.unlink
|
1331
|
-
end
|
1332
|
-
|
1333
|
-
it "should complain about a non Cosmos::LimitsResponse class" do
|
1334
|
-
filename = File.join(File.dirname(__FILE__), "../limits_response1.rb")
|
1335
|
-
File.open(filename, 'w') do |file|
|
1336
|
-
file.puts "class LimitsResponse1"
|
1337
|
-
file.puts " def call(target_name, packet_name, item, old_limits_state, new_limits_state)"
|
1338
|
-
file.puts " end"
|
1339
|
-
file.puts "end"
|
1340
|
-
end
|
1341
|
-
load 'limits_response1.rb'
|
1342
|
-
File.delete(filename) if File.exist?(filename)
|
1343
|
-
|
1344
|
-
tf = Tempfile.new('unittest')
|
1345
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1346
|
-
tf.puts ' ITEM item1 0 16 INT "Integer Item"'
|
1347
|
-
tf.puts ' LIMITS DEFAULT 3 ENABLED 1 2 6 7 3 5'
|
1348
|
-
tf.puts ' LIMITS_RESPONSE limits_response1.rb'
|
1349
|
-
tf.close
|
1350
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, /response must be a Cosmos::LimitsResponse but is a LimitsResponse1/)
|
1351
|
-
tf.unlink
|
1352
|
-
end
|
1353
|
-
|
1354
|
-
it "should set the response" do
|
1355
|
-
filename = File.join(File.dirname(__FILE__), "../limits_response2.rb")
|
1356
|
-
File.open(filename, 'w') do |file|
|
1357
|
-
file.puts "require 'cosmos/packets/limits_response'"
|
1358
|
-
file.puts "class LimitsResponse2 < Cosmos::LimitsResponse"
|
1359
|
-
file.puts " def call(target_name, packet_name, item, old_limits_state, new_limits_state)"
|
1360
|
-
file.puts " puts \"\#{target_name} \#{packet_name} \#{item.name} \#{old_limits_state} \#{new_limits_state}\""
|
1361
|
-
file.puts " end"
|
1362
|
-
file.puts "end"
|
1363
|
-
end
|
1364
|
-
load 'limits_response2.rb'
|
1365
|
-
|
1366
|
-
tf = Tempfile.new('unittest')
|
1367
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1368
|
-
tf.puts ' ITEM item1 0 16 INT "Integer Item"'
|
1369
|
-
tf.puts ' LIMITS DEFAULT 1 ENABLED 1 2 6 7 3 5'
|
1370
|
-
tf.puts ' LIMITS_RESPONSE limits_response2.rb'
|
1371
|
-
tf.close
|
1372
|
-
@pc.process_file(tf.path, "TGT1")
|
1373
|
-
pkt = @pc.telemetry["TGT1"]["PKT1"]
|
1374
|
-
pkt.get_item("ITEM1").limits.response.class.should eql LimitsResponse2
|
1375
|
-
|
1376
|
-
File.delete(filename) if File.exist?(filename)
|
1377
|
-
tf.unlink
|
1378
|
-
end
|
1379
|
-
|
1380
|
-
it "should call the response with parameters" do
|
1381
|
-
filename = File.join(File.dirname(__FILE__), "../limits_response2.rb")
|
1382
|
-
File.open(filename, 'w') do |file|
|
1383
|
-
file.puts "require 'cosmos/packets/limits_response'"
|
1384
|
-
file.puts "class LimitsResponse2 < Cosmos::LimitsResponse"
|
1385
|
-
file.puts " def initialize(val)"
|
1386
|
-
file.puts " puts \"initialize: \#{val}\""
|
1387
|
-
file.puts " end"
|
1388
|
-
file.puts " def call(target_name, packet_name, item, old_limits_state, new_limits_state)"
|
1389
|
-
file.puts " puts \"\#{target_name} \#{packet_name} \#{item.name} \#{old_limits_state} \#{new_limits_state}\""
|
1390
|
-
file.puts " end"
|
1391
|
-
file.puts "end"
|
1392
|
-
end
|
1393
|
-
load 'limits_response2.rb'
|
1394
|
-
|
1395
|
-
tf = Tempfile.new('unittest')
|
1396
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1397
|
-
tf.puts ' ITEM item1 0 16 INT "Integer Item"'
|
1398
|
-
tf.puts ' LIMITS DEFAULT 1 ENABLED 1 2 6 7 3 5'
|
1399
|
-
tf.puts ' LIMITS_RESPONSE limits_response2.rb 2'
|
1400
|
-
tf.close
|
1401
|
-
capture_io do |stdout|
|
1402
|
-
@pc.process_file(tf.path, "TGT1")
|
1403
|
-
stdout.string.should eql "initialize: 2\n"
|
1404
|
-
end
|
1405
|
-
|
1406
|
-
File.delete(filename) if File.exist?(filename)
|
1407
|
-
tf.unlink
|
1408
|
-
end
|
1409
|
-
end
|
1410
|
-
|
1411
|
-
context "with FORMAT_STRING" do
|
1412
|
-
it "should complain about invalid format strings" do
|
1413
|
-
tf = Tempfile.new('unittest')
|
1414
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1415
|
-
tf.puts ' ITEM item1 0 8 INT'
|
1416
|
-
tf.puts ' FORMAT_STRING "%*s"'
|
1417
|
-
tf.close
|
1418
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid FORMAT_STRING specified for type INT: %*s")
|
1419
|
-
tf.unlink
|
1420
|
-
|
1421
|
-
tf = Tempfile.new('unittest')
|
1422
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1423
|
-
tf.puts ' ITEM item1 0 8 STRING'
|
1424
|
-
tf.puts ' FORMAT_STRING "%d"'
|
1425
|
-
tf.close
|
1426
|
-
expect { @pc.process_file(tf.path, "TGT1") }.to raise_error(ConfigParser::Error, "Invalid FORMAT_STRING specified for type STRING: %d")
|
1427
|
-
tf.unlink
|
1428
|
-
end
|
1429
|
-
|
1430
|
-
it "should format integers" do
|
1431
|
-
tf = Tempfile.new('unittest')
|
1432
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1433
|
-
tf.puts ' ITEM item1 0 8 INT'
|
1434
|
-
tf.puts ' FORMAT_STRING "d%d"'
|
1435
|
-
tf.puts ' ITEM item2 0 8 UINT'
|
1436
|
-
tf.puts ' FORMAT_STRING "u%u"'
|
1437
|
-
tf.puts ' ITEM item3 0 8 UINT'
|
1438
|
-
tf.puts ' FORMAT_STRING "0x%x"'
|
1439
|
-
tf.close
|
1440
|
-
@pc.process_file(tf.path, "TGT1")
|
1441
|
-
@pc.telemetry["TGT1"]["PKT1"].buffer = "\x0a\x0b\x0c"
|
1442
|
-
@pc.telemetry["TGT1"]["PKT1"].read("ITEM1",:FORMATTED).should eql "d10"
|
1443
|
-
@pc.telemetry["TGT1"]["PKT1"].read("ITEM2",:FORMATTED).should eql "u10"
|
1444
|
-
@pc.telemetry["TGT1"]["PKT1"].read("ITEM3",:FORMATTED).should eql "0xa"
|
1445
|
-
tf.unlink
|
1446
|
-
end
|
1447
|
-
|
1448
|
-
it "should format floats" do
|
1449
|
-
tf = Tempfile.new('unittest')
|
1450
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1451
|
-
tf.puts ' ITEM item1 0 32 FLOAT'
|
1452
|
-
tf.puts ' FORMAT_STRING "%3.3f"'
|
1453
|
-
tf.close
|
1454
|
-
@pc.process_file(tf.path, "TGT1")
|
1455
|
-
@pc.telemetry["TGT1"]["PKT1"].write("ITEM1",12345.12345)
|
1456
|
-
@pc.telemetry["TGT1"]["PKT1"].read("ITEM1",:FORMATTED).should eql "12345.123"
|
1457
|
-
tf.unlink
|
1458
|
-
end
|
1459
|
-
|
1460
|
-
it "should format strings and blocks" do
|
1461
|
-
tf = Tempfile.new('unittest')
|
1462
|
-
tf.puts 'TELEMETRY tgt1 pkt1 LITTLE_ENDIAN "Packet"'
|
1463
|
-
tf.puts ' ITEM item1 0 32 STRING'
|
1464
|
-
tf.puts ' FORMAT_STRING "String: %s"'
|
1465
|
-
tf.puts ' ITEM item2 0 32 BLOCK'
|
1466
|
-
tf.puts ' FORMAT_STRING "Block: %s"'
|
1467
|
-
tf.close
|
1468
|
-
@pc.process_file(tf.path, "TGT1")
|
1469
|
-
@pc.telemetry["TGT1"]["PKT1"].write("ITEM1","HI")
|
1470
|
-
@pc.telemetry["TGT1"]["PKT1"].read("ITEM1",:FORMATTED).should eql "String: HI"
|
1471
|
-
@pc.telemetry["TGT1"]["PKT1"].write("ITEM2","\x00\x01\x02\x03")
|
1472
|
-
@pc.telemetry["TGT1"]["PKT1"].read("ITEM2",:FORMATTED).should eql "Block: \x00\x01\x02\x03"
|
657
|
+
item.limits.state.should eql :RED_LOW
|
1473
658
|
tf.unlink
|
1474
659
|
end
|
1475
660
|
end
|