cosmos 3.8.0 → 3.8.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (46) hide show
  1. checksums.yaml +4 -4
  2. data/autohotkey/tools/packet_viewer.ahk +4 -0
  3. data/cosmos.gemspec +1 -1
  4. data/data/crc.txt +277 -277
  5. data/demo/Gemfile +2 -2
  6. data/demo/config/data/crc.txt +176 -176
  7. data/demo/config/targets/INST/cmd_tlm/_ccsds_cmd.txt +2 -2
  8. data/demo/config/targets/INST/cmd_tlm/inst_cmds.txt +4 -4
  9. data/demo/procedures/example_test.rb +4 -0
  10. data/install/Gemfile +1 -1
  11. data/install/config/data/crc.txt +112 -112
  12. data/lib/cosmos/config/config_parser.rb +35 -1
  13. data/lib/cosmos/core_ext/string.rb +21 -17
  14. data/lib/cosmos/core_ext/time.rb +6 -2
  15. data/lib/cosmos/gui/opengl/gl_viewer.rb +4 -4
  16. data/lib/cosmos/gui/opengl/stl_shape.rb +5 -1
  17. data/lib/cosmos/gui/qt.rb +0 -26
  18. data/lib/cosmos/io/io_multiplexer.rb +27 -45
  19. data/lib/cosmos/packets/packet.rb +64 -24
  20. data/lib/cosmos/packets/packet_config.rb +254 -54
  21. data/lib/cosmos/packets/packet_item.rb +39 -10
  22. data/lib/cosmos/packets/parsers/packet_item_parser.rb +7 -2
  23. data/lib/cosmos/script/commands.rb +5 -0
  24. data/lib/cosmos/script/scripting.rb +5 -5
  25. data/lib/cosmos/script/telemetry.rb +5 -0
  26. data/lib/cosmos/tools/cmd_tlm_server/api.rb +22 -0
  27. data/lib/cosmos/tools/limits_monitor/limits_monitor.rb +38 -10
  28. data/lib/cosmos/tools/packet_viewer/packet_viewer.rb +48 -9
  29. data/lib/cosmos/tools/test_runner/test_runner.rb +76 -14
  30. data/lib/cosmos/tools/tlm_viewer/widgets/linegraph_widget.rb +11 -2
  31. data/lib/cosmos/tools/tlm_viewer/widgets/timegraph_widget.rb +15 -12
  32. data/lib/cosmos/top_level.rb +29 -32
  33. data/lib/cosmos/version.rb +4 -4
  34. data/spec/config/config_parser_spec.rb +8 -15
  35. data/spec/core_ext/socket_spec.rb +2 -2
  36. data/spec/core_ext/string_spec.rb +10 -0
  37. data/spec/core_ext/time_spec.rb +12 -4
  38. data/spec/io/io_multiplexer_spec.rb +11 -3
  39. data/spec/packets/packet_spec.rb +30 -0
  40. data/spec/script/commands_spec.rb +2 -1
  41. data/spec/script/scripting_spec.rb +22 -0
  42. data/spec/script/telemetry_spec.rb +2 -1
  43. data/spec/spec_helper.rb +2 -2
  44. data/spec/tools/cmd_tlm_server/router_thread_spec.rb +2 -2
  45. data/spec/top_level/top_level_spec.rb +4 -2
  46. metadata +5 -5
@@ -19,53 +19,35 @@ module Cosmos
19
19
  @streams = []
20
20
  end
21
21
 
22
- # @param args [Array<String>] Argument to send to the print method of each
23
- # stream
24
- def print(*args)
25
- @streams.each {|stream| stream.print(*args)}
26
- nil
22
+ def write(*args)
23
+ first = true
24
+ result = nil
25
+ @streams.each do |stream|
26
+ if first
27
+ result = stream.write(*args)
28
+ result = self if result == stream
29
+ first = false
30
+ else
31
+ stream.write(*args)
32
+ end
33
+ end
34
+ result
27
35
  end
