ceedling 0.27.0 → 0.28.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (78) hide show
  1. checksums.yaml +4 -4
  2. data/assets/project_as_gem.yml +6 -0
  3. data/assets/project_with_guts.yml +6 -0
  4. data/assets/project_with_guts_gcov.yml +88 -0
  5. data/assets/test_example_file_boom.c +13 -0
  6. data/assets/test_example_file_success.c +14 -0
  7. data/bin/ceedling +57 -113
  8. data/ceedling.gemspec +1 -1
  9. data/config/test_environment.rb +0 -1
  10. data/examples/blinky/project.yml +1 -1
  11. data/examples/temp_sensor/project.yml +7 -1
  12. data/examples/temp_sensor/rakefile.rb +3 -1
  13. data/lib/ceedling/build_invoker_utils.rb +14 -2
  14. data/lib/ceedling/configurator.rb +3 -1
  15. data/lib/ceedling/configurator_builder.rb +6 -4
  16. data/lib/ceedling/configurator_setup.rb +5 -1
  17. data/lib/ceedling/defaults.rb +5 -2
  18. data/lib/ceedling/dependinator.rb +1 -1
  19. data/lib/ceedling/file_path_utils.rb +1 -2
  20. data/lib/ceedling/generator_test_results.rb +3 -2
  21. data/lib/ceedling/generator_test_results_sanity_checker.rb +4 -3
  22. data/lib/ceedling/project_file_loader.rb +26 -9
  23. data/lib/ceedling/rakefile.rb +9 -2
  24. data/lib/ceedling/release_invoker.rb +1 -1
  25. data/lib/ceedling/reportinator.rb +18 -1
  26. data/lib/ceedling/system_utils.rb +6 -1
  27. data/lib/ceedling/system_wrapper.rb +2 -1
  28. data/lib/ceedling/target_loader.rb +2 -2
  29. data/lib/ceedling/tasks_filesystem.rake +8 -2
  30. data/lib/ceedling/tool_executor_helper.rb +71 -22
  31. data/lib/ceedling/version.rb +1 -1
  32. data/license.txt +1 -1
  33. data/out.fail +21 -0
  34. data/plugins/command_hooks/lib/command_hooks.rb +2 -1
  35. data/plugins/gcov/config/defaults.yml +22 -0
  36. data/plugins/gcov/gcov.rake +79 -65
  37. data/plugins/gcov/lib/gcov.rb +25 -38
  38. data/plugins/gcov/lib/gcov_constants.rb +16 -0
  39. data/spec/build_invoker_utils_spec.rb +54 -0
  40. data/spec/file_finder_helper_spec.rb +53 -0
  41. data/spec/gcov/gcov_deployment_spec.rb +70 -0
  42. data/spec/gcov/gcov_test_cases_spec.rb +91 -0
  43. data/spec/generator_test_results_sanity_checker_spec.rb +88 -0
  44. data/spec/generator_test_results_spec.rb +102 -0
  45. data/spec/reportinator_spec.rb +19 -0
  46. data/spec/spec_system_helper.rb +67 -5
  47. data/spec/support/other_target.yml +0 -0
  48. data/spec/support/target.yml +0 -0
  49. data/spec/support/test_example.fail +21 -0
  50. data/spec/support/test_example.pass +21 -0
  51. data/spec/support/test_example_empty.pass +13 -0
  52. data/spec/support/test_example_ignore.pass +21 -0
  53. data/spec/support/test_example_mangled.pass +19 -0
  54. data/spec/system/deployment_spec.rb +25 -5
  55. data/spec/system_utils_spec.rb +56 -0
  56. data/spec/target_loader_spec.rb +30 -0
  57. data/spec/tool_executor_helper_spec.rb +310 -0
  58. data/vendor/cmock/scripts/create_makefile.rb +35 -12
  59. data/vendor/unity/src/unity_internals.h +3 -3
  60. metadata +62 -27
  61. data/assets/rakefile_as_gem.rb +0 -3
  62. data/assets/rakefile_with_guts.rb +0 -6
  63. data/vendor/constructor/History.rdoc +0 -19
  64. data/vendor/constructor/README.rdoc +0 -72
  65. data/vendor/constructor/Rakefile +0 -33
  66. data/vendor/constructor/homepage/Notes.txt +0 -27
  67. data/vendor/constructor/homepage/Rakefile +0 -15
  68. data/vendor/constructor/homepage/index.erb +0 -27
  69. data/vendor/constructor/homepage/index.html +0 -36
  70. data/vendor/constructor/homepage/page_header.graffle +0 -0
  71. data/vendor/constructor/homepage/page_header.html +0 -9
  72. data/vendor/constructor/homepage/page_header.png +0 -0
  73. data/vendor/constructor/homepage/sample_code.png +0 -0
  74. data/vendor/constructor/homepage/sample_code.rb +0 -12
  75. data/vendor/constructor/lib/constructor.rb +0 -127
  76. data/vendor/constructor/lib/constructor_struct.rb +0 -33
  77. data/vendor/constructor/specs/constructor_spec.rb +0 -407
  78. data/vendor/constructor/specs/constructor_struct_spec.rb +0 -84
