contrast-agent 4.6.0 → 4.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.gitmodules +1 -1
- data/Rakefile +1 -2
- data/ext/build_funchook.rb +3 -3
- data/ext/extconf_common.rb +1 -5
- data/lib/contrast/agent/assess.rb +1 -1
- data/lib/contrast/agent/assess/contrast_object.rb +2 -2
- data/lib/contrast/agent/assess/events/event_factory.rb +2 -1
- data/lib/contrast/agent/assess/policy/dynamic_source_factory.rb +6 -3
- data/lib/contrast/agent/assess/policy/patcher.rb +10 -17
- data/lib/contrast/agent/assess/policy/policy_node.rb +25 -33
- data/lib/contrast/agent/assess/policy/preshift.rb +3 -1
- data/lib/contrast/agent/assess/policy/propagation_method.rb +6 -15
- data/lib/contrast/agent/assess/policy/propagation_node.rb +19 -8
- data/lib/contrast/agent/assess/policy/propagator/center.rb +2 -1
- data/lib/contrast/agent/assess/policy/propagator/insert.rb +3 -1
- data/lib/contrast/agent/assess/policy/propagator/match_data.rb +2 -1
- data/lib/contrast/agent/assess/policy/propagator/select.rb +2 -12
- data/lib/contrast/agent/assess/policy/propagator/split.rb +3 -7
- data/lib/contrast/agent/assess/policy/propagator/substitution.rb +1 -7
- data/lib/contrast/agent/assess/policy/propagator/trim.rb +3 -15
- data/lib/contrast/agent/assess/policy/rewriter_patch.rb +6 -3
- data/lib/contrast/agent/assess/policy/source_method.rb +6 -6
- data/lib/contrast/agent/assess/policy/source_validation/source_validation.rb +1 -3
- data/lib/contrast/agent/assess/policy/trigger/reflected_xss.rb +5 -1
- data/lib/contrast/agent/assess/policy/trigger_method.rb +6 -15
- data/lib/contrast/agent/assess/policy/trigger_node.rb +2 -1
- data/lib/contrast/agent/assess/policy/trigger_validation/redos_validator.rb +4 -3
- data/lib/contrast/agent/assess/policy/trigger_validation/ssrf_validator.rb +1 -2
- data/lib/contrast/agent/assess/policy/trigger_validation/xss_validator.rb +1 -8
- data/lib/contrast/agent/assess/property/evented.rb +8 -5
- data/lib/contrast/agent/assess/rule/provider/hardcoded_key.rb +11 -5
- data/lib/contrast/agent/assess/rule/provider/hardcoded_password.rb +4 -1
- data/lib/contrast/agent/assess/rule/provider/hardcoded_value_rule.rb +3 -5
- data/lib/contrast/agent/class_reopener.rb +3 -1
- data/lib/contrast/agent/disable_reaction.rb +1 -3
- data/lib/contrast/agent/exclusion_matcher.rb +5 -11
- data/lib/contrast/agent/inventory/dependencies.rb +2 -0
- data/lib/contrast/agent/middleware.rb +3 -5
- data/lib/contrast/agent/module_data.rb +3 -3
- data/lib/contrast/agent/patching/policy/after_load_patcher.rb +6 -5
- data/lib/contrast/agent/patching/policy/method_policy.rb +6 -2
- data/lib/contrast/agent/patching/policy/module_policy.rb +14 -7
- data/lib/contrast/agent/patching/policy/patch.rb +11 -16
- data/lib/contrast/agent/patching/policy/patch_status.rb +6 -7
- data/lib/contrast/agent/patching/policy/patcher.rb +15 -12
- data/lib/contrast/agent/patching/policy/policy_node.rb +14 -4
- data/lib/contrast/agent/patching/policy/trigger_node.rb +21 -8
- data/lib/contrast/agent/protect/policy/applies_command_injection_rule.rb +1 -1
- data/lib/contrast/agent/protect/policy/applies_deserialization_rule.rb +1 -1
- data/lib/contrast/agent/protect/policy/applies_no_sqli_rule.rb +1 -1
- data/lib/contrast/agent/protect/policy/applies_path_traversal_rule.rb +2 -3
- data/lib/contrast/agent/protect/policy/applies_sqli_rule.rb +1 -1
- data/lib/contrast/agent/protect/policy/applies_xxe_rule.rb +5 -9
- data/lib/contrast/agent/protect/policy/rule_applicator.rb +5 -5
- data/lib/contrast/agent/protect/rule/base.rb +13 -16
- data/lib/contrast/agent/protect/rule/base_service.rb +9 -5
- data/lib/contrast/agent/protect/rule/cmd_injection.rb +14 -18
- data/lib/contrast/agent/protect/rule/deserialization.rb +6 -13
- data/lib/contrast/agent/protect/rule/http_method_tampering.rb +3 -14
- data/lib/contrast/agent/protect/rule/no_sqli.rb +6 -2
- data/lib/contrast/agent/protect/rule/no_sqli/mongo_no_sql_scanner.rb +1 -3
- data/lib/contrast/agent/protect/rule/path_traversal.rb +5 -5
- data/lib/contrast/agent/protect/rule/sqli.rb +1 -1
- data/lib/contrast/agent/protect/rule/unsafe_file_upload.rb +1 -1
- data/lib/contrast/agent/protect/rule/xss.rb +1 -1
- data/lib/contrast/agent/protect/rule/xxe.rb +5 -12
- data/lib/contrast/agent/protect/rule/xxe/entity_wrapper.rb +1 -2
- data/lib/contrast/agent/reaction_processor.rb +11 -10
- data/lib/contrast/agent/request.rb +23 -23
- data/lib/contrast/agent/request_context.rb +9 -14
- data/lib/contrast/agent/rewriter.rb +5 -3
- data/lib/contrast/agent/service_heartbeat.rb +2 -3
- data/lib/contrast/agent/tracepoint_hook.rb +1 -1
- data/lib/contrast/agent/version.rb +1 -1
- data/lib/contrast/api/communication/response_processor.rb +2 -4
- data/lib/contrast/api/communication/service_lifecycle.rb +4 -2
- data/lib/contrast/api/communication/socket_client.rb +8 -21
- data/lib/contrast/api/communication/speedracer.rb +3 -7
- data/lib/contrast/api/decorators/application_startup.rb +6 -2
- data/lib/contrast/api/decorators/library.rb +8 -6
- data/lib/contrast/api/decorators/message.rb +3 -3
- data/lib/contrast/api/decorators/trace_event.rb +3 -1
- data/lib/contrast/api/decorators/trace_event_object.rb +1 -3
- data/lib/contrast/api/decorators/trace_taint_range_tags.rb +1 -6
- data/lib/contrast/components/agent.rb +9 -4
- data/lib/contrast/components/app_context.rb +6 -6
- data/lib/contrast/components/config.rb +2 -1
- data/lib/contrast/components/contrast_service.rb +7 -8
- data/lib/contrast/components/interface.rb +3 -2
- data/lib/contrast/components/sampling.rb +8 -2
- data/lib/contrast/components/settings.rb +4 -2
- data/lib/contrast/config/assess_rules_configuration.rb +1 -3
- data/lib/contrast/config/base_configuration.rb +4 -5
- data/lib/contrast/config/exception_configuration.rb +1 -5
- data/lib/contrast/config/heap_dump_configuration.rb +12 -6
- data/lib/contrast/config/logger_configuration.rb +1 -5
- data/lib/contrast/configuration.rb +3 -14
- data/lib/contrast/extension/assess/array.rb +1 -6
- data/lib/contrast/extension/assess/erb.rb +1 -7
- data/lib/contrast/extension/assess/eval_trigger.rb +2 -6
- data/lib/contrast/extension/assess/exec_trigger.rb +3 -9
- data/lib/contrast/extension/assess/fiber.rb +2 -12
- data/lib/contrast/extension/assess/kernel.rb +2 -9
- data/lib/contrast/extension/assess/marshal.rb +2 -6
- data/lib/contrast/extension/assess/regexp.rb +1 -6
- data/lib/contrast/extension/assess/string.rb +3 -1
- data/lib/contrast/extension/kernel.rb +4 -2
- data/lib/contrast/framework/manager.rb +1 -2
- data/lib/contrast/framework/rack/patch/session_cookie.rb +5 -18
- data/lib/contrast/framework/rack/patch/support.rb +6 -4
- data/lib/contrast/framework/rails/patch/assess_configuration.rb +7 -2
- data/lib/contrast/framework/rails/patch/support.rb +4 -2
- data/lib/contrast/framework/rails/rewrite/action_controller_railties_helper_inherited.rb +4 -1
- data/lib/contrast/framework/rails/rewrite/active_record_attribute_methods_read.rb +2 -0
- data/lib/contrast/framework/rails/rewrite/active_record_named.rb +2 -0
- data/lib/contrast/framework/rails/rewrite/active_record_time_zone_inherited.rb +2 -0
- data/lib/contrast/framework/rails/support.rb +2 -2
- data/lib/contrast/framework/sinatra/support.rb +3 -1
- data/lib/contrast/funchook/funchook.rb +1 -5
- data/lib/contrast/logger/application.rb +12 -9
- data/lib/contrast/logger/format.rb +2 -5
- data/lib/contrast/logger/log.rb +4 -3
- data/lib/contrast/logger/request.rb +1 -2
- data/lib/contrast/security_exception.rb +1 -1
- data/lib/contrast/tasks/service.rb +5 -1
- data/lib/contrast/utils/assess/tracking_util.rb +1 -2
- data/lib/contrast/utils/class_util.rb +0 -8
- data/lib/contrast/utils/hash_digest.rb +2 -5
- data/lib/contrast/utils/io_util.rb +1 -1
- data/lib/contrast/utils/job_servers_running.rb +9 -4
- data/lib/contrast/utils/os.rb +2 -1
- data/lib/contrast/utils/ruby_ast_rewriter.rb +2 -1
- data/ruby-agent.gemspec +13 -14
- data/sonar-project.properties +9 -0
- metadata +37 -36
|
@@ -52,9 +52,7 @@ module Contrast
|
|
|
52
52
|
tmp = []
|
|
53
53
|
tmp << obj_string[0, UNTRUNCATED_PORTION_LENGTH]
|
|
54
54
|
tmp << ELLIPSIS
|
|
55
|
-
tmp << obj_string[
|
|
56
|
-
obj_string.length - UNTRUNCATED_PORTION_LENGTH,
|
|
57
|
-
UNTRUNCATED_PORTION_LENGTH]
|
|
55
|
+
tmp << obj_string[obj_string.length - UNTRUNCATED_PORTION_LENGTH, UNTRUNCATED_PORTION_LENGTH]
|
|
58
56
|
tmp.join
|
|
59
57
|
end
|
|
60
58
|
end
|
|
@@ -97,12 +97,7 @@ module Contrast
|
|
|
97
97
|
DATABASE_WRITE
|
|
98
98
|
].cs__freeze
|
|
99
99
|
|
|
100
|
-
VALID_SOURCE_TAGS = %w[
|
|
101
|
-
NO_NEWLINES
|
|
102
|
-
UNTRUSTED
|
|
103
|
-
CROSS_SITE
|
|
104
|
-
LIMITED_CHARS
|
|
105
|
-
].cs__freeze
|
|
100
|
+
VALID_SOURCE_TAGS = %w[NO_NEWLINES UNTRUSTED CROSS_SITE LIMITED_CHARS].cs__freeze
|
|
106
101
|
end
|
|
107
102
|
end
|
|
108
103
|
end
|
|
@@ -69,8 +69,10 @@ module Contrast
|
|
|
69
69
|
def exception_control
|
|
70
70
|
@_exception_control ||= {
|
|
71
71
|
enable: true?(CONFIG.root.agent.ruby.exceptions.capture),
|
|
72
|
-
status:
|
|
73
|
-
|
|
72
|
+
status:
|
|
73
|
+
CONFIG.root.agent.ruby.exceptions.override_status || 403,
|
|
74
|
+
message:
|
|
75
|
+
CONFIG.root.agent.ruby.exceptions.override_message || Contrast::Utils::ObjectShare::OVERRIDE_MESSAGE
|
|
74
76
|
}
|
|
75
77
|
end
|
|
76
78
|
|
|
@@ -80,8 +82,9 @@ module Contrast
|
|
|
80
82
|
loaded_module_name.start_with?(*CONFIG.root.agent.ruby.uninstrument_namespace)
|
|
81
83
|
end
|
|
82
84
|
|
|
85
|
+
# Insert ourselves into the application, keeping our middleware at the outermost layer of the onion
|
|
83
86
|
def insert_middleware app
|
|
84
|
-
app.middleware.insert_before 0, Contrast::Agent::Middleware
|
|
87
|
+
app.middleware.insert_before 0, Contrast::Agent::Middleware
|
|
85
88
|
end
|
|
86
89
|
|
|
87
90
|
def enable_tracepoint
|
|
@@ -94,7 +97,9 @@ module Contrast
|
|
|
94
97
|
# Ruby exposed the C method for interpolation in version 2.6.0, meaning
|
|
95
98
|
# we can attempt to patch using Funchook for that version and later.
|
|
96
99
|
def interpolation_patch_possible?
|
|
97
|
-
|
|
100
|
+
if @_interpolation_patch_possible.nil?
|
|
101
|
+
@_interpolation_patch_possible = Gem::Version.new(RUBY_VERSION) >= INTERPOLATION_HOOKABLE_VERSION
|
|
102
|
+
end
|
|
98
103
|
@_interpolation_patch_possible
|
|
99
104
|
end
|
|
100
105
|
|
|
@@ -37,9 +37,9 @@ module Contrast
|
|
|
37
37
|
end
|
|
38
38
|
end
|
|
39
39
|
|
|
40
|
-
def
|
|
41
|
-
@
|
|
42
|
-
tmp = CONFIG.root.application.name
|
|
40
|
+
def app_name
|
|
41
|
+
@_app_name ||= begin
|
|
42
|
+
tmp = CONFIG.root.application.name # rubocop:disable Security/Module/Name
|
|
43
43
|
tmp = Contrast::Agent.framework_manager.app_name unless Contrast::Utils::StringUtils.present?(tmp)
|
|
44
44
|
tmp = File.basename(Dir.pwd) unless Contrast::Utils::StringUtils.present?(tmp)
|
|
45
45
|
Contrast::Utils::StringUtils.truncate(tmp, DEFAULT_APP_NAME)
|
|
@@ -59,7 +59,7 @@ module Contrast
|
|
|
59
59
|
|
|
60
60
|
def server_name
|
|
61
61
|
@_server_name ||= begin
|
|
62
|
-
tmp = CONFIG.root.server.name
|
|
62
|
+
tmp = CONFIG.root.server.name # rubocop:disable Security/Module/Name
|
|
63
63
|
tmp = Socket.gethostname unless Contrast::Utils::StringUtils.present?(tmp)
|
|
64
64
|
tmp = Contrast::Utils::StringUtils.force_utf8(tmp)
|
|
65
65
|
Contrast::Utils::StringUtils.truncate(tmp, DEFAULT_SERVER_NAME)
|
|
@@ -88,7 +88,7 @@ module Contrast
|
|
|
88
88
|
server_name: msg.server_name,
|
|
89
89
|
server_path: msg.server_path,
|
|
90
90
|
server_type: msg.server_type,
|
|
91
|
-
application_name:
|
|
91
|
+
application_name: app_name,
|
|
92
92
|
application_path: path,
|
|
93
93
|
application_language: Contrast::Utils::ObjectShare::RUBY)
|
|
94
94
|
|
|
@@ -108,7 +108,7 @@ module Contrast
|
|
|
108
108
|
end
|
|
109
109
|
|
|
110
110
|
def client_id
|
|
111
|
-
@_client_id ||= [
|
|
111
|
+
@_client_id ||= [app_name, pgid].join('-')
|
|
112
112
|
end
|
|
113
113
|
|
|
114
114
|
def instrument_middleware_stack?
|
|
@@ -56,7 +56,8 @@ module Contrast
|
|
|
56
56
|
|
|
57
57
|
private
|
|
58
58
|
|
|
59
|
-
SESSION_VARIABLES =
|
|
59
|
+
SESSION_VARIABLES = 'Invalid configuration. '\
|
|
60
|
+
"Setting both application.session_id and application.session_metadata is not allowed.\n"
|
|
60
61
|
def validate log: false
|
|
61
62
|
# The config has information about how to construct the logger.
|
|
62
63
|
# If the config is invalid, and you want to know about it, then
|
|
@@ -25,14 +25,13 @@ module Contrast
|
|
|
25
25
|
def use_bundled_service?
|
|
26
26
|
# Validates the config to decide if it's suitable for starting
|
|
27
27
|
# the bundled service
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
end
|
|
28
|
+
|
|
29
|
+
# Requirement says "must be true" but that
|
|
30
|
+
# should be "must not be false" -- oops.
|
|
31
|
+
@_use_bundled_service ||= !false?(CONFIG.root.agent.start_bundled_service) &&
|
|
32
|
+
# Either a valid host or a valid socket
|
|
33
|
+
# Path validity is the service's problem
|
|
34
|
+
(LOCALHOST.match?(host) || !!socket_path)
|
|
36
35
|
end
|
|
37
36
|
|
|
38
37
|
def host
|
|
@@ -134,7 +134,7 @@ module Contrast
|
|
|
134
134
|
if (mods = component_map[sym]) # rubocop:disable Style/GuardClause
|
|
135
135
|
# We may support multiple components via one access request.
|
|
136
136
|
mods.each do |m|
|
|
137
|
-
name = Contrast::Components.component_const_name(m.
|
|
137
|
+
name = Contrast::Components.component_const_name(m.cs__name)
|
|
138
138
|
cs__const_set(name, m::COMPONENT_INTERFACE) if m.cs__const_defined?(:COMPONENT_INTERFACE)
|
|
139
139
|
include m::InstanceMethods if m.cs__const_defined?(:InstanceMethods, false)
|
|
140
140
|
extend m::ClassMethods if m.cs__const_defined?(:ClassMethods, false)
|
|
@@ -181,7 +181,8 @@ require 'contrast/components/agent'
|
|
|
181
181
|
Contrast::Components::ComponentReceiverClassInterface::COMPONENT_MAP[:agent] = [Contrast::Components::Agent]
|
|
182
182
|
|
|
183
183
|
require 'contrast/components/contrast_service'
|
|
184
|
-
Contrast::Components::ComponentReceiverClassInterface::COMPONENT_MAP[:contrast_service] =
|
|
184
|
+
Contrast::Components::ComponentReceiverClassInterface::COMPONENT_MAP[:contrast_service] =
|
|
185
|
+
[Contrast::Components::ContrastService]
|
|
185
186
|
|
|
186
187
|
require 'contrast/components/app_context'
|
|
187
188
|
Contrast::Components::ComponentReceiverClassInterface::COMPONENT_MAP[:app_context] = [Contrast::Components::AppContext]
|
|
@@ -65,7 +65,10 @@ module Contrast
|
|
|
65
65
|
# @param settings [Contrast::Api::Settings::Sampling] the Sampling settings as provided by TeamServer
|
|
66
66
|
# @return [Integer] the resolution of the config_settings, settings, and default value
|
|
67
67
|
def request_frequency config_settings, settings
|
|
68
|
-
[
|
|
68
|
+
[
|
|
69
|
+
config_settings&.request_frequency, settings&.request_frequency,
|
|
70
|
+
DEFAULT_SAMPLING_REQUEST_FREQUENCY
|
|
71
|
+
].map(&:to_i).find(&:positive?)
|
|
69
72
|
end
|
|
70
73
|
|
|
71
74
|
# @param config_settings [Contrast::Config::SamplingConfiguration] the Sampling configuration as provided by
|
|
@@ -73,7 +76,10 @@ module Contrast
|
|
|
73
76
|
# @param settings [Contrast::Api::Settings::Sampling] the Sampling settings as provided by TeamServer
|
|
74
77
|
# @return [Integer] the resolution of the config_settings, settings, and default value
|
|
75
78
|
def response_frequency config_settings, settings
|
|
76
|
-
[
|
|
79
|
+
[
|
|
80
|
+
config_settings&.response_frequency, settings&.response_frequency,
|
|
81
|
+
DEFAULT_SAMPLING_RESPONSE_FREQUENCY
|
|
82
|
+
].map(&:to_i).find(&:positive?)
|
|
77
83
|
end
|
|
78
84
|
|
|
79
85
|
# @param config_settings [Contrast::Config::SamplingConfiguration] the Sampling configuration as provided by
|
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
# Copyright (c) 2021 Contrast Security, Inc. See https://www.contrastsecurity.com/enduser-terms-0317a for more details.
|
|
2
2
|
# frozen_string_literal: true
|
|
3
3
|
|
|
4
|
+
require 'contrast/api/settings.pb'
|
|
5
|
+
|
|
4
6
|
module Contrast
|
|
5
7
|
module Components
|
|
6
8
|
# This component encapsulates the statefulness of settings.
|
|
@@ -8,8 +10,8 @@ module Contrast
|
|
|
8
10
|
# directives (likely provided by TeamServer) about product operation.
|
|
9
11
|
# 'Settings' is not a generic term for 'configurable stuff'.
|
|
10
12
|
module Settings
|
|
11
|
-
APPLICATION_STATE_BASE = Struct.new(:modes_by_id, :exclusion_matchers).
|
|
12
|
-
Hash.new
|
|
13
|
+
APPLICATION_STATE_BASE = Struct.new(:modes_by_id, :exclusion_matchers).
|
|
14
|
+
new(Hash.new(Contrast::Api::Settings::ProtectionRule::Mode::NO_ACTION), [])
|
|
13
15
|
PROTECT_STATE_BASE = Struct.new(:enabled, :rules).new(false, {})
|
|
14
16
|
ASSESS_STATE_BASE = Struct.new(:enabled, :sampling_settings, :disabled_assess_rules).new(false, nil, []) do
|
|
15
17
|
def sampling_settings= new_val
|
|
@@ -6,9 +6,7 @@ module Contrast
|
|
|
6
6
|
# Common Configuration settings. Those in this section pertain to the
|
|
7
7
|
# disabled assess rule functionality of the Agent.
|
|
8
8
|
class AssessRulesConfiguration < BaseConfiguration
|
|
9
|
-
KEYS = {
|
|
10
|
-
disabled_rules: EMPTY_VALUE
|
|
11
|
-
}.cs__freeze
|
|
9
|
+
KEYS = { disabled_rules: EMPTY_VALUE }.cs__freeze
|
|
12
10
|
|
|
13
11
|
def initialize hsh
|
|
14
12
|
super(hsh, KEYS)
|
|
@@ -17,10 +17,7 @@ module Contrast
|
|
|
17
17
|
attr_reader :map
|
|
18
18
|
|
|
19
19
|
alias_method :to_hash, :map
|
|
20
|
-
def_delegators :@map, :empty?, :key?,
|
|
21
|
-
:delete,
|
|
22
|
-
:fetch, :[], :[]=,
|
|
23
|
-
:each, :each_pair, :each_key, :each_value
|
|
20
|
+
def_delegators :@map, :empty?, :key?, :delete, :fetch, :[], :[]=, :each, :each_pair, :each_key, :each_value
|
|
24
21
|
|
|
25
22
|
EMPTY_VALUE = :EMPTY_VALUE
|
|
26
23
|
|
|
@@ -35,7 +32,9 @@ module Contrast
|
|
|
35
32
|
current_level = current_level.send(segment) if current_level.cs__respond_to?(segment)
|
|
36
33
|
end
|
|
37
34
|
last_entry = dot_path_array[-1]
|
|
38
|
-
|
|
35
|
+
if current_level.nil? == false && current_level.cs__respond_to?(last_entry)
|
|
36
|
+
current_level.send("#{ last_entry }=", value)
|
|
37
|
+
end
|
|
39
38
|
nil
|
|
40
39
|
end
|
|
41
40
|
|
|
@@ -7,11 +7,7 @@ module Contrast
|
|
|
7
7
|
# exception handling in Ruby, allowing for the override of Response Code
|
|
8
8
|
# and Message when Security Exceptions are raised.
|
|
9
9
|
class ExceptionConfiguration < BaseConfiguration
|
|
10
|
-
KEYS = {
|
|
11
|
-
capture: EMPTY_VALUE,
|
|
12
|
-
override_status: EMPTY_VALUE,
|
|
13
|
-
override_message: EMPTY_VALUE
|
|
14
|
-
}.cs__freeze
|
|
10
|
+
KEYS = { capture: EMPTY_VALUE, override_status: EMPTY_VALUE, override_message: EMPTY_VALUE }.cs__freeze
|
|
15
11
|
|
|
16
12
|
def initialize hsh
|
|
17
13
|
super(hsh, KEYS)
|
|
@@ -7,12 +7,18 @@ module Contrast
|
|
|
7
7
|
# Heap Dump collection functionality of the Agent.
|
|
8
8
|
class HeapDumpConfiguration < BaseConfiguration
|
|
9
9
|
KEYS = {
|
|
10
|
-
enable:
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
10
|
+
enable: # should dumps be taken
|
|
11
|
+
Contrast::Config::DefaultValue.new(Contrast::Utils::ObjectShare::FALSE),
|
|
12
|
+
path: # dir to which dumps should be
|
|
13
|
+
Contrast::Config::DefaultValue.new('contrast_heap_dumps'), # saved
|
|
14
|
+
delay_ms: # time, in ms, after initialization
|
|
15
|
+
Contrast::Config::DefaultValue.new(10_000), # to delay before taking dump
|
|
16
|
+
window_ms: # ms between each dump
|
|
17
|
+
Contrast::Config::DefaultValue.new(10_000), #
|
|
18
|
+
count: # number of dumps to take
|
|
19
|
+
Contrast::Config::DefaultValue.new(5), #
|
|
20
|
+
clean: # remove temporary objects or not
|
|
21
|
+
Contrast::Config::DefaultValue.new(Contrast::Utils::ObjectShare::FALSE) #
|
|
16
22
|
}.cs__freeze
|
|
17
23
|
|
|
18
24
|
def initialize hsh
|
|
@@ -6,11 +6,7 @@ module Contrast
|
|
|
6
6
|
# Common Configuration settings. Those in this section pertain to the
|
|
7
7
|
# logging in the Agent.
|
|
8
8
|
class LoggerConfiguration < BaseConfiguration
|
|
9
|
-
KEYS = {
|
|
10
|
-
path: EMPTY_VALUE,
|
|
11
|
-
level: EMPTY_VALUE,
|
|
12
|
-
progname: EMPTY_VALUE
|
|
13
|
-
}.cs__freeze
|
|
9
|
+
KEYS = { path: EMPTY_VALUE, level: EMPTY_VALUE, progname: EMPTY_VALUE }.cs__freeze
|
|
14
10
|
|
|
15
11
|
def initialize hsh
|
|
16
12
|
super(hsh, KEYS)
|
|
@@ -25,16 +25,8 @@ module Contrast
|
|
|
25
25
|
|
|
26
26
|
DEFAULT_YAML_PATH = 'contrast_security.yaml'
|
|
27
27
|
MILLISECOND_MARKER = '_ms'
|
|
28
|
-
CONVERSION = {
|
|
29
|
-
|
|
30
|
-
}.cs__freeze
|
|
31
|
-
CONFIG_BASE_PATHS = [
|
|
32
|
-
'',
|
|
33
|
-
'config/',
|
|
34
|
-
'/etc/contrast/ruby/',
|
|
35
|
-
'/etc/contrast/',
|
|
36
|
-
'/etc/'
|
|
37
|
-
].cs__freeze
|
|
28
|
+
CONVERSION = { 'agent.service.enable' => 'agent.start_bundled_service' }.cs__freeze
|
|
29
|
+
CONFIG_BASE_PATHS = ['', 'config/', '/etc/contrast/ruby/', '/etc/contrast/', '/etc/'].cs__freeze
|
|
38
30
|
|
|
39
31
|
def initialize cli_options = nil, default_name = DEFAULT_YAML_PATH
|
|
40
32
|
@default_name = default_name
|
|
@@ -189,10 +181,7 @@ module Contrast
|
|
|
189
181
|
# When we fail to parse a configuration because it is misformatted, log an
|
|
190
182
|
# appropriate message based on the Agent Onboarding specification
|
|
191
183
|
def log_yaml_parse_error path, exception
|
|
192
|
-
hash = {
|
|
193
|
-
path: path,
|
|
194
|
-
pwd: Dir.pwd
|
|
195
|
-
}
|
|
184
|
+
hash = { path: path, pwd: Dir.pwd }
|
|
196
185
|
if exception.is_a?(Psych::SyntaxError)
|
|
197
186
|
hash[:context] = exception.context
|
|
198
187
|
hash[:column] = exception.column
|
|
@@ -56,12 +56,7 @@ module Contrast
|
|
|
56
56
|
return ret unless Contrast::Agent::Assess::Tracker.tracked?(ret)
|
|
57
57
|
|
|
58
58
|
properties.cleanup_tags
|
|
59
|
-
properties.build_event(
|
|
60
|
-
ARRAY_JOIN_NODE,
|
|
61
|
-
ret,
|
|
62
|
-
ary,
|
|
63
|
-
ret,
|
|
64
|
-
[separator])
|
|
59
|
+
properties.build_event(ARRAY_JOIN_NODE, ret, ary, ret, [separator])
|
|
65
60
|
properties.event.instance_variable_set(:@_parent_events, parent_events)
|
|
66
61
|
ret
|
|
67
62
|
end
|
|
@@ -25,13 +25,7 @@ module ERBPropagator
|
|
|
25
25
|
parent_event = Contrast::Agent::Assess::Tracker.properties(bound_variable_value)&.event
|
|
26
26
|
parent_events << parent_event if parent_event
|
|
27
27
|
end
|
|
28
|
-
properties.build_event(
|
|
29
|
-
patcher,
|
|
30
|
-
ret,
|
|
31
|
-
preshift.object,
|
|
32
|
-
ret,
|
|
33
|
-
preshift.args,
|
|
34
|
-
1)
|
|
28
|
+
properties.build_event(patcher, ret, preshift.object, ret, preshift.args, 1)
|
|
35
29
|
properties.event.instance_variable_set(:@_parent_events, parent_events)
|
|
36
30
|
|
|
37
31
|
ret
|
|
@@ -31,12 +31,8 @@ module Contrast
|
|
|
31
31
|
# source might not be all the args passed in, but it is the one we care
|
|
32
32
|
# about. we could pass in all the args in the last param here if it
|
|
33
33
|
# becomes an issue in rendering on TS
|
|
34
|
-
Contrast::Agent::Assess::Policy::TriggerMethod.apply_eval_trigger(
|
|
35
|
-
|
|
36
|
-
source,
|
|
37
|
-
obj,
|
|
38
|
-
ret,
|
|
39
|
-
source)
|
|
34
|
+
Contrast::Agent::Assess::Policy::TriggerMethod.apply_eval_trigger(trigger_node(clazz, method), source, obj,
|
|
35
|
+
ret, source)
|
|
40
36
|
end
|
|
41
37
|
|
|
42
38
|
def instrument_basic_object_track
|
|
@@ -18,20 +18,14 @@ module Contrast
|
|
|
18
18
|
# source might not be all the args passed in, but it is the one we care
|
|
19
19
|
# about. we could pass in all the args in the last param here if it
|
|
20
20
|
# becomes an issue in rendering on TS
|
|
21
|
-
Contrast::Agent::Assess::Policy::TriggerMethod.build_finding(
|
|
22
|
-
trigger_node,
|
|
23
|
-
source,
|
|
24
|
-
Kernel,
|
|
25
|
-
nil,
|
|
26
|
-
source)
|
|
21
|
+
Contrast::Agent::Assess::Policy::TriggerMethod.build_finding(trigger_node, source, Kernel, nil, source)
|
|
27
22
|
end
|
|
28
23
|
|
|
29
24
|
private
|
|
30
25
|
|
|
31
26
|
def trigger_node
|
|
32
|
-
@_trigger_node ||=
|
|
33
|
-
|
|
34
|
-
end
|
|
27
|
+
@_trigger_node ||= Contrast::Agent::Assess::Policy::Policy.instance.find_node('cmd-injection', 'Kernel',
|
|
28
|
+
:exec, false)
|
|
35
29
|
end
|
|
36
30
|
end
|
|
37
31
|
end
|
|
@@ -64,12 +64,7 @@ module Contrast
|
|
|
64
64
|
next unless (result_properties = Contrast::Agent::Assess::Tracker.properties!(result))
|
|
65
65
|
|
|
66
66
|
result_properties.splat_from(fiber, result)
|
|
67
|
-
result_properties.build_event(
|
|
68
|
-
FIBER_YIELD_NODE,
|
|
69
|
-
result,
|
|
70
|
-
fiber,
|
|
71
|
-
result,
|
|
72
|
-
[])
|
|
67
|
+
result_properties.build_event(FIBER_YIELD_NODE, result, fiber, result, [])
|
|
73
68
|
end
|
|
74
69
|
end
|
|
75
70
|
rescue Exception => e # rubocop:disable Lint/RescueException
|
|
@@ -85,12 +80,7 @@ module Contrast
|
|
|
85
80
|
return unless properties
|
|
86
81
|
|
|
87
82
|
properties.splat_from(underlying, fiber)
|
|
88
|
-
properties.build_event(
|
|
89
|
-
FIBER_NEW_NODE,
|
|
90
|
-
fiber,
|
|
91
|
-
underlying,
|
|
92
|
-
fiber,
|
|
93
|
-
[])
|
|
83
|
+
properties.build_event(FIBER_NEW_NODE, fiber, underlying, fiber, [])
|
|
94
84
|
end
|
|
95
85
|
rescue Exception => e # rubocop:disable Lint/RescueException
|
|
96
86
|
logger.error('Unable to propagate during Fiber.new', e)
|
|
@@ -47,13 +47,7 @@ module Contrast
|
|
|
47
47
|
parent_events = []
|
|
48
48
|
track_sprintf(ret, format_string, args, parent_events)
|
|
49
49
|
|
|
50
|
-
properties.build_event(
|
|
51
|
-
patcher,
|
|
52
|
-
ret,
|
|
53
|
-
preshift.object,
|
|
54
|
-
ret,
|
|
55
|
-
preshift.args,
|
|
56
|
-
1)
|
|
50
|
+
properties.build_event(patcher, ret, preshift.object, ret, preshift.args, 1)
|
|
57
51
|
|
|
58
52
|
properties.event.instance_variable_set(:@_parent_events, parent_events)
|
|
59
53
|
ret
|
|
@@ -70,8 +64,7 @@ module Contrast
|
|
|
70
64
|
handle_sprintf_array(args, result, parent_events)
|
|
71
65
|
end
|
|
72
66
|
rescue StandardError => e
|
|
73
|
-
logger.error(
|
|
74
|
-
'Unable to track dataflow through sprintf', e)
|
|
67
|
+
logger.error('Unable to track dataflow through sprintf', e)
|
|
75
68
|
end
|
|
76
69
|
|
|
77
70
|
def instrument_kernel_track
|