28
36
 
29
- # @param args [Array<String>] Argument to send to the printf method of each
30
- # stream
31
- def printf(*args)
32
- @streams.each {|stream| stream.printf(*args)}
33
- nil
34
- end
35
-
36
- # @param object [Object] Argument to send to the putc method of each
37
- # stream
38
- def putc(object)
39
- @streams.each {|stream| stream.putc(object)}
40
- object
41
- end
42
-
43
- # @param args [Array<String>] Argument to send to the puts method of each
44
- # stream
45
- def puts(*args)
46
- @streams.each {|stream| stream.puts(*args)}
47
- nil
48
- end
49
-
50
- # Calls flush on each stream
51
- def flush
52
- @streams.each {|stream| stream.flush}
53
- end
54
-
55
- # @param string [String] Argument to send to the write method of each
56
- # stream
57
- # @return [Integer] The length of the string argument
58
- def write(string)
59
- @streams.each {|stream| stream.write(string)}
60
- string.length
61
- end
62
-
63
- # @param string [String] Argument to send to the write_nonblock method of each
64
- # stream
65
- # @return [Integer] The length of the string argument
66
- def write_nonblock(string)
67
- @streams.each {|stream| stream.write_nonblock(string)}
68
- string.length
37
+ # Forwards IO methods to all streams
38
+ def method_missing(method_name, *args)
39
+ first = true
40
+ result = nil
41
+ @streams.each do |stream|
42
+ if first
43
+ result = stream.send(method_name, *args)
44
+ result = self if result == stream
45
+ first = false
46
+ else
47
+ stream.send(method_name, *args)
48
+ end
49
+ end
50
+ result
69
51
  end
70
52
 
71
53
  # Removes STDOUT and STDERR from the array of streams
@@ -185,36 +185,59 @@ module Cosmos
185
185
  Logger.instance.warn(msg)
186
186
  warnings << msg
187
187
  end
188
- if item.array_size
189
- if item.array_size > 0
190
- expected_next_offset = item.bit_offset + item.array_size
191
- else
192
- expected_next_offset = item.array_size
193
- end
188
+ expected_next_offset = Packet.next_bit_offset(item)
189
+ previous_item = item
190
+ end
191
+ warnings
192
+ end
193
+
194
+ # Checks if the packet has any gaps or overlapped items
195
+ #
196
+ # @return [Boolean] true if the packet has no gaps or overlapped items
197
+ def packed?
198
+ expected_next_offset = nil
199
+ @sorted_items.each do |item|
200
+ if expected_next_offset and item.bit_offset != expected_next_offset
201
+ return false
202
+ end
203
+ expected_next_offset = Packet.next_bit_offset(item)
204
+ end
205
+ true
206
+ end
207
+
208
+ # Returns the bit offset of the next item after the current item if items are packed
209
+ #
210
+ # @param item [PacketItem] The item to calculate the next offset for
211
+ # @return [Integer] Bit Offset of Next Item if Packed
212
+ def self.next_bit_offset(item)
213
+ if item.array_size
214
+ if item.array_size > 0
215
+ next_offset = item.bit_offset + item.array_size
194
216
  else
195
- expected_next_offset = nil
196
- if item.bit_offset > 0
197
- # Handle little-endian bit fields
198
- byte_aligned = ((item.bit_offset % 8) == 0)
199
- if item.endianness == :LITTLE_ENDIAN and (item.data_type == :INT or item.data_type == :UINT) and !(byte_aligned and (item.bit_size == 8 or item.bit_size == 16 or item.bit_size == 32 or item.bit_size == 64))
200
- # Bit offset always refers to the most significant bit of a bitfield
201
- bits_remaining_in_last_byte = 8 - (item.bit_offset % 8)
202
- if item.bit_size > bits_remaining_in_last_byte
203
- expected_next_offset = item.bit_offset + bits_remaining_in_last_byte
204
- end
217
+ next_offset = item.array_size
218
+ end
219
+ else
220
+ next_offset = nil
221
+ if item.bit_offset > 0
222
+ # Handle little-endian bit fields
223
+ byte_aligned = ((item.bit_offset % 8) == 0)
224
+ if item.endianness == :LITTLE_ENDIAN and (item.data_type == :INT or item.data_type == :UINT) and !(byte_aligned and (item.bit_size == 8 or item.bit_size == 16 or item.bit_size == 32 or item.bit_size == 64))
225
+ # Bit offset always refers to the most significant bit of a bitfield
226
+ bits_remaining_in_last_byte = 8 - (item.bit_offset % 8)
227
+ if item.bit_size > bits_remaining_in_last_byte
228
+ next_offset = item.bit_offset + bits_remaining_in_last_byte
205
229
  end