@@ -5,7 +5,6 @@
5
5
  'test',
6
6
  'vendor/behaviors/lib',
7
7
  'vendor/hardmock/lib',
8
- 'vendor/constructor/lib',
9
8
  'vendor/deep_merge/lib',
10
9
  ].each do |dir|
11
10
  $LOAD_PATH.unshift( File.join( File.expand_path(File.dirname(__FILE__) + "/../"), dir) )
@@ -14,7 +14,7 @@
14
14
  #You'll have to specify these
15
15
  :environment:
16
16
  - :mcu: atmega328p
17
- - :f_cpu: 16000000UL
17
+ - :f_cpu: 16000000UL
18
18
  - :serial_port: COM8 #change this to the serial port you are using!!!
19
19
  - :objcopy: avr-objcopy
20
20
  # Uncomment these lines if you are using windows and don't have these tools in your path
@@ -60,11 +60,17 @@
60
60
  :tools_test_linker:
61
61
  :arguments:
62
62
  - -lm
63
+ :tools_gcov_linker:
64
+ :arguments:
65
+ - -lm
66
+ #:gcov:
67
+ # :html_report_type: basic
63
68
 
64
69
  :plugins:
65
70
  :load_paths:
66
71
  - vendor/ceedling/plugins
67
72
  :enabled:
68
73
  - stdout_pretty_tests_report
69
- #- stdout_ide_tests_report
74
+ - module_generator
75
+ - gcov
70
76
  ...
@@ -1,4 +1,6 @@
1
1
  PROJECT_CEEDLING_ROOT = "vendor/ceedling"
2
- load "#{PROJECT_CEEDLING_ROOT}/lib/ceedling/rakefile.rb"
2
+ load "#{PROJECT_CEEDLING_ROOT}/lib/ceedling.rb"
3
+
4
+ Ceedling.load_project
3
5
 
4
6
  task :default => %w[ test:all release ]
@@ -1,10 +1,22 @@
1
1
  require 'ceedling/constants'
2
2
 
3
-
3
+ ##
4
+ # Utilities for raiser and reporting errors during building.
4
5
  class BuildInvokerUtils
5
6
 
6
7
  constructor :configurator, :streaminator
7
-
8
+
9
+ ##
10
+ # Processes exceptions and tries to display a useful message for the user.
11
+ #
12
+ # ==== Attriboops...utes
13
+ #
14
+ # * _exception_: The exception given by a rescue statement.
15
+ # * _context_: A symbol representing where in the build the exception
16
+ # occurs.
17
+ # * _test_build_: A bool to signify if the exception occurred while building
18
+ # from test or source.
19
+ #
8
20
  def process_exception(exception, context, test_build=true)
