openc3 5.5.2 → 5.6.1
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of openc3 might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/bin/openc3cli +167 -69
- data/data/config/_interfaces.yaml +1 -6
- data/data/config/interface_modifiers.yaml +55 -4
- data/data/config/microservice.yaml +30 -3
- data/ext/openc3/ext/crc/crc.c +82 -1
- data/lib/openc3/api/cmd_api.rb +19 -7
- data/lib/openc3/api/tlm_api.rb +13 -12
- data/lib/openc3/bridge/bridge_config.rb +4 -4
- data/lib/openc3/config/config_parser.rb +1 -0
- data/lib/openc3/conversions/unix_time_conversion.rb +3 -1
- data/lib/openc3/ext/.keep +0 -0
- data/lib/openc3/interfaces/interface.rb +54 -26
- data/lib/openc3/interfaces/serial_interface.rb +4 -5
- data/lib/openc3/interfaces/simulated_target_interface.rb +4 -4
- data/lib/openc3/interfaces/stream_interface.rb +2 -2
- data/lib/openc3/interfaces/tcpip_client_interface.rb +4 -3
- data/lib/openc3/interfaces/tcpip_server_interface.rb +18 -19
- data/lib/openc3/interfaces/udp_interface.rb +10 -4
- data/lib/openc3/io/json_api.rb +72 -0
- data/lib/openc3/io/serial_driver.rb +4 -5
- data/lib/openc3/logs/buffered_packet_log_writer.rb +2 -4
- data/lib/openc3/logs/log_writer.rb +9 -8
- data/lib/openc3/logs/packet_log_reader.rb +8 -1
- data/lib/openc3/logs/packet_log_writer.rb +3 -4
- data/lib/openc3/logs/stream_log.rb +116 -0
- data/lib/openc3/logs/stream_log_pair.rb +70 -0
- data/lib/openc3/microservices/cleanup_microservice.rb +1 -1
- data/lib/openc3/microservices/decom_microservice.rb +17 -2
- data/lib/openc3/microservices/interface_decom_common.rb +42 -0
- data/lib/openc3/microservices/interface_microservice.rb +24 -17
- data/lib/openc3/microservices/router_microservice.rb +46 -4
- data/lib/openc3/migrations/20220420190000_log_stuff.rb +47 -0
- data/lib/openc3/migrations/20221202214600_add_target_names.rb +1 -1
- data/lib/openc3/models/gem_model.rb +2 -2
- data/lib/openc3/models/interface_model.rb +13 -14
- data/lib/openc3/models/metadata_model.rb +1 -1
- data/lib/openc3/models/note_model.rb +1 -1
- data/lib/openc3/models/plugin_model.rb +3 -2
- data/lib/openc3/operators/operator.rb +2 -0
- data/lib/openc3/packets/commands.rb +2 -0
- data/lib/openc3/packets/packet_config.rb +3 -2
- data/lib/openc3/packets/parsers/xtce_converter.rb +2 -1
- data/lib/openc3/script/gems.rb +125 -0
- data/lib/openc3/script/plugins.rb +186 -0
- data/lib/openc3/script/screen.rb +119 -0
- data/lib/openc3/script/script.rb +3 -0
- data/lib/openc3/script/script_runner.rb +19 -8
- data/lib/openc3/script/suite_results.rb +2 -2
- data/lib/openc3/script/web_socket_api.rb +5 -1
- data/lib/openc3/streams/serial_stream.rb +14 -11
- data/lib/openc3/streams/tcpip_client_stream.rb +5 -2
- data/lib/openc3/streams/tcpip_socket_stream.rb +37 -71
- data/lib/openc3/streams/web_socket_client_stream.rb +5 -3
- data/lib/openc3/system/system.rb +2 -0
- data/lib/openc3/topics/interface_topic.rb +13 -4
- data/lib/openc3/topics/router_topic.rb +6 -6
- data/lib/openc3/topics/telemetry_decom_topic.rb +10 -1
- data/lib/openc3/utilities/bucket_utilities.rb +12 -5
- data/lib/openc3/utilities/cli_generator.rb +56 -4
- data/lib/openc3/utilities/crc.rb +42 -7
- data/lib/openc3/utilities/process_manager.rb +3 -1
- data/lib/openc3/utilities/ruby_lex_utils.rb +265 -504
- data/lib/openc3/version.rb +6 -6
- data/templates/conversion/conversion.rb +10 -2
- data/templates/microservice/microservices/TEMPLATE/microservice.rb +1 -1
- data/templates/plugin/Rakefile +8 -1
- data/templates/widget/.browserslistrc +16 -0
- data/templates/widget/.eslintrc.js +43 -0
- data/templates/widget/.nycrc +3 -0
- data/templates/widget/.prettierrc.js +5 -0
- data/templates/widget/LICENSE.txt +20 -0
- data/templates/widget/Rakefile +24 -0
- data/templates/widget/babel.config.json +11 -0
- data/templates/widget/package.json +35 -0
- data/templates/widget/src/Widget.vue +46 -0
- data/templates/widget/vue.config.js +25 -0
- data/templates/widget/yarn.lock +8938 -0
- metadata +22 -4
- data/lib/openc3/io/raw_logger.rb +0 -170
- data/lib/openc3/io/raw_logger_pair.rb +0 -80
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: aec8c77fa13a1d046d9a6a75b0ab2854a5c130a9ea967dc7b9164ae3840ca4a1
|
4
|
+
data.tar.gz: 9071d947cf90051add2c714a74c40ab54b359b4a16861029e93e290cd68b05bd
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 399787f9f75cf2d66d340662e9dbfb57feb700ea6661f0e93668a88e0b327dead2f1ca76a910da7d604ffce64ec627e8a177997d4c6c5292c281c8e410510516
|
7
|
+
data.tar.gz: bae872d3fef6e8e2014d116b461b4685e56222e9d2ac31c5c1ee2720733affa3ae5cb0b482dfc5c30488d34809063e97a352b69c8afb1bb2cb5c8e5eabe4abb6
|
data/bin/openc3cli
CHANGED
@@ -79,6 +79,28 @@ def print_usage
|
|
79
79
|
puts ""
|
80
80
|
end
|
81
81
|
|
82
|
+
def check_environment
|
83
|
+
hostname = ENV['OPENC3_API_HOSTNAME'] || (ENV['OPENC3_DEVEL'] ? '127.0.0.1' : 'openc3-cosmos-cmd-tlm-api')
|
84
|
+
begin
|
85
|
+
Resolv.getaddress(hostname)
|
86
|
+
rescue Resolv::ResolvError
|
87
|
+
abort "Unable to resolv api hostname: #{hostname}"
|
88
|
+
end
|
89
|
+
|
90
|
+
if hostname =~ /openc3-cosmos-cmd-tlm-api/
|
91
|
+
$openc3_in_cluster = true
|
92
|
+
else
|
93
|
+
$openc3_in_cluster = false
|
94
|
+
end
|
95
|
+
|
96
|
+
unless $openc3_in_cluster
|
97
|
+
# Make sure the user has all the required environment variables set
|
98
|
+
abort "OPENC3_API_HOSTNAME environment variable is required" unless ENV['OPENC3_API_HOSTNAME']
|
99
|
+
abort "OPENC3_API_PORT environment variable is required" unless ENV['OPENC3_API_PORT']
|
100
|
+
abort "OPENC3_API_PASSWORD environment variable is required" unless ENV['OPENC3_API_PASSWORD']
|
101
|
+
end
|
102
|
+
end
|
103
|
+
|
82
104
|
def migrate(args)
|
83
105
|
MIGRATE_PARSER.parse!(args)
|
84
106
|
abort(MIGRATE_PARSER.to_s) if args.length == 0
|
@@ -101,9 +123,7 @@ def migrate(args)
|
|
101
123
|
# NOTE: generate does a chdir to be inside the plugin directory
|
102
124
|
###############################################################
|
103
125
|
plugin = args.shift
|
104
|
-
|
105
|
-
# Delete target contents from the plugin framework (but keep directory)
|
106
|
-
FileUtils.rm_rf Dir.glob("targets/#{target_name}/*")
|
126
|
+
OpenC3::CliGenerator.generate(['plugin', plugin])
|
107
127
|
|
108
128
|
if MIGRATE_OPTIONS.all
|
109
129
|
# Grab all target directories to match the command line input
|
@@ -301,6 +321,29 @@ def update_plugin(plugin_file_path, plugin_name, variables: nil, plugin_txt_line
|
|
301
321
|
end
|
302
322
|
end
|
303
323
|
|
324
|
+
def wait_process_complete(process_name)
|
325
|
+
STDOUT.flush
|
326
|
+
state = 'Running'
|
327
|
+
status = nil
|
328
|
+
while state == 'Running'
|
329
|
+
status = plugin_status(process_name)
|
330
|
+
state = status['state']
|
331
|
+
sleep(5)
|
332
|
+
print '.'
|
333
|
+
STDOUT.flush
|
334
|
+
end
|
335
|
+
puts "\nFinished: #{state}"
|
336
|
+
puts "Output:\n"
|
337
|
+
puts status['output']
|
338
|
+
if state == 'Complete'
|
339
|
+
puts "Success!"
|
340
|
+
exit 0
|
341
|
+
else
|
342
|
+
puts "Failed!"
|
343
|
+
exit 1
|
344
|
+
end
|
345
|
+
end
|
346
|
+
|
304
347
|
# Loads a plugin into the OpenC3 system
|
305
348
|
# This code is used from the command line and is the same code that gets called if you
|
306
349
|
# edit/upgrade or install a new plugin from the Admin interface
|
@@ -320,90 +363,142 @@ end
|
|
320
363
|
#
|
321
364
|
def load_plugin(plugin_file_path, scope:, plugin_hash_file: nil, force: false)
|
322
365
|
scope ||= 'DEFAULT'
|
323
|
-
|
324
|
-
|
325
|
-
|
326
|
-
|
327
|
-
|
328
|
-
|
329
|
-
|
330
|
-
|
331
|
-
|
366
|
+
check_environment()
|
367
|
+
if $openc3_in_cluster
|
368
|
+
# In Cluster
|
369
|
+
|
370
|
+
# Only create the scope if it doesn't already exist
|
371
|
+
unless OpenC3::ScopeModel.names.include?(scope)
|
372
|
+
begin
|
373
|
+
puts "Creating scope: #{scope}"
|
374
|
+
scope_model = OpenC3::ScopeModel.new(name: scope, scope: scope)
|
375
|
+
scope_model.create
|
376
|
+
scope_model.deploy(".", {})
|
377
|
+
rescue => err
|
378
|
+
abort("Error creating scope: #{scope}: #{err.formatted}")
|
379
|
+
end
|
332
380
|
end
|
333
|
-
end
|
334
381
|
|
335
|
-
|
336
|
-
|
337
|
-
|
338
|
-
|
339
|
-
|
340
|
-
|
341
|
-
|
342
|
-
|
343
|
-
|
344
|
-
|
345
|
-
|
346
|
-
|
347
|
-
|
348
|
-
|
349
|
-
|
350
|
-
|
351
|
-
|
352
|
-
|
353
|
-
|
354
|
-
|
355
|
-
|
356
|
-
|
382
|
+
begin
|
383
|
+
if plugin_hash_file
|
384
|
+
# Admin Create / Edit / or Upgrade Plugin
|
385
|
+
OpenC3::PluginModel.install_phase1(plugin_file_path, scope: scope)
|
386
|
+
plugin_hash = JSON.parse(File.read(plugin_hash_file), :allow_nan => true, :create_additions => true)
|
387
|
+
else
|
388
|
+
# Init or Command Line openc3cli load with no plugin_hash_file
|
389
|
+
file_full_name = File.basename(plugin_file_path, ".gem")
|
390
|
+
file_gem_name = file_full_name.split('-')[0..-2].join('-')
|
391
|
+
found = false
|
392
|
+
plugin_names = OpenC3::PluginModel.names(scope: scope)
|
393
|
+
plugin_names.each do |plugin_name|
|
394
|
+
gem_name = plugin_name.split("__")[0]
|
395
|
+
full_name = File.basename(gem_name, ".gem")
|
396
|
+
gem_name = full_name.split('-')[0..-2].join('-')
|
397
|
+
if file_gem_name == gem_name
|
398
|
+
found = true
|
399
|
+
# Upgrade if version changed else do nothing
|
400
|
+
if file_full_name != full_name
|
401
|
+
update_plugin(plugin_file_path, plugin_name, scope: scope, existing_plugin_name: plugin_name, force: force)
|
402
|
+
else
|
403
|
+
puts "No version change detected for: #{plugin_name}"
|
404
|
+
end
|
357
405
|
end
|
358
406
|
end
|
407
|
+
return if found
|
408
|
+
|
409
|
+
plugin_hash = OpenC3::PluginModel.install_phase1(plugin_file_path, scope: scope)
|
359
410
|
end
|
360
|
-
return if found
|
361
411
|
|
362
|
-
|
363
|
-
|
412
|
+
# Determine if plugin named in plugin_hash exists
|
413
|
+
existing_plugin_hash = OpenC3::PluginModel.get(name: plugin_hash['name'], scope: scope)
|
414
|
+
|
415
|
+
# Existing plugin hash will be present if plugin is being edited or upgraded
|
416
|
+
# However, a missing existing could also be that a plugin was updated in local mode directly from across installations
|
417
|
+
# changing the plugin name without really meaning to create a new instance of the plugin
|
418
|
+
# ie.
|
419
|
+
# User on machine 1 checks in a changed plugin_instance.json with a different name - There is still only one plugin desired and committed
|
420
|
+
# User on machine 2 starts up with the new configuration, OpenC3::PluginModel.get will return nil because the exact name is different
|
421
|
+
# In this case, the plugin should be updated without installing a second instance. analyze_local_mode figures this out.
|
422
|
+
unless existing_plugin_hash
|
423
|
+
existing_plugin_hash = OpenC3::LocalMode.analyze_local_mode(plugin_name: plugin_hash['name'], scope: scope)
|
424
|
+
end
|
364
425
|
|
365
|
-
|
366
|
-
|
367
|
-
|
368
|
-
|
369
|
-
|
370
|
-
|
371
|
-
|
372
|
-
|
373
|
-
|
374
|
-
|
375
|
-
|
376
|
-
|
426
|
+
if existing_plugin_hash
|
427
|
+
# Upgrade or Edit
|
428
|
+
update_plugin(plugin_file_path, plugin_hash['name'], variables: plugin_hash['variables'], scope: scope,
|
429
|
+
plugin_txt_lines: plugin_hash['plugin_txt_lines'], existing_plugin_name: existing_plugin_hash['name'], force: force)
|
430
|
+
else
|
431
|
+
# New Install
|
432
|
+
puts "Loading new plugin: #{plugin_file_path}\n#{plugin_hash}"
|
433
|
+
plugin_hash = OpenC3::PluginModel.install_phase2(plugin_hash, scope: scope)
|
434
|
+
OpenC3::LocalMode.update_local_plugin(plugin_file_path, plugin_hash, scope: scope)
|
435
|
+
end
|
436
|
+
rescue => error
|
437
|
+
abort("Error installing plugin: #{scope}: #{plugin_file_path}\n#{error.message}")
|
377
438
|
end
|
439
|
+
else
|
440
|
+
# Outside Cluster
|
441
|
+
require 'openc3/script'
|
378
442
|
|
379
|
-
if
|
380
|
-
|
381
|
-
update_plugin(plugin_file_path, plugin_hash['name'], variables: plugin_hash['variables'], scope: scope,
|
382
|
-
plugin_txt_lines: plugin_hash['plugin_txt_lines'], existing_plugin_name: existing_plugin_hash['name'], force: force)
|
443
|
+
if plugin_hash_file
|
444
|
+
plugin_hash = JSON.parse(File.read(plugin_hash_file), :allow_nan => true, :create_additions => true)
|
383
445
|
else
|
384
|
-
|
385
|
-
puts "Loading new plugin: #{plugin_file_path}\n#{plugin_hash}"
|
386
|
-
plugin_hash = OpenC3::PluginModel.install_phase2(plugin_hash, scope: scope)
|
387
|
-
OpenC3::LocalMode.update_local_plugin(plugin_file_path, plugin_hash, scope: scope)
|
446
|
+
plugin_hash = plugin_install_phase1(plugin_file_path, scope: scope)
|
388
447
|
end
|
389
|
-
|
390
|
-
|
448
|
+
|
449
|
+
process_name = plugin_install_phase2(plugin_hash, scope: scope)
|
450
|
+
|
451
|
+
print "Installing..."
|
452
|
+
wait_process_complete(process_name)
|
391
453
|
end
|
392
454
|
end
|
393
455
|
|
394
456
|
def unload_plugin(plugin_name, scope:)
|
395
457
|
scope ||= 'DEFAULT'
|
396
|
-
|
397
|
-
|
398
|
-
|
399
|
-
|
400
|
-
|
401
|
-
|
458
|
+
check_environment()
|
459
|
+
if $openc3_in_cluster
|
460
|
+
begin
|
461
|
+
plugin_model = OpenC3::PluginModel.get_model(name: plugin_name, scope: scope)
|
462
|
+
plugin_model.destroy
|
463
|
+
OpenC3::LocalMode.remove_local_plugin(plugin_name, scope: scope)
|
464
|
+
OpenC3::Logger.info("PluginModel destroyed: #{plugin_name}", scope: scope)
|
465
|
+
rescue => err
|
466
|
+
abort("Error uninstalling plugin: #{scope}: #{plugin_name}: #{err.formatted}")
|
467
|
+
end
|
468
|
+
else
|
469
|
+
# Outside Cluster
|
470
|
+
require 'openc3/script'
|
471
|
+
process_name = plugin_uninstall(plugin_name, scope: scope)
|
472
|
+
print "Uninstalling..."
|
473
|
+
wait_process_complete(process_name)
|
474
|
+
end
|
475
|
+
end
|
476
|
+
|
477
|
+
def cli_gem_install(gem_filename, scope:)
|
478
|
+
scope ||= 'DEFAULT'
|
479
|
+
check_environment()
|
480
|
+
if $openc3_in_cluster
|
481
|
+
OpenC3::GemModel.install(gem_filename, scope: scope)
|
482
|
+
else
|
483
|
+
# Outside Cluster
|
484
|
+
require 'openc3/script'
|
485
|
+
process_name = gem_install(gem_filename, scope: scope)
|
486
|
+
print "Installing..."
|
487
|
+
wait_process_complete(process_name)
|
402
488
|
end
|
403
489
|
end
|
404
490
|
|
405
|
-
def
|
406
|
-
|
491
|
+
def cli_gem_uninstall(gem_filename, scope:)
|
492
|
+
scope ||= 'DEFAULT'
|
493
|
+
check_environment()
|
494
|
+
if $openc3_in_cluster
|
495
|
+
OpenC3::GemModel.destroy(gem_filename)
|
496
|
+
else
|
497
|
+
# Outside Cluster
|
498
|
+
require 'openc3/script'
|
499
|
+
gem_uninstall(gem_filename, scope: scope)
|
500
|
+
puts "Success!"
|
501
|
+
end
|
407
502
|
end
|
408
503
|
|
409
504
|
def get_redis_keys
|
@@ -510,7 +605,10 @@ if not ARGV[0].nil? # argument(s) given
|
|
510
605
|
unload_plugin(ARGV[1], scope: ARGV[2])
|
511
606
|
|
512
607
|
when 'geminstall'
|
513
|
-
|
608
|
+
cli_gem_install(ARGV[1], scope: ARGV[2])
|
609
|
+
|
610
|
+
when 'gemuninstall'
|
611
|
+
cli_gem_uninstall(ARGV[1], scope: ARGV[2])
|
514
612
|
|
515
613
|
when 'generate'
|
516
614
|
OpenC3::CliGenerator.generate(ARGV[1..-1])
|
@@ -17,7 +17,6 @@ tcpip_client_interface.rb:
|
|
17
17
|
- name: Write Timeout
|
18
18
|
required: true
|
19
19
|
description: Number of seconds to wait before aborting the write.
|
20
|
-
Pass 'nil' to block on write.
|
21
20
|
values: .+
|
22
21
|
- name: Read Timeout
|
23
22
|
required: true
|
@@ -43,7 +42,6 @@ tcpip_server_interface.rb:
|
|
43
42
|
- name: Write Timeout
|
44
43
|
required: true
|
45
44
|
description: Number of seconds to wait before aborting the write.
|
46
|
-
Pass 'nil' to block on write.
|
47
45
|
values: .+
|
48
46
|
- name: Read Timeout
|
49
47
|
required: true
|
@@ -90,9 +88,7 @@ udp_interface.rb:
|
|
90
88
|
values: .+
|
91
89
|
- name: Write Timeout
|
92
90
|
required: false
|
93
|
-
description:
|
94
|
-
Number of seconds to wait before aborting the write. Default is
|
95
|
-
'nil' (block on write).
|
91
|
+
description: Number of seconds to wait before aborting the write
|
96
92
|
values: .+
|
97
93
|
- name: Read Timeout
|
98
94
|
required: false
|
@@ -134,7 +130,6 @@ serial_interface.rb:
|
|
134
130
|
- name: Write Timeout
|
135
131
|
required: true
|
136
132
|
description: Number of seconds to wait before aborting the write.
|
137
|
-
Pass 'nil' to block on write.
|
138
133
|
values: .+
|
139
134
|
- name: Read Timeout
|
140
135
|
required: true
|
@@ -6,6 +6,9 @@ MAP_TARGET:
|
|
6
6
|
required: true
|
7
7
|
description: Target name to map to this interface
|
8
8
|
values: .+
|
9
|
+
example: |
|
10
|
+
INTERFACE DATA_INT tcpip_client_interface.rb host.docker.internal 8080 8081 10.0 nil BURST
|
11
|
+
MAP_TARGET DATA
|
9
12
|
MAP_CMD_TARGET:
|
10
13
|
summary: Maps a target name to an interface for commands only
|
11
14
|
since: 5.2.0
|
@@ -14,6 +17,9 @@ MAP_CMD_TARGET:
|
|
14
17
|
required: true
|
15
18
|
description: Command target name to map to this interface
|
16
19
|
values: .+
|
20
|
+
example: |
|
21
|
+
INTERFACE CMD_INT tcpip_client_interface.rb host.docker.internal 8080 8081 10.0 nil BURST
|
22
|
+
MAP_CMD_TARGET DATA # Only DATA commands go on the CMD_INT interface
|
17
23
|
MAP_TLM_TARGET:
|
18
24
|
summary: Maps a target name to an interface for telemetry only
|
19
25
|
since: 5.2.0
|
@@ -22,6 +28,9 @@ MAP_TLM_TARGET:
|
|
22
28
|
required: true
|
23
29
|
description: Telemetry target name to map to this interface
|
24
30
|
values: .+
|
31
|
+
example: |
|
32
|
+
INTERFACE TLM_INT tcpip_client_interface.rb host.docker.internal 8080 8081 10.0 nil BURST
|
33
|
+
MAP_TLM_TARGET DATA # Only DATA telemetry received on TLM_INT interface
|
25
34
|
DONT_CONNECT:
|
26
35
|
summary: Server will not automatically try to connect to the interface at startup
|
27
36
|
DONT_RECONNECT:
|
@@ -43,14 +52,41 @@ DISABLE_DISCONNECT:
|
|
43
52
|
Use this keyword to prevent the user from disconnecting from the interface.
|
44
53
|
This is typically used in a 'production' environment where you would not want
|
45
54
|
the user to inadvertantly disconnect from a target.
|
46
|
-
DONT_LOG:
|
47
|
-
summary: Disable logging commands and telemetry on this interface
|
48
55
|
LOG_RAW:
|
56
|
+
summary: Deprecated, use LOG_STREAM
|
57
|
+
LOG_STREAM:
|
49
58
|
summary: Log all data on the interface exactly as it is sent and received
|
50
59
|
description:
|
51
|
-
|
60
|
+
LOG_STREAM does not add any OpenC3 headers and thus can not be read by OpenC3 tools.
|
52
61
|
It is primarily useful for low level debugging of an interface. You will have to
|
53
62
|
manually parse these logs yourself using a hex editor or other application.
|
63
|
+
since: 5.5.2
|
64
|
+
parameters:
|
65
|
+
- name: Cycle Time
|
66
|
+
required: false
|
67
|
+
description:
|
68
|
+
Amount of time to wait before cycling the log file. Default is 10 min.
|
69
|
+
If nil refer to Cycle Hour and Cycle Minute.
|
70
|
+
values: .*
|
71
|
+
- name: Cycle Size
|
72
|
+
required: false
|
73
|
+
description: Amount of data to write before cycling the log file. Default is 50MB.
|
74
|
+
values: .*
|
75
|
+
- name: Cycle Hour
|
76
|
+
required: false
|
77
|
+
description:
|
78
|
+
The time at which to cycle the log. Combined with Cycle Minute to cycle
|
79
|
+
the log daily at the specified time. If nil, the log will be cycled hourly at the specified Cycle Minute.
|
80
|
+
Only applies if Cycle Time is nil.
|
81
|
+
values: .*
|
82
|
+
- name: Cycle Minute
|
83
|
+
required: false
|
84
|
+
description: See Cycle Hour.
|
85
|
+
values: .*
|
86
|
+
example: |
|
87
|
+
INTERFACE EXAMPLE example_interface.rb
|
88
|
+
# Override the default log time of 600
|
89
|
+
LOG_STREAM 60
|
54
90
|
PROTOCOL:
|
55
91
|
summary: Protocols modify the interface by processing the data
|
56
92
|
description:
|
@@ -71,6 +107,14 @@ PROTOCOL:
|
|
71
107
|
- name: Protocol specific parameters
|
72
108
|
required: false
|
73
109
|
description: Additional parameters used by the protocol
|
110
|
+
example: |
|
111
|
+
INTERFACE DATA_INT tcpip_client_interface.rb host.docker.internal 8080 8081 10.0 nil nil
|
112
|
+
MAP_TARGET DATA
|
113
|
+
# Rather than defining the LENGTH protocol on the INTERFACE line we define it here
|
114
|
+
PROTOCOL READ LengthProtocol 0 16 0 1 BIG_ENDIAN 4 0xBA5EBA11
|
115
|
+
INTERFACE DATA_INT tcpip_client_interface.rb host.docker.internal 8080 8081 10.0 nil BURST
|
116
|
+
MAP_TARGET DATA
|
117
|
+
PROTOCOL READ IgnorePacketProtocol INST IMAGE # Drop all INST IMAGE packets
|
74
118
|
OPTION:
|
75
119
|
summary: Set a parameter on an interface
|
76
120
|
description:
|
@@ -90,6 +134,10 @@ OPTION:
|
|
90
134
|
required: false
|
91
135
|
description: Parameters to pass to the option
|
92
136
|
values: .*
|
137
|
+
example: |
|
138
|
+
INTERFACE SERIAL_INT serial_interface.rb COM1 COM1 115200 NONE 1 10.0 nil
|
139
|
+
OPTION FLOW_CONTROL RTSCTS
|
140
|
+
OPTION DATA_BITS 8
|
93
141
|
SECRET:
|
94
142
|
summary: Define a secret needed by this interface
|
95
143
|
description: Defines a secret for this interface and optionally assigns its value to an option
|
@@ -105,7 +153,7 @@ SECRET:
|
|
105
153
|
required: true
|
106
154
|
description: The name of the secret to retrieve
|
107
155
|
values: .*
|
108
|
-
- name: Environment Variable
|
156
|
+
- name: Environment Variable or File Path
|
109
157
|
required: true
|
110
158
|
description: Environment variable name or file path to store secret
|
111
159
|
values: .*
|
@@ -117,3 +165,6 @@ SECRET:
|
|
117
165
|
required: false
|
118
166
|
description: Name of the secret store for stores with multipart keys
|
119
167
|
values: .*
|
168
|
+
example: |
|
169
|
+
SECRET ENV USERNAME ENV_USERNAME USERNAME
|
170
|
+
SECRET FILE KEY "/tmp/DATA/cert" KEY
|
@@ -1,7 +1,6 @@
|
|
1
1
|
---
|
2
2
|
MICROSERVICE:
|
3
3
|
summary: Defines a new microservice
|
4
|
-
example: MICROSERVICE EXAMPLE example-microservice
|
5
4
|
description: Defines a microservice that the plugin adds to the OpenC3 system. Microservices are background software processes that perform persistent processing.
|
6
5
|
parameters:
|
7
6
|
- name: Microservice Folder Name
|
@@ -12,6 +11,7 @@ MICROSERVICE:
|
|
12
11
|
description: The specific name of this instance of the microservice in the OpenC3 system
|
13
12
|
required: true
|
14
13
|
values: .+
|
14
|
+
example: MICROSERVICE EXAMPLE openc3-example
|
15
15
|
modifiers:
|
16
16
|
ENV:
|
17
17
|
summary: Sets an environment variable in the microservice.
|
@@ -24,6 +24,9 @@ MICROSERVICE:
|
|
24
24
|
required: true
|
25
25
|
description: Environment variable value
|
26
26
|
values: .+
|
27
|
+
example: |
|
28
|
+
MICROSERVICE EXAMPLE openc3-example
|
29
|
+
ENV COMPANY OpenC3
|
27
30
|
WORK_DIR:
|
28
31
|
summary: Set the working directory
|
29
32
|
description: Working directory to run the microservice CMD in. Can be a path relative to the microservice folder in the plugin, or an absolute path in the container the microservice runs in.
|
@@ -32,6 +35,9 @@ MICROSERVICE:
|
|
32
35
|
required: true
|
33
36
|
description: Working directory to run the microservice CMD in. Can be a path relative to the microservice folder in the plugin, or an absolute path in the container the microservice runs in.
|
34
37
|
values: .+
|
38
|
+
example: |
|
39
|
+
MICROSERVICE EXAMPLE openc3-example
|
40
|
+
WORK_DIR .
|
35
41
|
PORT:
|
36
42
|
summary: Open port for the microservice
|
37
43
|
description: Kubernetes needs a Service to be applied to open a port so this is required for Kubernetes support
|
@@ -45,6 +51,9 @@ MICROSERVICE:
|
|
45
51
|
required: false
|
46
52
|
description: Port protocol. Default is TCP.
|
47
53
|
values: .+
|
54
|
+
example: |
|
55
|
+
MICROSERVICE EXAMPLE openc3-example
|
56
|
+
PORT 7272
|
48
57
|
TOPIC:
|
49
58
|
summary: Associate a Redis topic
|
50
59
|
description: Redis topic to associate with this microservice. Standard OpenC3 microservices such as decom_microservice use this information to know what packet streams to subscribe to. The TOPIC keyword can be used as many times as necessary to associate all needed topics.
|
@@ -53,6 +62,12 @@ MICROSERVICE:
|
|
53
62
|
required: true
|
54
63
|
description: Redis Topic to associate with the microservice
|
55
64
|
values: .+
|
65
|
+
example: |
|
66
|
+
MICROSERVICE EXAMPLE openc3-example
|
67
|
+
# Manually assigning topics is an advanced topic and requires
|
68
|
+
# intimate knowledge of the internal COSMOS data structures.
|
69
|
+
TOPIC DEFAULT__openc3_log_messages
|
70
|
+
TOPIC DEFAULT__TELEMETRY__EXAMPLE__STATUS
|
56
71
|
TARGET_NAME:
|
57
72
|
summary: Associate a OpenC3 target
|
58
73
|
description: OpenC3 target to associate with the microservice. For standard OpenC3 microservices such as decom_microservice this causes the target configuration to get loaded into the container for the microservice.
|
@@ -61,6 +76,9 @@ MICROSERVICE:
|
|
61
76
|
required: true
|
62
77
|
description: OpenC3 target to associate with the microservice
|
63
78
|
values: .+
|
79
|
+
example: |
|
80
|
+
MICROSERVICE EXAMPLE openc3-example
|
81
|
+
TARGET_NAME EXAMPLE
|
64
82
|
CMD:
|
65
83
|
summary: Command line to execute to run the microservice.
|
66
84
|
description: Command line to execute to run the microservice.
|
@@ -69,6 +87,9 @@ MICROSERVICE:
|
|
69
87
|
required: true
|
70
88
|
description: One or more arguments to exec to run the microservice.
|
71
89
|
values: .+
|
90
|
+
example: |
|
91
|
+
MICROSERVICE EXAMPLE openc3-example
|
92
|
+
CMD ruby example_target.rb
|
72
93
|
OPTION:
|
73
94
|
summary: Pass an option to the microservice
|
74
95
|
description: Generic key/value(s) options to pass to the microservice. These take the form of KEYWORD/PARAMS like a line in a OpenC3 configuration file. Multiple OPTION keywords can be used to pass multiple options to the microservice.
|
@@ -82,8 +103,8 @@ MICROSERVICE:
|
|
82
103
|
description: One or more values to associate with the option
|
83
104
|
values: .+
|
84
105
|
CONTAINER:
|
85
|
-
summary: Docker Container
|
86
|
-
description: Container to execute and run the microservice in.
|
106
|
+
summary: Docker Container
|
107
|
+
description: Container to execute and run the microservice in. Only used in COSMOS Enterprise Edition.
|
87
108
|
parameters:
|
88
109
|
- name: Args
|
89
110
|
required: false
|
@@ -112,6 +133,9 @@ MICROSERVICE:
|
|
112
133
|
required: false
|
113
134
|
description: Name of the secret store for stores with multipart keys
|
114
135
|
values: .*
|
136
|
+
example: |
|
137
|
+
SECRET ENV USERNAME ENV_USERNAME
|
138
|
+
SECRET FILE KEY "/tmp/DATA/cert"
|
115
139
|
ROUTE_PREFIX:
|
116
140
|
summary: Prefix of route
|
117
141
|
description: Prefix of route to the microservice to expose externally with Traefik
|
@@ -121,3 +145,6 @@ MICROSERVICE:
|
|
121
145
|
required: true
|
122
146
|
description: Route prefix. Must be unique across all scopes. Something like /myprefix
|
123
147
|
values: .*
|
148
|
+
example: |
|
149
|
+
MICROSERVICE CFDP CFDP
|
150
|
+
ROUTE_PREFIX /cfdp
|
data/ext/openc3/ext/crc/crc.c
CHANGED
@@ -18,7 +18,7 @@
|
|
18
18
|
# All changes Copyright 2022, OpenC3, Inc.
|
19
19
|
# All Rights Reserved
|
20
20
|
#
|
21
|
-
# This file may also be used under the terms of a commercial license
|
21
|
+
# This file may also be used under the terms of a commercial license
|
22
22
|
# if purchased from OpenC3, Inc.
|
23
23
|
*/
|
24
24
|
|
@@ -27,6 +27,7 @@
|
|
27
27
|
|
28
28
|
VALUE mOpenC3;
|
29
29
|
VALUE cCrc;
|
30
|
+
VALUE cCrc8;
|
30
31
|
VALUE cCrc16;
|
31
32
|
VALUE cCrc32;
|
32
33
|
VALUE cCrc64;
|
@@ -98,6 +99,83 @@ static unsigned long long bit_reverse_64(unsigned long long value)
|
|
98
99
|
((unsigned long long)BIT_REVERSE_TABLE[(value >> 56) & 0x00000000000000ffULL]);
|
99
100
|
}
|
100
101
|
|
102
|
+
/*
|
103
|
+
* Calculate a 8-bit CRC
|
104
|
+
*/
|
105
|
+
static VALUE crc8_calculate(int argc, VALUE *argv, VALUE self)
|
106
|
+
{
|
107
|
+
volatile VALUE param_data = Qnil;
|
108
|
+
volatile VALUE param_seed = Qnil;
|
109
|
+
unsigned char *data = NULL;
|
110
|
+
unsigned char *table = NULL;
|
111
|
+
int i = 0;
|
112
|
+
long length = 0;
|
113
|
+
unsigned char crc = 0;
|
114
|
+
|
115
|
+
switch (argc)
|
116
|
+
{
|
117
|
+
case 1:
|
118
|
+
Check_Type(argv[0], T_STRING);
|
119
|
+
param_data = argv[0];
|
120
|
+
param_seed = rb_ivar_get(self, id_ivar_seed);
|
121
|
+
break;
|
122
|
+
case 2:
|
123
|
+
Check_Type(argv[0], T_STRING);
|
124
|
+
param_data = argv[0];
|
125
|
+
if (argv[1] == Qnil)
|
126
|
+
{
|
127
|
+
param_seed = rb_ivar_get(self, id_ivar_seed);
|
128
|
+
}
|
129
|
+
else
|
130
|
+
{
|
131
|
+
param_seed = argv[1];
|
132
|
+
}
|
133
|
+
break;
|
134
|
+
default:
|
135
|
+
/* Invalid number of arguments given */
|
136
|
+
rb_raise(rb_eArgError, "wrong number of arguments (%d for 1..2)", argc);
|
137
|
+
break;
|
138
|
+
};
|
139
|
+
|
140
|
+
crc = NUM2UINT(param_seed);
|
141
|
+
data = (unsigned char *)RSTRING_PTR(param_data);
|
142
|
+
length = RSTRING_LEN(param_data);
|
143
|
+
table = (unsigned char *)RSTRING_PTR(rb_ivar_get(self, id_ivar_table));
|
144
|
+
|
145
|
+
if (RTEST(rb_ivar_get(self, id_ivar_reflect)))
|
146
|
+
{
|
147
|
+
for (i = 0; i < length; i++)
|
148
|
+
{
|
149
|
+
crc = (crc << 8) ^ table[(crc) ^ bit_reverse_8(data[i])];
|
150
|
+
}
|
151
|
+
|
152
|
+
if (RTEST(rb_ivar_get(self, id_ivar_xor)))
|
153
|
+
{
|
154
|
+
return UINT2NUM(bit_reverse_8(crc ^ 0xFF));
|
155
|
+
}
|
156
|
+
else
|
157
|
+
{
|
158
|
+
return UINT2NUM(bit_reverse_8(crc));
|
159
|
+
}
|
160
|
+
}
|
161
|
+
else
|
162
|
+
{
|
163
|
+
for (i = 0; i < length; i++)
|
164
|
+
{
|
165
|
+
crc = (crc << 8) ^ table[(crc) ^ data[i]];
|
166
|
+
}
|
167
|
+
|
168
|
+
if (RTEST(rb_ivar_get(self, id_ivar_xor)))
|
169
|
+
{
|
170
|
+
return UINT2NUM(crc ^ 0xFF);
|
171
|
+
}
|
172
|
+
else
|
173
|
+
{
|
174
|
+
return UINT2NUM(crc);
|
175
|
+
}
|
176
|
+
}
|
177
|
+
}
|
178
|
+
|
101
179
|
/*
|
102
180
|
* Calculate a 16-bit CRC
|
103
181
|
*/
|
@@ -343,6 +421,9 @@ void Init_crc()
|
|
343
421
|
|
344
422
|
cCrc = rb_define_class_under(mOpenC3, "Crc", rb_cObject);
|
345
423
|
|
424
|
+
cCrc8 = rb_define_class_under(mOpenC3, "Crc8", cCrc);
|
425
|
+
rb_define_method(cCrc8, "calc", crc8_calculate, -1);
|
426
|
+
|
346
427
|
cCrc16 = rb_define_class_under(mOpenC3, "Crc16", cCrc);
|
347
428
|
rb_define_method(cCrc16, "calc", crc16_calculate, -1);
|
348
429
|
|