206
230
  end
207
- unless expected_next_offset
208
- if item.bit_size > 0
209
- expected_next_offset = item.bit_offset + item.bit_size
210
- else
211
- expected_next_offset = item.bit_size
212
- end
231
+ end
232
+ unless next_offset
233
+ if item.bit_size > 0
234
+ next_offset = item.bit_offset + item.bit_size
235
+ else
236
+ next_offset = item.bit_size
213
237
  end
214
238
  end
215
- previous_item = item
216
239
  end
217
- warnings
240
+ next_offset
218
241
  end
219
242
 
220
243
  # Id items are used by the identify? method to determine if a raw buffer of
@@ -338,6 +361,15 @@ module Cosmos
338
361
  synchronize_allow_reads() do
339
362
  if @read_conversion_cache[item]
340
363
  value = @read_conversion_cache[item]
364
+
365
+ # Make sure cached value is not modified by anyone by creating
366
+ # a deep copy
367
+ if String === value
368
+ value = value.clone
369
+ elsif Array === value
370
+ value = Marshal.load(Marshal.dump(value))
371
+ end
372
+
341
373
  using_cached_value = true
342
374
  end
343
375
  end
@@ -355,6 +387,14 @@ module Cosmos
355
387
  synchronize_allow_reads() do
356
388
  @read_conversion_cache ||= {}
357
389
  @read_conversion_cache[item] = value
390
+
391
+ # Make sure cached value is not modified by anyone by creating
392
+ # a deep copy
393
+ if String === value
394
+ value = value.clone
395
+ elsif Array === value
396
+ value = Marshal.load(Marshal.dump(value))
397
+ end
358
398
  end
359
399
  end
360
400
  end
@@ -370,10 +370,51 @@ module Cosmos
370
370
  attrs = { :name => (packet_name + '_Base'), :abstract => "true" }
371
371
  xml['xtce'].SequenceContainer(attrs) do
372
372
  xml['xtce'].EntryList do
373
+ packed = packet.packed?
373
374
  packet.sorted_items.each do |item|
374
375
  next if item.data_type == :DERIVED
375
- # TODO: Handle explicit bit offset in packet and nonunique item names
376
- xml['xtce'].ParameterRefEntry(:parameterRef => item.name)
376
+ # TODO: Handle nonunique item names
377
+ if item.array_size
378
+ xml['xtce'].ArrayParameterRefEntry(:parameterRef => item.name) do
379
+ if !packed
380
+ if item.bit_offset >= 0
381
+ xml['xtce'].LocationInContainerInBits(:referenceLocation => 'containerStart') do
382
+ xml['xtce'].FixedValue(item.bit_offset)
383
+ end
384
+ else
385
+ xml['xtce'].LocationInContainerInBits(:referenceLocation => 'containerEnd') do
386
+ xml['xtce'].FixedValue(-item.bit_offset)
387
+ end
388
+ end
389
+ end
390
+ xml['xtce'].DimensionList do
391
+ xml['xtce'].Dimension do
392
+ xml['xtce'].StartingIndex do
393
+ xml['xtce'].FixedValue(0)
394
+ end
395
+ xml['xtce'].EndingIndex do
396
+ xml['xtce'].FixedValue((item.array_size / item.bit_size) - 1)
397
+ end
398
+ end
399
+ end
400
+ end
401
+ else
402
+ if packed
403
+ xml['xtce'].ParameterRefEntry(:parameterRef => item.name)
404
+ else
405
+ xml['xtce'].ParameterRefEntry(:parameterRef => item.name) do
406
+ if item.bit_offset >= 0
407
+ xml['xtce'].LocationInContainerInBits(:referenceLocation => 'containerStart') do
408
+ xml['xtce'].FixedValue(item.bit_offset)
409
+ end
410
+ else
411
+ xml['xtce'].LocationInContainerInBits(:referenceLocation => 'containerEnd') do
412
+ xml['xtce'].FixedValue(-item.bit_offset)
413
+ end
414
+ end
415
+ end
416
+ end
417
+ end
377
418
  end