9
21
  if (exception.message =~ /Don't know how to build task '(.+)'/i)
10
22
  error_header = "ERROR: Rake could not find file referenced in source"
@@ -107,7 +107,8 @@ class Configurator
107
107
  cmock[:unity_helper] = false if (cmock[:unity_helper].nil?)
108
108
 
109
109
  if (cmock[:unity_helper])
110
- cmock[:includes] << File.basename(cmock[:unity_helper])
110
+ cmock[:unity_helper] = [cmock[:unity_helper]] if cmock[:unity_helper].is_a? String
111
+ cmock[:includes] += cmock[:unity_helper].map{|helper| File.basename(helper) }
111
112
  cmock[:includes].uniq!
112
113
  end
113
114
 
@@ -327,6 +328,7 @@ class Configurator
327
328
 
328
329
  def insert_rake_plugins(plugins)
329
330
  plugins.each do |plugin|
331
+ # TODO needs a duplicate guard
330
332
  @project_config_hash[:project_rakefile_component_files] << plugin
331
333
  end
332
334
  end
@@ -392,10 +392,12 @@ class ConfiguratorBuilder
392
392
 
393
393
  # if we're using mocks & a unity helper is defined & that unity helper includes a source file component (not only a header of macros),
394
394
  # then link in the unity_helper object file too
395
- if ( in_hash[:project_use_mocks] and
396
- in_hash[:cmock_unity_helper] and
397
- @file_wrapper.exist?(in_hash[:cmock_unity_helper].ext(in_hash[:extension_source])) )
398
- objects << File.basename(in_hash[:cmock_unity_helper])
395
+ if ( in_hash[:project_use_mocks] and in_hash[:cmock_unity_helper] )
396
+ in_hash[:cmock_unity_helper].each do |helper|
397
+ if @file_wrapper.exist?(helper.ext(in_hash[:extension_source]))
398
+ objects << File.basename(helper)
399
+ end
400
+ end
399
401
  end
400
402
 
401
403
  # no build paths here so plugins can remap if necessary (i.e. path mapping happens at runtime)
@@ -76,7 +76,11 @@ class ConfiguratorSetup
76
76
  validation = []
77
77
 
78
78
  validation << @configurator_validator.validate_filepath(config, :project, :build_root)
79
- validation << @configurator_validator.validate_filepath(config, :cmock, :unity_helper) if config[:cmock][:unity_helper]
79
+ if config[:cmock][:unity_helper]
80
+ config[:cmock][:unity_helper].each do |path|
81
+ validation << @configurator_validator.validate_filepath_simple( path, :cmock, :unity_helper )
82
+ end
83
+ end
80
84
 
81
85
  config[:project][:options_paths].each do |path|
82
86
  validation << @configurator_validator.validate_filepath_simple( path, :project, :options_paths )
@@ -183,6 +183,8 @@ DEFAULT_RELEASE_LINKER_TOOL = {
183
183
  :arguments => [
184
184
  "\"${1}\"".freeze,
185
185
  "-o \"${2}\"".freeze,
186
+ "".freeze,
187
+ "${4}".freeze
186
188
  ].freeze
187
189
  }
188
190
 
@@ -311,7 +313,8 @@ DEFAULT_CEEDLING_CONFIG = {
311
313
 
312
314
  :cmock => {
313
315
  :vendor_path => CEEDLING_VENDOR,
314
- :defines => []
316
+ :defines => [],
317
+ :includes => []
315
318
  },
316
319
 
317
320
  :cexception => {
@@ -344,7 +347,7 @@ DEFAULT_CEEDLING_CONFIG = {
344
347
  :release_dependencies_generator => { :arguments => [] },
345
348
 
346
349
  :plugins => {
347
- :load_paths => CEEDLING_PLUGINS,
350
+ :load_paths => [], #XXX this is injected twice as of now so removed til better handling is found CEEDLING_PLUGINS,
348
351
  :enabled => [],
349
352
  }
350
353
  }.freeze
@@ -52,7 +52,7 @@ class Dependinator
52
52
  # if input configuration or ceedling changes, make sure these guys get rebuilt
53
53
  mocks_list.each do |mock_filepath|
54
54
  @rake_wrapper[mock_filepath].enhance( [@configurator.project_test_force_rebuild_filepath] ) if (@project_config_manager.test_config_changed)
55
- @rake_wrapper[mock_filepath].enhance( [@configurator.cmock_unity_helper] ) if (@configurator.cmock_unity_helper)
55
+ @rake_wrapper[mock_filepath].enhance( @configurator.cmock_unity_helper ) if (@configurator.cmock_unity_helper)
56
56
  end
57
57
  end
58
58
 
@@ -19,11 +19,10 @@ class FilePathUtils
19
19
 
20
20
  ######### class methods ##########
21
21
 
22
- # standardize path to use '/' path separator & begin with './' & have no trailing path separator
22
+ # standardize path to use '/' path separator & have no trailing path separator
23
23
  def self.standardize(path)
24
24
  path.strip!
25
25
  path.gsub!(/\\/, '/')
26
- path.gsub!(/^((\+|-):)?/, '')
27
26
  path.chomp!('/')
28
27
  return path
29
28
  end
@@ -1,7 +1,6 @@
1
1
  require 'rubygems'
2
2
  require 'rake' # for .ext()
3
3
  require 'ceedling/constants'
4
-
5
4
 
6
5
  class GeneratorTestResults
7
6
 
@@ -80,7 +79,9 @@ class GeneratorTestResults
80
79
 
81
80
  # collect up test results minus and extra output
82
81
  elements = (line.strip.split(':'))[1..-1]
83
- return {:test => elements[1], :line => elements[0].to_i, :message => (elements[3..-1].join(':')).strip}, stdout
82
+
83
+ return {:test => elements[1], :line => elements[0].to_i, :message => (elements[3..-1].join(':')).strip}, stdout if elements.size >= 3
84
+ return {:test => '???', :line => -1, :message => nil} #fallback safe option. TODO better handling
84
85
  end
85
86
 
86
87
  end
@@ -11,8 +11,9 @@ class GeneratorTestResultsSanityChecker
11
11
 
12
12
  # do no sanity checking if it's disabled
13
13
  return if (@configurator.sanity_checks == TestResultsSanityChecks::NONE)
14
-
15
- ceedling_ignores_count = results[:ignores].size
14
+ raise "results nil or empty" if results.nil? || results.empty?
15
+
16
+ ceedling_ignores_count = results[:ignores].size
16
17
  ceedling_failures_count = results[:failures].size
17
18
  ceedling_tests_summation = (ceedling_ignores_count + ceedling_failures_count + results[:successes].size)
18
19
 
@@ -45,7 +46,7 @@ class GeneratorTestResultsSanityChecker
45
46
 
46
47
  private
47
48
 
48
- def sanity_check_warning(file, message)
49
+ def sanity_check_warning(file, message)
49
50
  unless defined?(CEEDLING_IGNORE_SANITY_CHECK)
50
51
  notice = "\n" +
51
52
  "ERROR: Internal sanity check for test fixture '#{file.ext(@configurator.extension_executable)}' finds that #{message}\n" +
@@ -9,9 +9,11 @@ class ProjectFileLoader
9
9
 
10
10
  def setup
11
11
  @main_file = nil
12
+ @mixin_files = []
12
13
  @user_file = nil
13
14
 
14
15
  @main_project_filepath = ''
16
+ @mixin_project_filepaths = []
15
17
  @user_project_filepath = ''
16
18
  end
17
19
 
@@ -26,6 +28,16 @@ class ProjectFileLoader
26
28
  @user_project_filepath = DEFAULT_CEEDLING_USER_PROJECT_FILE
27
29
  end
28
30
 
31
+ # next check for mixin project files by looking for environment variable
32
+ mixin_filepaths = @system_wrapper.env_get('CEEDLING_MIXIN_PROJECT_FILES')
33
+ if ( not mixin_filepaths.nil? )
34
+ mixin_filepaths.split(File::PATH_SEPARATOR).each do |filepath|
35
+ if ( @file_wrapper.exist?(filepath) )
36
+ @mixin_project_filepaths.push(filepath)
37
+ end
38
+ end
39
+ end
40
+
29
41
  # next check for main project file by looking for environment variable and then default location on disk;
30
42
  # blow up if we don't find this guy -- like, he's so totally important
31
43
  main_filepath = @system_wrapper.env_get('CEEDLING_MAIN_PROJECT_FILE')
@@ -42,6 +54,9 @@ class ProjectFileLoader
42
54
  end
43
55
 
44
56
  @main_file = File.basename( @main_project_filepath )
57
+ @mixin_project_filepaths.each do |filepath|
58
+ @mixin_files.push(File.basename( filepath ))
59
+ end
45
60
  @user_file = File.basename( @user_project_filepath ) if ( not @user_project_filepath.empty? )
46
61
  end
47
62
 
@@ -64,16 +79,18 @@ class ProjectFileLoader
64
79
  end
65
80
 
66
81
  def load_project_config
67
- config_hash = {}
68
- # if there's no user project file, then just provide hash from project file
69
- if (@user_project_filepath.empty?)
70
- config_hash = @yaml_wrapper.load(@main_project_filepath)
71
- # if there is a user project file, load it too and merge it on top of the project file,
72
- # superseding anything that's common between them
73
- else
74
- main_hash = @yaml_wrapper.load(@main_project_filepath)
82
+ config_hash = @yaml_wrapper.load(@main_project_filepath)
83
+
84
+ # if there are mixin project files, then use them
85
+ @mixin_project_filepaths.each do |filepath|
86
+ mixin = @yaml_wrapper.load(filepath)
87
+ config_hash = yaml_merger( config_hash, mixin )
88
+ end
89
+
90
+ # if there's a user project file, then use it
91
+ if ( not @user_project_filepath.empty? )
75
92
  user_hash = @yaml_wrapper.load(@user_project_filepath)
76
- config_hash = yaml_merger( main_hash, user_hash )
93
+ config_hash = yaml_merger( config_hash, user_hash )
77
94
  end
78
95
 
79
96
  return config_hash
@@ -9,12 +9,14 @@ CEEDLING_RELEASE = File.join(CEEDLING_ROOT, 'release')
9
9
  $LOAD_PATH.unshift( CEEDLING_LIB )
10
10
  $LOAD_PATH.unshift( File.join(CEEDLING_VENDOR, 'unity/auto') )
11
11
  $LOAD_PATH.unshift( File.join(CEEDLING_VENDOR, 'diy/lib') )
12
- $LOAD_PATH.unshift( File.join(CEEDLING_VENDOR, 'constructor/lib') )
13
12
  $LOAD_PATH.unshift( File.join(CEEDLING_VENDOR, 'cmock/lib') )
14
13
  $LOAD_PATH.unshift( File.join(CEEDLING_VENDOR, 'deep_merge/lib') )
15
14
 
16
15
  require 'rake'
17
16
 
17
+ #Let's make sure we remember the task descriptions in case we need them
18
+ Rake::TaskManager.record_task_metadata = true
19
+
18
20
  require 'diy'
19
21
  require 'constructor'
20
22
 
@@ -58,6 +60,9 @@ verbose(false)
58
60
 
59
61
  # end block always executed following rake run
60
62
  END {
63
+ $stdout.flush unless $stdout.nil?
64
+ $stderr.flush unless $stderr.nil?
65
+
61
66
  # cache our input configurations to use in comparison upon next execution
62
67
  @ceedling[:cacheinator].cache_test_config( @ceedling[:setupinator].config_hash ) if (@ceedling[:task_invoker].test_invoked?)
63
68
  @ceedling[:cacheinator].cache_release_config( @ceedling[:setupinator].config_hash ) if (@ceedling[:task_invoker].release_invoked?)
@@ -73,6 +78,8 @@ END {
73
78
  # tell all our plugins the build is done and process results
74
79
  @ceedling[:plugin_manager].post_build
75
80
  @ceedling[:plugin_manager].print_plugin_failures
76
- exit(1) if (@ceedling[:plugin_manager].plugins_failed? && !@ceedling[:setupinator].config_hash[:graceful_fail])
81
+ exit(1) if (@ceedling[:plugin_manager].plugins_failed? && !@ceedling[:setupinator].config_hash[:graceful_fail])
82
+ else
83
+ puts "ERROR: Ceedling Failed"
77
84
  end
78
85
  }
@@ -64,7 +64,7 @@ class ReleaseInvoker
64
64
  end
65
65
 
66
66
  def sort_objects_and_libraries(both)
67
- extension = "\\" + (EXTENSION_SUBPROJECTS || ".LIBRARY")
67
+ extension = "\\" + ((defined? EXTENSION_SUBPROJECTS) ? EXTENSION_SUBPROJECTS : ".LIBRARY")
68
68
  sorted_objects = both.group_by {|v| v.match(/.+#{extension}$/) ? :libraries : :objects }
69
69
  libraries = sorted_objects[:libraries] || []
70
70
  objects = sorted_objects[:objects] || []
@@ -1,6 +1,23 @@
1
-
1
+ ##
2
+ # Pretifies reports
2
3
  class Reportinator
3
4
 
5
+ ##
6
+ # Generates a banner for a message based on the length of the message or a
7
+ # given width.
8
+ # ==== Attributes
9
+ #
10
+ # * _message_: The message to put.
11
+ # * _width_: The width of the message. If nil the size of the banner is
12
+ # determined by the length of the message.
13
+ #
14
+ # ==== Examples
15
+ #
16
+ # rp = Reportinator.new
17
+ # rp.generate_banner("Hello world!") => "------------\nHello world!\n------------\n"
18
+ # rp.generate_banner("Hello world!", 3) => "---\nHello world!\n---\n"
19
+ #
20
+ #
4
21
  def generate_banner(message, width=nil)
5
22
  dash_count = ((width.nil?) ? message.strip.length : width)
6
23
  return "#{'-' * dash_count}\n#{message}\n#{'-' * dash_count}\n"
@@ -6,14 +6,20 @@ class Object
6
6
  end
7
7
 
8
8
 
9
+ ##
10
+ # Class containing system utility funcions.
9
11
  class SystemUtils
10
12
 
11
13
  constructor :system_wrapper
12
14
 
15
+ ##
16
+ # Sets up the class.
13
17
  def setup
14
18
  @tcsh_shell = nil
15
19
  end
16
20
 
21
+ ##
22
+ # Checks the system shell to see if it a tcsh shell.
17
23
  def tcsh_shell?
18
24
  # once run a single time, return state determined at that execution
19
25
  return @tcsh_shell if not @tcsh_shell.nil?
@@ -28,5 +34,4 @@ class SystemUtils
28
34
 
29
35
  return @tcsh_shell
30
36
  end
31
-
32
37
  end
@@ -68,7 +68,8 @@ class SystemWrapper
68
68
  end
69
69
 
70
70
  def ruby_success
71
- return ($exit_code == 0) && ($!.nil? || $!.is_a?(SystemExit) && $!.success?)
71
+ # We are successful if we've never had an exit code that went boom (either because it's empty or it was 0)
72
+ return ($exit_code.nil? || ($exit_code == 0)) && ($!.nil? || $!.is_a?(SystemExit) && $!.success?)
72
73
  end
73
74
 
74
75
  def constants_include?(item)
@@ -13,10 +13,10 @@ module TargetLoader
13
13
 
14
14
  targets = config[:targets]
15
15
  unless targets[:targets_directory]
16
- raise NoDirectory("No targets directory specified.")
16
+ raise NoDirectory.new("No targets directory specified.")
17
17
  end
18
18
  unless targets[:default_target]
19
- raise NoDefault("No default target specified.")
19
+ raise NoDefault.new("No default target specified.")
20
20
  end
21
21
 
22
22
  target_path = lambda {|name| File.join(targets[:targets_directory], name + ".yml")}
@@ -33,14 +33,20 @@ task(:clean) do
33
33
  if (not @ceedling[:task_invoker].invoked?(/^clobber$/))
34
34
  @ceedling[:streaminator].stdout_puts("\nCleaning build artifacts...\n(For large projects, this task may take a long time to complete)\n\n")
35
35
  end
36
- CLEAN.each { |fn| REMOVE_FILE_PROC.call(fn) }
36
+ begin
37
+ CLEAN.each { |fn| REMOVE_FILE_PROC.call(fn) }
38
+ rescue
39
+ end
37
40
  end
38
41
 
39
42
  # redefine clobber so we can override how it advertises itself
40
43
  desc "Delete all generated files (and build artifacts)."
41
44
  task(:clobber => [:clean]) do
42
45
  @ceedling[:streaminator].stdout_puts("\nClobbering all generated files...\n(For large projects, this task may take a long time to complete)\n\n")
43
- CLOBBER.each { |fn| REMOVE_FILE_PROC.call(fn) }
46
+ begin
47
+ CLOBBER.each { |fn| REMOVE_FILE_PROC.call(fn) }
48
+ rescue
49
+ end
44
50
  end
45
51
 
46
52
 
@@ -1,25 +1,41 @@
1
1
  require 'ceedling/constants' # for Verbosity enumeration & $stderr redirect enumeration
2
2
 
3
+ ##
4
+ # Helper functions for the tool executor
3
5
  class ToolExecutorHelper
4
6
 
5
7
  constructor :streaminator, :system_utils, :system_wrapper
6
8
 
9
+ ##
10
+ # Returns the stderr redirection based on the config and logging.
11
+ # ==== Attributes
12
+ #
13
+ # * _tool_config_: A hash containing config information.
14
+ # * _logging_: A boolean representing if logging is enabled or not.
15
+ #
7
16
  def stderr_redirection(tool_config, logging)
8
17
  # if there's no logging enabled, return :stderr_redirect unmodified
9
18
  return tool_config[:stderr_redirect] if (not logging)
10
-
19
+
11
20
  # if there is logging enabled but the redirect is a custom value (not enum), return the custom string
12
21
  return tool_config[:stderr_redirect] if (tool_config[:stderr_redirect].class == String)
13
-
22
+
14
23
  # if logging is enabled but there's no custom string, return the AUTO enumeration so $stderr goes into the log
15
24
  return StdErrRedirect::AUTO
16
25
  end
17
26
 
27
+
28
+ ##
29
+ # Returns the background execution prepend based on the config.
30
+ # ==== Attributes
31
+ #
32
+ # * _tool_config_: A hash containing config information.
33
+ #
18
34
  def background_exec_cmdline_prepend(tool_config)
19
- return nil if (tool_config[:background_exec].nil?)
20
-
35
+ return nil if (tool_config.nil? || tool_config[:background_exec].nil?)
36
+
21
37
  config_exec = tool_config[:background_exec]
22
-
38
+
23
39
  if ((config_exec == BackgroundExec::AUTO) and (@system_wrapper.windows?))
24
40
  return 'start'
25
41
  end
@@ -31,26 +47,37 @@ class ToolExecutorHelper
31
47
  return nil
32
48
  end
33
49
 
50
+
51
+ ##
52
+ # Modifies an executables path based on platform.
53
+ # ==== Attributes
54
+ #
55
+ # * _executable_: The executable's path.
56
+ #
34
57
  def osify_path_separators(executable)
35
58
  return executable.gsub(/\//, '\\') if (@system_wrapper.windows?)
36
59
  return executable
37
60
  end
38
-
61
+
62
+ ##
63
+ # Returns the stderr redirect append based on the config.
64
+ # ==== Attributes
65
+ #
66
+ # * _tool_config_: A hash containing config information.
67
+ #
39
68
  def stderr_redirect_cmdline_append(tool_config)
40
- return nil if (tool_config[:stderr_redirect].nil?)
41
-
69
+ return nil if (tool_config.nil? || tool_config[:stderr_redirect].nil?)
70
+
42
71
  config_redirect = tool_config[:stderr_redirect]
43
72
  redirect = StdErrRedirect::NONE
44
-
73
+
45
74
  if (config_redirect == StdErrRedirect::AUTO)
46
75
  if (@system_wrapper.windows?)
47
76
  redirect = StdErrRedirect::WIN
77
+ elsif (@system_utils.tcsh_shell?)
78
+ redirect = StdErrRedirect::TCSH
48
79
  else
49
- if (@system_utils.tcsh_shell?)
50
- redirect = StdErrRedirect::TCSH
51
- else
52
- redirect = StdErrRedirect::UNIX
53
- end
80
+ redirect = StdErrRedirect::UNIX
54
81
  end
55
82
  end
56
83
 
@@ -64,11 +91,17 @@ class ToolExecutorHelper
64
91
  end
65
92
  end
66
93
 
94
+ ##
95
+ # Returns the background execution append based on the config.
96
+ # ==== Attributes
97
+ #
98
+ # * _tool_config_: A hash containing config information.
99
+ #
67
100
  def background_exec_cmdline_append(tool_config)
68
- return nil if (tool_config[:background_exec].nil?)
101
+ return nil if (tool_config.nil? || tool_config[:background_exec].nil?)
69
102
 
70
103
  config_exec = tool_config[:background_exec]
71
-
104
+
72
105
  # if :auto & windows, then we already prepended 'start' and should append nothing
73
106
  return nil if ((config_exec == BackgroundExec::AUTO) and (@system_wrapper.windows?))
74
107
 
@@ -77,26 +110,43 @@ class ToolExecutorHelper
77
110
 
78
111
  # if explicitly Unix, then append '&'
79
112
  return '&' if (config_exec == BackgroundExec::UNIX)
80
-
113
+
114
+ # * _command_str_: A hash containing config information.
81
115
  # all other cases, including :none, :win, & anything unrecognized, append nothing
82
116
  return nil
83
117
  end
84
118
 
85
- # if command succeeded and we have verbosity cranked up, spill our guts
119
+ ##
120
+ # Outputs success results if command succeeded and we have verbosity cranked up.
121
+ # ==== Attributes
122
+ #
123
+ # * _command_str_: The command ran.
124
+ # * _shell_results_: The outputs of the command including exit code and
125
+ # output.
126
+ # * _boom_: A boolean representing if a non zero result is erroneous.
127
+ #
86
128
  def print_happy_results(command_str, shell_result, boom=true)
87
129
  if ((shell_result[:exit_code] == 0) or ((shell_result[:exit_code] != 0) and not boom))
88
130
  output = "> Shell executed command:\n"
89
- output += "#{command_str}\n"
131
+ output += "'#{command_str}'\n"
90
132
  output += "> Produced output:\n" if (not shell_result[:output].empty?)
91
133
  output += "#{shell_result[:output].strip}\n" if (not shell_result[:output].empty?)
92
134
  output += "> And exited with status: [#{shell_result[:exit_code]}].\n" if (shell_result[:exit_code] != 0)
93
135
  output += "\n"
94
-
136
+
95
137
  @streaminator.stdout_puts(output, Verbosity::OBNOXIOUS)
96
138
  end
97
139
  end
98
140
 
99
- # if command failed and we have verbosity set to minimum error level, spill our guts
141
+ ##
142
+ # Outputs failures results if command failed and we have verbosity set to minimum error level.
143
+ # ==== Attributes
144
+ #
145
+ # * _command_str_: The command ran.
146
+ # * _shell_results_: The outputs of the command including exit code and
147
+ # output.
148
+ # * _boom_: A boolean representing if a non zero result is erroneous.
149
+ #
100
150
  def print_error_results(command_str, shell_result, boom=true)
101
151
  if ((shell_result[:exit_code] != 0) and boom)
102
152
  output = "ERROR: Shell command failed.\n"
@@ -111,5 +161,4 @@ class ToolExecutorHelper
111
161
  @streaminator.stderr_puts(output, Verbosity::ERRORS)
112
162
  end
113
163
  end
114
-
115
164
  end