378
419
  end
379
420
  end # Abstract SequenceContainer
@@ -417,9 +458,50 @@ module Cosmos
417
458
  end # ArgumentList
418
459
  xml['xtce'].CommandContainer(:name => "#{target_name}_#{packet_name}_CommandContainer") do
419
460
  xml['xtce'].EntryList do
461
+ packed = packet.packed?
420
462
  packet.sorted_items.each do |item|
421
463
  next if item.data_type == :DERIVED
422
- xml['xtce'].ArgumentRefEntry(:argumentRef => item.name)
464
+ if item.array_size
465
+ xml['xtce'].ArrayArgumentRefEntry(:parameterRef => item.name) do
466
+ if !packed
467
+ if item.bit_offset >= 0
468
+ xml['xtce'].LocationInContainerInBits(:referenceLocation => 'containerStart') do
469
+ xml['xtce'].FixedValue(item.bit_offset)
470
+ end
471
+ else
472
+ xml['xtce'].LocationInContainerInBits(:referenceLocation => 'containerEnd') do
473
+ xml['xtce'].FixedValue(-item.bit_offset)
474
+ end
475
+ end
476
+ end
477
+ xml['xtce'].DimensionList do
478
+ xml['xtce'].Dimension do
479
+ xml['xtce'].StartingIndex do
480
+ xml['xtce'].FixedValue(0)
481
+ end
482
+ xml['xtce'].EndingIndex do
483
+ xml['xtce'].FixedValue((item.array_size / item.bit_size) - 1)
484
+ end
485
+ end
486
+ end
487
+ end
488
+ else
489
+ if packed
490
+ xml['xtce'].ArgumentRefEntry(:argumentRef => item.name)
491
+ else
492
+ xml['xtce'].ArgumentRefEntry(:argumentRef => item.name) do
493
+ if item.bit_offset >= 0
494
+ xml['xtce'].LocationInContainerInBits(:referenceLocation => 'containerStart') do
495
+ xml['xtce'].FixedValue(item.bit_offset)
496
+ end
497
+ else
498
+ xml['xtce'].LocationInContainerInBits(:referenceLocation => 'containerEnd') do
499
+ xml['xtce'].FixedValue(-item.bit_offset)
500
+ end
501
+ end
502
+ end
503
+ end
504
+ end
423
505
  end
424
506
  end
425
507
  end
@@ -492,11 +574,6 @@ module Cosmos
492
574
  if XTCE_IGNORED_ELEMENTS.include?(element.name)
493
575
  return false
494
576
  end
495
- #~ if element.name == 'LongDescription'
496
- #~ puts "#{' ' * depth}<#{element.name}> #{xtce_format_attributes(element)} #{element.text}"
497
- #~ else
498
- #~ puts "#{' ' * depth}<#{element.name}> #{xtce_format_attributes(element)}"
499
- #~ end
500
577
 
501
578
  case element.name
502
579
  when 'SpaceSystem'
@@ -510,11 +587,17 @@ module Cosmos
510
587
  finish_packet()
511
588
  @current_cmd_or_tlm = COMMAND
512
589
 
513
- when 'ParameterTypeSet', 'EnumerationList', 'ParameterSet', 'ContainerSet', 'EntryList', 'DefaultCalibrator', 'DefaultAlarm', 'RestrictionCriteria', 'ComparisonList', 'MetaCommandSet', 'DefaultCalibrator', 'ArgumentTypeSet', 'ArgumentList', 'ArgumentAssignmentList'
590
+ when 'ParameterTypeSet', 'EnumerationList', 'ParameterSet', 'ContainerSet', 'EntryList', 'DefaultCalibrator', 'DefaultAlarm',
591
+ 'RestrictionCriteria', 'ComparisonList', 'MetaCommandSet', 'DefaultCalibrator', 'ArgumentTypeSet', 'ArgumentList', 'ArgumentAssignmentList',
592
+ 'LocationInContainerInBits'
593
+
514
594
  # Do Nothing
515
595
 
516
- when 'EnumeratedParameterType', 'EnumeratedArgumentType', 'IntegerParameterType', 'IntegerArgumentType', 'FloatParameterType', 'FloatArgumentType', 'StringParameterType', 'StringArgumentType', 'BinaryParameterType', 'BinaryArgumentType'
596
+ when 'EnumeratedParameterType', 'EnumeratedArgumentType', 'IntegerParameterType', 'IntegerArgumentType', 'FloatParameterType', 'FloatArgumentType',
597
+ 'StringParameterType', 'StringArgumentType', 'BinaryParameterType', 'BinaryArgumentType'
598
+
517
599
  @current_type = OpenStruct.new
600
+ @current_type.endianness = :BIG_ENDIAN
518
601
  element.attributes.each do |att_name, att|
519
602
  @current_type[att.name] = att.value
520
603
  end
@@ -541,6 +624,30 @@ module Cosmos
541
624
  @current_type.sizeInBits = 8 # This is undocumented but appears to be the design
542
625
  end
543
626
 
627
+ when 'ArrayParameterType', 'ArrayArgumentType'
628
+ @current_type = OpenStruct.new
629
+ element.attributes.each do |att_name, att|
630
+ @current_type[att.name] = att.value
631
+ end
632
+ if element.name =~ /Argument/
633
+ @argument_types[element["name"]] = @current_type
634
+ else
635
+ @parameter_types[element["name"]] = @current_type
636
+ end
637
+
638
+ when 'ByteOrderList'
639
+ xtce_recurse_element(element, depth + 1) do |element, depth|
640
+ if element.name == 'Byte'
641
+ if element['byteSignificance'] and element['byteSignificance'].to_i == 0
642
+ @current_type.endianness = :LITTLE_ENDIAN
643
+ end
644
+ false
645
+ else
646
+ true
647
+ end
648
+ end
649
+ return false # Already recursed
650
+
544
651
  when "SizeInBits"
545
652
  xtce_recurse_element(element, depth + 1) do |element, depth|
546
653
  if element.name == 'FixedValue'
@@ -581,7 +688,7 @@ module Cosmos
581
688
  when 'PolynomialCalibrator'
582
689
  xtce_recurse_element(element, depth + 1) do |element, depth|
583
690
  if element.name == 'Term'
584
- index = Integer(element['exponent'])
691
+ index = Float(element['exponent']).to_i
585
692
  coeff = Float(element['coefficient'])
586
693
  @current_type.conversion ||= PolynomialConversion.new([])
587
694
  @current_type.conversion.coeffs[index] = coeff
@@ -657,25 +764,80 @@ module Cosmos
657
764
  @current_packet.description = element.text
658
765
  end
659
766
 
660
- when 'ParameterRefEntry', 'ArgumentRefEntry'
661
- if element.name =~ /Argument/
662
- # Look up the argument and argument type
663
- argument = @arguments[element['argumentRef']]
664
- raise "argumentRef #{element['argumentRef']} not found" unless argument
665
- argument_type = @argument_types[argument.argumentTypeRef]
666
- raise "argumentTypeRef #{argument.argumentTypeRef} not found" unless argument_type
667
- refName = 'argumentRef'
668
- object = argument
669
- type = argument_type
670
- else
767
+ when 'ParameterRefEntry', 'ArgumentRefEntry', 'ArrayParameterRefEntry', 'ArrayArgumentRefEntry'
768
+ reference_location, bit_offset = xtce_handle_location_in_container_in_bits(element)
769
+
770
+ array_type = nil
771
+ array_bit_size = nil
772
+ if element.name =~ /Parameter/
671
773
  # Look up the parameter and parameter type
672
774
  parameter = @parameters[element['parameterRef']]
673
775
  raise "parameterRef #{element['parameterRef']} not found" unless parameter
674
776
  parameter_type = @parameter_types[parameter.parameterTypeRef]
675
777
  raise "parameterTypeRef #{parameter.parameterTypeRef} not found" unless parameter_type
778
+ if element.name == 'ArrayParameterRefEntry'
779
+ array_type = parameter_type
780
+ parameter_type = @parameter_types[array_type.arrayTypeRef]
781
+ raise "arrayTypeRef #{parameter.arrayTypeRef} not found" unless parameter_type
782
+ end
676
783
  refName = 'parameterRef'
677
784
  object = parameter
678
785
  type = parameter_type
786
+ else
787
+ # Look up the argument and argument type
788
+ if element.name == 'ArrayArgumentRefEntry'
789
+ # Requiring parameterRef for argument arrays appears to be a defect in the schema
790
+ argument = @arguments[element['parameterRef']]
791
+ raise "parameterRef #{element['parameterRef']} not found" unless argument
792
+ argument_type = @argument_types[argument.argumentTypeRef]
793
+ raise "argumentTypeRef #{argument.argumentTypeRef} not found" unless argument_type
794
+ array_type = argument_type
795
+ argument_type = @argument_types[array_type.arrayTypeRef]
796
+ raise "arrayTypeRef #{array_type.arrayTypeRef} not found" unless argument_type
797
+ refName = 'parameterRef'
798
+ else
799
+ argument = @arguments[element['argumentRef']]
800
+ raise "argumentRef #{element['argumentRef']} not found" unless argument
801
+ argument_type = @argument_types[argument.argumentTypeRef]
802
+ raise "argumentTypeRef #{argument.argumentTypeRef} not found" unless argument_type
803
+ refName = 'argumentRef'
804
+ end
805
+ object = argument
806
+ type = argument_type
807
+ end
808
+
809
+ bit_size = Integer(type.sizeInBits)
810
+
811
+ if array_type
812
+ array_num_items = 1
813
+ # Need to determine dimensions
814
+ xtce_recurse_element(element, depth + 1) do |element, depth|
815
+ if element.name == 'Dimension'
816
+ starting_index = 0
817
+ ending_index = 0
818
+ element.children.each do |child_element|
819
+ if child_element.name == 'StartingIndex'
820
+ child_element.children.each do |child_element2|
821
+ if child_element2.name == 'FixedValue'
822
+ starting_index = child_element2.text.to_i
823
+ end
824
+ end
825
+ elsif child_element.name == 'EndingIndex'
826
+ child_element.children.each do |child_element2|
827
+ if child_element2.name == 'FixedValue'
828
+ ending_index = child_element2.text.to_i
829
+ end
830
+ end
831
+ array_num_items *= ((ending_index - starting_index).abs + 1)
832
+ end
833
+ false # Don't recurse again
834
+ end
835
+ false # Don't recurse again
836
+ else
837
+ true # Keep recursing
838
+ end
839
+ end
840
+ array_bit_size = array_num_items * bit_size
679
841
  end
680
842
 
681
843
  # Add item to packet
@@ -697,7 +859,21 @@ module Cosmos
697
859
  raise "Referenced Parameter/Argument has no xtce_encoding: #{element[refName]}"
698
860
  end
699
861
 
700
- item = @current_packet.append_item(object.name, Integer(type.sizeInBits), data_type) #, array_size = nil, endianness = @default_endianness, overflow = :ERROR, format_string = nil, read_conversion = nil, write_conversion = nil, id_value = nil)
862
+ if bit_offset
863
+ case reference_location
864
+ when 'containerStart'
865
+ item = @current_packet.define_item(object.name, bit_offset, bit_size, data_type, array_bit_size, type.endianness) # overflow = :ERROR, format_string = nil, read_conversion = nil, write_conversion = nil, id_value = nil)
866
+ when 'containerEnd'
867
+ item = @current_packet.define_item(object.name, -bit_offset, bit_size, data_type, array_bit_size, type.endianness) # overflow = :ERROR, format_string = nil, read_conversion = nil, write_conversion = nil, id_value = nil)
868
+ when 'previousEntry', nil
869
+ item = @current_packet.define_item(object.name, @current_packet.length + bit_offset, bit_size, data_type, array_bit_size, type.endianness) # overflow = :ERROR, format_string = nil, read_conversion = nil, write_conversion = nil, id_value = nil)
870
+ when 'nextEntry'
871
+ raise 'nextEntry is not supported'
872
+ end
873
+ else
874
+ item = @current_packet.append_item(object.name, bit_size, data_type, array_bit_size, type.endianness) # overflow = :ERROR, format_string = nil, read_conversion = nil, write_conversion = nil, id_value = nil)
875
+ end
876
+
701
877
  item.description = type.shortDescription if type.shortDescription
702
878
  if type.states
703
879
  item.states = type.states
@@ -713,27 +889,24 @@ module Cosmos
713
889
  end
714
890
 
715
891
  # Need to set min, max, and default
716
- if data_type == :INT
717
- item.range = (-(2 ** (Integer(type.sizeInBits) - 1)))..((2 ** (Integer(type.sizeInBits) - 1)) - 1)
718
- if type.minInclusive and type.maxInclusive
719
- item.range = Integer(type.minInclusive)..Integer(type.maxInclusive)
720
- end
721
- item.default = 0
722
- if item.states and item.states[type.initialValue.to_s.upcase]
723
- item.default = Integer(item.states[type.initialvalue.to_s.upcase])
892
+ if data_type == :INT or data_type == :UINT
893
+ if data_type == :INT
894
+ item.range = (-(2 ** (Integer(type.sizeInBits) - 1)))..((2 ** (Integer(type.sizeInBits) - 1)) - 1)
724
895
  else
725
- item.default = Integer(type.initialValue) if type.initialValue
896
+ item.range = 0..((2 ** Integer(type.sizeInBits)) - 1)
726
897
  end
727
- elsif data_type == :UINT
728
- item.range = 0..((2 ** Integer(type.sizeInBits)) - 1)
729
898
  if type.minInclusive and type.maxInclusive
730
899
  item.range = Integer(type.minInclusive)..Integer(type.maxInclusive)
731
900
  end
732
- item.default = 0
733
- if item.states and item.states[type.initialValue.to_s.upcase]
734
- item.default = Integer(item.states[type.initialValue.to_s.upcase])
901
+ if item.array_size
902
+ item.default = []
735
903
  else
736
- item.default = Integer(type.initialValue) if type.initialValue
904
+ item.default = 0
905
+ if item.states and item.states[type.initialValue.to_s.upcase]
906
+ item.default = Integer(item.states[type.initialValue.to_s.upcase])
907
+ else
908
+ item.default = Integer(type.initialValue) if type.initialValue
909
+ end
737
910
  end
738
911
  elsif data_type == :FLOAT
739
912
  if Integer(type.sizeInBits) == 32
@@ -744,19 +917,31 @@ module Cosmos
744
917
  if type.minInclusive and type.maxInclusive
745
918
  item.range = Float(type.minInclusive)..Float(type.maxInclusive)
746
919
  end
747
- item.default = 0.0
748
- item.default = Float(type.initialValue) if type.initialValue
920
+ if item.array_size
921
+ item.default = []
922
+ else
923
+ item.default = 0.0
924
+ item.default = Float(type.initialValue) if type.initialValue
925
+ end
749
926
  elsif data_type == :STRING
750
- if type.initialValue
751
- item.default = type.initialValue
927
+ if item.array_size
928
+ item.default = []
752
929
  else
753
- item.default = ''
930
+ if type.initialValue
931
+ item.default = type.initialValue
932
+ else
933
+ item.default = ''
934
+ end
754
935
  end
755
936
  elsif data_type == :BLOCK
756
- if type.initialValue
757
- item.default = type.initialValue
937
+ if item.array_size
938
+ item.default = []
758
939
  else
759
- item.default = ''
940
+ if type.initialValue
941
+ item.default = type.initialValue
942
+ else
943
+ item.default = ''
944
+ end
760
945
  end
761
946
  end
762
947
  else
@@ -774,6 +959,8 @@ module Cosmos
774
959
  end
775
960
  end
776
961
 
962
+ return false # Already recursed
963
+
777
964
  when 'BaseContainer'
778
965
  # Handled in SequenceContainer/CommandContainer
779
966
 
@@ -879,6 +1066,19 @@ module Cosmos
879
1066
  end
880
1067
  end
881
1068
 
1069
+ def xtce_handle_location_in_container_in_bits(element)
1070
+ element.children.each do |child_element|
1071
+ if child_element.name == 'LocationInContainerInBits'
1072
+ child_element.children.each do |child_element2|
1073
+ if child_element2.name == 'FixedValue'
1074
+ return [child_element['referenceLocation'], Integer(child_element2.text)]
1075
+ end
1076
+ end
1077
+ end
1078
+ end
1079
+ return [nil, nil]
1080
+ end
1081
+
882
1082
  def process_current_packet(parser, keyword, params)
883
1083
  case keyword
884
1084
 
@@ -1079,9 +1279,9 @@ module Cosmos
1079
1279
  end
1080
1280
  usage = "MINIMUM_VALUE <MINIMUM VALUE>"
1081
1281
  parser.verify_num_parameters(1, 1, usage)
1082
- @current_item.range =
1083
- Range.new(ConfigParser.handle_defined_constants(
1084
- params[0].convert_to_value), @current_item.range.end)
1282
+ min = ConfigParser.handle_defined_constants(
1283
+ params[0].convert_to_value, @current_item.data_type, @current_item.bit_size)
1284
+ @current_item.range = Range.new(min, @current_item.range.end)
1085
1285
 
1086
1286
  # Update the maximum value for the current command parameter
1087
1287
  when 'MAXIMUM_VALUE'
@@ -1090,9 +1290,9 @@ module Cosmos
1090
1290
  end
1091
1291
  usage = "MAXIMUM_VALUE <MAXIMUM VALUE>"
1092
1292
  parser.verify_num_parameters(1, 1, usage)
1093
- @current_item.range =
1094
- Range.new(@current_item.range.begin,
1095
- ConfigParser.handle_defined_constants(params[0].convert_to_value))
1293
+ max = ConfigParser.handle_defined_constants(
1294
+ params[0].convert_to_value, @current_item.data_type, @current_item.bit_size)
1295
+ @current_item.range = Range.new(@current_item.range.begin, max)
1096
1296
 
1097
1297
  # Update the default value for the current command parameter
1098
1298
  when 'DEFAULT_VALUE'
@@ -1105,8 +1305,8 @@ module Cosmos
1105
1305
  (@current_item.data_type == :BLOCK))
1106
1306
  @current_item.default = params[0]
1107
1307
  else
1108
- @current_item.default =
1109
- ConfigParser.handle_defined_constants(params[0].convert_to_value)
1308
+ @current_item.default = ConfigParser.handle_defined_constants(
1309
+ params[0].convert_to_value, @current_item.data_type, @current_item.bit_size)
1110
1310
  end
1111
1311
 
1112
1312
  # Update the overflow type for the current command parameter