contrast-agent 6.6.3 → 6.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.
Files changed (185) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +3 -0
  3. data/.gitmodules +0 -3
  4. data/ext/cs__scope/cs__scope.c +1 -1
  5. data/lib/contrast/agent/assess/contrast_event.rb +2 -24
  6. data/lib/contrast/agent/assess/events/source_event.rb +7 -61
  7. data/lib/contrast/agent/assess/finalizers/hash.rb +11 -0
  8. data/lib/contrast/agent/assess/policy/dynamic_source_factory.rb +0 -55
  9. data/lib/contrast/agent/assess/policy/policy_node.rb +3 -3
  10. data/lib/contrast/agent/assess/policy/policy_node_utils.rb +0 -1
  11. data/lib/contrast/agent/assess/policy/propagation_node.rb +4 -4
  12. data/lib/contrast/agent/assess/policy/source_method.rb +24 -1
  13. data/lib/contrast/agent/assess/policy/trigger/reflected_xss.rb +7 -5
  14. data/lib/contrast/agent/assess/policy/trigger/xpath.rb +6 -1
  15. data/lib/contrast/agent/assess/policy/trigger_method.rb +38 -119
  16. data/lib/contrast/agent/assess/policy/trigger_node.rb +3 -3
  17. data/lib/contrast/agent/assess/property/evented.rb +2 -12
  18. data/lib/contrast/agent/assess/rule/provider/hardcoded_value_rule.rb +42 -82
  19. data/lib/contrast/agent/assess/rule/response/base_rule.rb +11 -27
  20. data/lib/contrast/agent/assess/rule/response/body_rule.rb +1 -3
  21. data/lib/contrast/agent/assess/rule/response/cache_control_header_rule.rb +77 -62
  22. data/lib/contrast/agent/assess/rule/response/csp_header_insecure_rule.rb +1 -1
  23. data/lib/contrast/agent/assess/rule/response/framework/rails_support.rb +6 -1
  24. data/lib/contrast/agent/assess/rule/response/header_rule.rb +5 -5
  25. data/lib/contrast/agent/assess/rule/response/hsts_header_rule.rb +1 -1
  26. data/lib/contrast/agent/assess/rule/response/x_xss_protection_header_rule.rb +1 -1
  27. data/lib/contrast/agent/assess/tracker.rb +1 -7
  28. data/lib/contrast/agent/at_exit_hook.rb +1 -7
  29. data/lib/contrast/agent/excluder.rb +206 -0
  30. data/lib/contrast/agent/exclusion_matcher.rb +6 -0
  31. data/lib/contrast/agent/inventory/database_config.rb +18 -23
  32. data/lib/contrast/agent/middleware.rb +0 -1
  33. data/lib/contrast/agent/protect/policy/applies_command_injection_rule.rb +4 -0
  34. data/lib/contrast/agent/protect/policy/applies_sqli_rule.rb +1 -0
  35. data/lib/contrast/agent/protect/rule/base.rb +64 -24
  36. data/lib/contrast/agent/protect/rule/base_service.rb +1 -0
  37. data/lib/contrast/agent/protect/rule/cmd_injection.rb +18 -104
  38. data/lib/contrast/agent/protect/rule/cmdi/cmdi_backdoors.rb +129 -0
  39. data/lib/contrast/agent/protect/rule/cmdi/cmdi_base_rule.rb +169 -0
  40. data/lib/contrast/agent/protect/rule/deserialization.rb +7 -5
  41. data/lib/contrast/agent/protect/rule/path_traversal.rb +9 -7
  42. data/lib/contrast/agent/protect/rule/sql_sample_builder.rb +16 -14
  43. data/lib/contrast/agent/protect/rule/sqli/sqli_base_rule.rb +51 -0
  44. data/lib/contrast/agent/protect/rule/sqli/sqli_semantic/sqli_dangerous_functions.rb +67 -0
  45. data/lib/contrast/agent/protect/rule/sqli.rb +6 -31
  46. data/lib/contrast/agent/protect/rule/xxe.rb +11 -6
  47. data/lib/contrast/agent/protect/rule.rb +3 -1
  48. data/lib/contrast/agent/reporting/attack_result/attack_result.rb +8 -0
  49. data/lib/contrast/agent/reporting/attack_result/rasp_rule_sample.rb +91 -36
  50. data/lib/contrast/agent/reporting/attack_result/user_input.rb +11 -0
  51. data/lib/contrast/agent/reporting/details/bot_blocker_details.rb +29 -0
  52. data/lib/contrast/agent/reporting/details/cmd_injection_details.rb +30 -0
  53. data/lib/contrast/agent/reporting/details/details.rb +18 -0
  54. data/lib/contrast/agent/reporting/details/http_method_tempering_details.rb +27 -0
  55. data/lib/contrast/agent/reporting/details/ip_denylist_details.rb +27 -0
  56. data/lib/contrast/agent/reporting/details/no_sqli_details.rb +36 -0
  57. data/lib/contrast/agent/reporting/details/path_traversal_details.rb +24 -0
  58. data/lib/contrast/agent/reporting/details/path_traversal_semantic_analysis_details.rb +32 -0
  59. data/lib/contrast/agent/reporting/details/protect_rule_details.rb +17 -0
  60. data/lib/contrast/agent/reporting/details/sqli_dangerous_functions.rb +22 -0
  61. data/lib/contrast/agent/reporting/details/sqli_details.rb +36 -0
  62. data/lib/contrast/agent/reporting/details/untrusted_deserialization_details.rb +27 -0
  63. data/lib/contrast/agent/reporting/details/virtual_patch_details.rb +24 -0
  64. data/lib/contrast/agent/reporting/details/xss_details.rb +33 -0
  65. data/lib/contrast/agent/reporting/details/xss_match.rb +30 -0
  66. data/lib/contrast/agent/reporting/details/xxe_details.rb +36 -0
  67. data/lib/contrast/agent/reporting/details/xxe_match.rb +25 -0
  68. data/lib/contrast/agent/reporting/details/xxe_wrapper.rb +25 -0
  69. data/lib/contrast/agent/reporting/input_analysis/input_analysis_result.rb +1 -1
  70. data/lib/contrast/agent/reporting/masker/masker.rb +78 -65
  71. data/lib/contrast/agent/reporting/masker/masker_utils.rb +1 -30
  72. data/lib/contrast/agent/reporting/reporter.rb +1 -2
  73. data/lib/contrast/agent/reporting/reporting_events/agent_startup.rb +2 -2
  74. data/lib/contrast/agent/reporting/reporting_events/application_activity.rb +81 -15
  75. data/lib/contrast/agent/reporting/reporting_events/application_defend_activity.rb +13 -25
  76. data/lib/contrast/agent/reporting/reporting_events/application_defend_attack_activity.rb +17 -22
  77. data/lib/contrast/agent/reporting/reporting_events/application_defend_attack_sample.rb +46 -125
  78. data/lib/contrast/agent/reporting/reporting_events/application_defend_attack_sample_activity.rb +5 -16
  79. data/lib/contrast/agent/reporting/reporting_events/application_defend_attacker_activity.rb +10 -18
  80. data/lib/contrast/agent/reporting/reporting_events/application_inventory_activity.rb +6 -14
  81. data/lib/contrast/agent/reporting/reporting_events/application_startup.rb +1 -1
  82. data/lib/contrast/agent/reporting/reporting_events/architecture_component.rb +7 -21
  83. data/lib/contrast/agent/reporting/reporting_events/finding.rb +19 -49
  84. data/lib/contrast/agent/reporting/reporting_events/finding_event.rb +12 -9
  85. data/lib/contrast/agent/reporting/reporting_events/finding_event_signature.rb +1 -1
  86. data/lib/contrast/agent/reporting/reporting_events/finding_event_source.rb +23 -21
  87. data/lib/contrast/agent/reporting/reporting_events/finding_event_stack.rb +5 -18
  88. data/lib/contrast/agent/reporting/reporting_events/finding_event_taint_range.rb +1 -0
  89. data/lib/contrast/{api/decorators/trace_taint_range_tags.rb → agent/reporting/reporting_events/finding_event_taint_range_tags.rb} +7 -6
  90. data/lib/contrast/agent/reporting/reporting_events/finding_request.rb +45 -10
  91. data/lib/contrast/agent/reporting/reporting_events/library_usage_observation.rb +1 -1
  92. data/lib/contrast/agent/reporting/reporting_events/observed_route.rb +2 -2
  93. data/lib/contrast/agent/reporting/reporting_events/preflight_message.rb +10 -14
  94. data/lib/contrast/agent/reporting/reporting_events/reporting_event.rb +11 -0
  95. data/lib/contrast/agent/reporting/reporting_events/route_coverage.rb +3 -1
  96. data/lib/contrast/agent/reporting/reporting_events/route_discovery.rb +11 -23
  97. data/lib/contrast/agent/reporting/reporting_events/route_discovery_observation.rb +8 -26
  98. data/lib/contrast/agent/reporting/reporting_utilities/audit.rb +1 -1
  99. data/lib/contrast/agent/reporting/reporting_utilities/build_preflight.rb +4 -7
  100. data/lib/contrast/agent/reporting/reporting_utilities/headers.rb +1 -1
  101. data/lib/contrast/agent/reporting/reporting_utilities/reporter_client.rb +2 -1
  102. data/lib/contrast/agent/reporting/reporting_utilities/reporter_client_utils.rb +3 -3
  103. data/lib/contrast/agent/request.rb +4 -2
  104. data/lib/contrast/agent/request_context.rb +12 -15
  105. data/lib/contrast/agent/request_context_extend.rb +67 -69
  106. data/lib/contrast/agent/request_handler.rb +1 -11
  107. data/lib/contrast/agent/response.rb +0 -18
  108. data/lib/contrast/agent/service_heartbeat.rb +1 -1
  109. data/lib/contrast/agent/telemetry/events/event.rb +1 -1
  110. data/lib/contrast/agent/telemetry/events/metric_event.rb +1 -1
  111. data/lib/contrast/agent/telemetry/events/startup_metrics_event.rb +3 -3
  112. data/lib/contrast/agent/version.rb +1 -1
  113. data/lib/contrast/api/communication/messaging_queue.rb +2 -3
  114. data/lib/contrast/api/communication/socket_client.rb +4 -4
  115. data/lib/contrast/api/communication/speedracer.rb +4 -8
  116. data/lib/contrast/api/decorators/agent_startup.rb +5 -6
  117. data/lib/contrast/api/decorators/application_settings.rb +2 -1
  118. data/lib/contrast/api/decorators/application_startup.rb +6 -6
  119. data/lib/contrast/api/decorators/message.rb +0 -4
  120. data/lib/contrast/api/decorators/rasp_rule_sample.rb +0 -6
  121. data/lib/contrast/api/decorators.rb +0 -6
  122. data/lib/contrast/api/dtm.pb.rb +0 -489
  123. data/lib/contrast/components/agent.rb +16 -12
  124. data/lib/contrast/components/api.rb +10 -10
  125. data/lib/contrast/components/app_context.rb +9 -9
  126. data/lib/contrast/components/app_context_extend.rb +1 -1
  127. data/lib/contrast/components/assess.rb +92 -38
  128. data/lib/contrast/components/assess_rules.rb +36 -0
  129. data/lib/contrast/components/config.rb +54 -12
  130. data/lib/contrast/components/contrast_service.rb +8 -8
  131. data/lib/contrast/components/heap_dump.rb +1 -1
  132. data/lib/contrast/components/protect.rb +5 -5
  133. data/lib/contrast/components/ruby_component.rb +81 -0
  134. data/lib/contrast/components/sampling.rb +1 -1
  135. data/lib/contrast/components/security_logger.rb +23 -0
  136. data/lib/contrast/components/service.rb +55 -0
  137. data/lib/contrast/components/settings.rb +12 -4
  138. data/lib/contrast/config/base_configuration.rb +1 -1
  139. data/lib/contrast/config/protect_rules_configuration.rb +17 -3
  140. data/lib/contrast/config/server_configuration.rb +1 -1
  141. data/lib/contrast/config.rb +0 -6
  142. data/lib/contrast/configuration.rb +81 -17
  143. data/lib/contrast/extension/assess/exec_trigger.rb +3 -1
  144. data/lib/contrast/extension/assess/marshal.rb +3 -2
  145. data/lib/contrast/extension/assess/string.rb +0 -1
  146. data/lib/contrast/extension/extension.rb +1 -1
  147. data/lib/contrast/framework/base_support.rb +0 -5
  148. data/lib/contrast/framework/grape/support.rb +1 -23
  149. data/lib/contrast/framework/manager.rb +0 -10
  150. data/lib/contrast/framework/rails/patch/action_controller_live_buffer.rb +1 -6
  151. data/lib/contrast/framework/rails/support.rb +5 -58
  152. data/lib/contrast/framework/sinatra/support.rb +2 -21
  153. data/lib/contrast/logger/cef_log.rb +21 -3
  154. data/lib/contrast/logger/log.rb +1 -11
  155. data/lib/contrast/tasks/config.rb +4 -2
  156. data/lib/contrast/utils/assess/event_limit_utils.rb +28 -12
  157. data/lib/contrast/utils/assess/trigger_method_utils.rb +10 -18
  158. data/lib/contrast/utils/findings.rb +6 -5
  159. data/lib/contrast/utils/hash_digest.rb +9 -24
  160. data/lib/contrast/utils/hash_digest_extend.rb +6 -6
  161. data/lib/contrast/utils/invalid_configuration_util.rb +21 -58
  162. data/lib/contrast/utils/log_utils.rb +47 -17
  163. data/lib/contrast/utils/net_http_base.rb +7 -8
  164. data/lib/contrast/utils/patching/policy/patch_utils.rb +3 -2
  165. data/lib/contrast/utils/stack_trace_utils.rb +0 -25
  166. data/lib/contrast/utils/string_utils.rb +9 -0
  167. data/lib/contrast/utils/telemetry_client.rb +13 -7
  168. data/lib/contrast.rb +5 -10
  169. metadata +39 -28
  170. data/lib/contrast/agent/reporting/reporting_events/trace_event_source.rb +0 -30
  171. data/lib/contrast/agent/reporting/reporting_utilities/dtm_message.rb +0 -43
  172. data/lib/contrast/api/decorators/activity.rb +0 -33
  173. data/lib/contrast/api/decorators/architecture_component.rb +0 -36
  174. data/lib/contrast/api/decorators/finding.rb +0 -29
  175. data/lib/contrast/api/decorators/route_coverage.rb +0 -91
  176. data/lib/contrast/api/decorators/trace_event.rb +0 -120
  177. data/lib/contrast/api/decorators/trace_event_object.rb +0 -63
  178. data/lib/contrast/api/decorators/trace_event_signature.rb +0 -69
  179. data/lib/contrast/api/decorators/trace_taint_range.rb +0 -52
  180. data/lib/contrast/config/assess_configuration.rb +0 -93
  181. data/lib/contrast/config/assess_rules_configuration.rb +0 -32
  182. data/lib/contrast/config/root_configuration.rb +0 -90
  183. data/lib/contrast/config/ruby_configuration.rb +0 -81
  184. data/lib/contrast/config/service_configuration.rb +0 -49
  185. data/lib/contrast/utils/preflight_util.rb +0 -13
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 38657595e182ad9ef1a26180b273061522dcea43e441e1750d9883d2d1d2d9f6
4
- data.tar.gz: 37fe627c2fec00f17c6a2cd6b42aa96149bc4b01871fddd6bb929c5a2baabb63
3
+ metadata.gz: c688788c7666c5ea72351e52ad02fe838923dc0dde589199917d2bfa96080630
4
+ data.tar.gz: f63416e47b9b815f0ec7a79858fb11f866bf5c49c952cf278dfb851679f44957
5
5
  SHA512:
6
- metadata.gz: 1a2a85843ec7ba80d84a84f21defd2333a1b1130165113777c324176597231ca17b6c861f1f44ff6024f71e01e7d3508f0d57e767381e3d7580e82c7e10bee4a
7
- data.tar.gz: b7b98e93f5b8e3bfd826f730e3981bb6006aa69a71dbd24ecec6eeef373b0b147ce542f0e0416f42d9da33dbbe4a76945bb1341bde91ea9b7134a4ddee80b2fb
6
+ metadata.gz: 0b5ee56bb30a55609a6252a105c8ab60e0bf66bdcac23e4efa937cfbc99f7669ab5ed7ffdc41dfd1b9659a09a93d2f7714af0eb398b46069542f0dff753c1ccd
7
+ data.tar.gz: 84b72b0f516808677745cc1ea7ecdedf762309ceb79eaac2908f1f16ac6abc811f2997bc50673e78101d7845ddd67a73c996c7ed3ebdbca6d33cf88883926499
data/.gitignore CHANGED
@@ -23,6 +23,9 @@ ruby-spec
23
23
  mspec
24
24
  service_executables
25
25
 
26
+ # rspec generated files
27
+ /spec/dummy_files/*
28
+
26
29
  # Funchook artifacts
27
30
  /ext/**/funchook.h
28
31
  /ext/**/libfunchook.dylib
data/.gitmodules CHANGED
@@ -1,6 +1,3 @@
1
- [submodule "agent-service-api"]
2
- path = agent-service-api
3
- url = git@github.com:Contrast-Security-Inc/agent-service-api.git
4
1
  [submodule "funchook"]
5
2
  path = funchook
6
3
  url = https://github.com/kubo/funchook.git
@@ -81,7 +81,7 @@ void rb_raise_scope_no_method_err(const VALUE method_scope_sym) {
81
81
  * sets scope instance variables.
82
82
  * def initialize
83
83
  * @contrast_scope = 0
84
- * @deserialization_scope = 0
84
+ * @deserialization_scope = 0
85
85
  * @split_scope = 0
86
86
  * end
87
87
  */
@@ -9,6 +9,7 @@ require 'contrast/utils/stack_trace_utils'
9
9
  require 'contrast/utils/string_utils'
10
10
  require 'contrast/utils/timer'
11
11
  require 'contrast/agent/assess/contrast_object'
12
+ require 'contrast/agent/reporting/reporting_events/finding_event'
12
13
 
13
14
  module Contrast
14
15
  module Agent
@@ -63,34 +64,11 @@ module Contrast
63
64
  capture_stacktrace!
64
65
  end
65
66
 
67
+ # @return [Array<Contrast::Agent::Assess::ContrastEvent>]
66
68
  def parent_events
67
69
  @_parent_events ||= []
68
70
  end
69
71
 
70
- # We have to do a little work to figure out what our TS appropriate target is. To break this down, the logic is
71
- # as follows:
72
- # 1) If my policy_node has a target, work on targets. Else, work on sources. Per TS law, each policy_node must
73
- # have at least a source or a target. The only type of policy_node w/o targets is a Trigger, but that may
74
- # change.
75
- # 2) I'll set the event's source and target to TS values.
76
- # 3) Return the first source/target as the taint target.
77
- def determine_taint_target event_dtm
78
- if @policy_node&.targets&.any?
79
- event_dtm.source = @policy_node.source_string if @policy_node.source_string
80
- event_dtm.target = @policy_node.target_string
81
- @policy_node.targets[0]
82
- elsif policy_node&.sources&.any?
83
- event_dtm.source = @policy_node.source_string
84
- event_dtm.target = @policy_node.target_string if @policy_node.target_string
85
- @policy_node.sources[0]
86
- end
87
- end
88
-
89
- # Convert this event into a DTM that TeamServer can consume
90
- def to_dtm_event
91
- Contrast::Api::Dtm::TraceEvent.build(self)
92
- end
93
-
94
72
  private
95
73
 
96
74
  # Parent events are the events of all the sources of this event which were tracked prior to this event
@@ -2,7 +2,8 @@
2
2
  # frozen_string_literal: true
3
3
 
4
4
  require 'contrast/agent/assess/contrast_event'
5
- require 'contrast/agent/reporting/reporting_events/trace_event_source'
5
+ require 'contrast/agent/reporting/reporting_events/finding_event'
6
+ require 'contrast/agent/reporting/reporting_events/finding_event_source'
6
7
  require 'contrast/utils/string_utils'
7
8
 
8
9
  module Contrast
@@ -19,6 +20,8 @@ module Contrast
19
20
  attr_reader :source_name
20
21
  # @return [String] the TeamServer understood type of source; i.e. parameter
21
22
  attr_reader :source_type
23
+ # @return [Contrast::Agent::Reporting::FindingEventSource] the source of this trace
24
+ attr_reader :event_source
22
25
 
23
26
  # @param event_data [Contrast::Agent::Assess::Events::EventData]
24
27
  # @param source_type [String] the type of this source, from the source_node, or a KEY_TYPE if invoked for a
@@ -27,72 +30,15 @@ module Contrast
27
30
  # nil if a type like
28
31
  def initialize event_data, source_type = nil, source_name = nil
29
32
  super(event_data)
30
- @source_type = source_type
31
- @source_name = source_name
33
+ @source_type = Contrast::Utils::StringUtils.force_utf8(source_type)
34
+ @source_name = Contrast::Utils::StringUtils.force_utf8(source_name)
35
+ @event_source = Contrast::Agent::Reporting::FindingEventSource.new(@source_type, @source_name)
32
36
  @request = Contrast::Agent::REQUEST_TRACKER.current&.request
33
37
  end
34
38
 
35
39
  def parent_events
36
40
  nil
37
41
  end
38
-
39
- # Convert this event into a DTM that TeamServer can consume
40
- def to_dtm_event
41
- event = super
42
- event.field_name = Contrast::Utils::StringUtils.force_utf8(source_name)
43
- event_source_dtm = build_event_source_dtm
44
- event.event_sources << event_source_dtm if event_source_dtm
45
- event.object_id = event_id.to_i
46
- event
47
- end
48
-
49
- def forced_source_type
50
- @_forced_source_type ||= Contrast::Utils::StringUtils.force_utf8(source_type)
51
- end
52
-
53
- def forced_source_name
54
- @_forced_source_name ||= Contrast::Utils::StringUtils.force_utf8(source_name)
55
- end
56
-
57
- # Probably only for source events, but we'll go with source_type instead. java & .net support source_type
58
- # in propagation events, so we'll future proof this
59
- #
60
- # @return [Contrast::Agent::Reporting::TraceEventSource, nil]
61
- def build_event_source
62
- # You can have a source w/o a name, but not w/o a type
63
- return unless source_type
64
-
65
- trace_event_source = Contrast::Agent::Reporting::TraceEventSource.new
66
- trace_event_source.type = forced_source_type
67
- trace_event_source.name = forced_source_name
68
- trace_event_source
69
- end
70
-
71
- # We have to do a little work to figure out what our TS appropriate target is. To break this down, the logic
72
- # is as follows:
73
- # 1) I'll set the event's source and target to TS values.
74
- # 2) Return the first source/target as the taint target.
75
- def determine_taint_target event_dtm
76
- return unless @policy_node&.targets&.any?
77
-
78
- event_dtm.source = @policy_node.source_string if @policy_node.source_string
79
- event_dtm.target = @policy_node.target_string
80
- @policy_node.targets[0]
81
- end
82
-
83
- private
84
-
85
- # Probably only for source events, but we'll go with source_type instead. java & .net support source_type
86
- # in propagation events, so we'll future proof this
87
- def build_event_source_dtm
88
- # You can have a source w/o a name, but not w/o a type
89
- return unless source_type
90
-
91
- dtm = Contrast::Api::Dtm::TraceEventSource.new
92
- dtm.type = forced_source_type
93
- dtm.name = forced_source_name
94
- dtm
95
- end
96
42
  end
97
43
  end
98
44
  end
@@ -10,8 +10,11 @@ module Contrast
10
10
  module Finalizers
11
11
  # An extension of Hash that doesn't impact GC of the object being stored by storing its ID as a Key to lookup
12
12
  # and registering a finalizer on the object to remove its entry from the Hash immediately after it's GC'd.
13
+ #
14
+ # NOTE: PROPERTIES_HASH is called from C
13
15
  class Hash < Hash
14
16
  FROZEN_FINALIZED_IDS = Set.new
17
+ KEEP_AGE = 600_000.cs__freeze # 10 minutes
15
18
 
16
19
  def []= key, obj
17
20
  return unless obj
@@ -89,6 +92,14 @@ module Contrast
89
92
  rescue StandardError => _e
90
93
  nil
91
94
  end
95
+
96
+ def cleanup!
97
+ ids = keys.dup
98
+ ids.each do |key|
99
+ properties = fetch(key.__id__, nil)
100
+ delete(key) unless properties&.event && (Contrast::Utils::Timer.now_ms - properties.event.time) < KEEP_AGE
101
+ end
102
+ end
92
103
  end
93
104
  end
94
105
  end
@@ -44,11 +44,6 @@ module Contrast
44
44
  Contrast::Agent::Assess::Policy::Policy.instance.add_node(dynamic_source_node, :dynamic_source)
45
45
  method_policy = build_source_policy(method_name, dynamic_source_node)
46
46
  Contrast::Agent::Patching::Policy::Patcher.patch_method(klass, instance_methods, method_policy)
47
- next unless current_context
48
-
49
- dynamic_source = create_dynamic_source(current_request, dynamic_source_node, field, properties)
50
- node_id = Contrast::Utils::StringUtils.force_utf8(dynamic_source_node.id)
51
- current_context.activity.dynamic_sources[node_id] = dynamic_source
52
47
  end
53
48
  end
54
49
 
@@ -97,56 +92,6 @@ module Contrast
97
92
  source_node: dynamic_source_node
98
93
  })
99
94
  end
100
-
101
- # @param request [Contrast::Agent::Request] the request during
102
- # which this source is to be created.
103
- # @param source_node [Contrast::Agent::Assess::Policy::SourceNode]
104
- # the SourceNode that applies to this method
105
- # @param field [String] the name of the method to which this source
106
- # applies
107
- # @param properties [Contrast::Agent::Assess::Properties] the
108
- # properties which this source should relate to the data tracked
109
- # as a result of this Source Method
110
- # @return [Contrast::Api::Dtm::DynamicSource] the message to send
111
- # to the Service to allow it to report the events leading up to
112
- # the creation of the Dynamic Source
113
- def create_dynamic_source request, source_node, field, properties
114
- dynamic_source = Contrast::Api::Dtm::DynamicSource.new
115
- dynamic_source.class_name = Contrast::Utils::StringUtils.force_utf8(source_node.class_name)
116
- dynamic_source.method_name = Contrast::Utils::StringUtils.force_utf8(field)
117
- dynamic_source.instance_method = source_node.instance_method?
118
- dynamic_source.target = Contrast::Utils::StringUtils.force_utf8(source_node.target_string)
119
- append_properties!(dynamic_source, request, source_node, field)
120
- append_events!(dynamic_source, properties.event)
121
- dynamic_source
122
- end
123
-
124
- # Append the properties needed to reconstruct the given DynamicSource in other dataflows and for rendering
125
- # in TeamServer
126
- #
127
- # @param dynamic_source [Contrast::Api::Dtm::DynamicSource] the message to send to the Service to allow it
128
- # to report the events leading up to the creation of the Dynamic Source.
129
- # @param request [Contrast::Agent::Request] the request during which this source is to be created.
130
- # @param source_node [Contrast::Agent::Assess::Policy::SourceNode] the SourceNode that applies to this
131
- # method.
132
- # @param field [String] the name of the method to which this source applies.
133
- def append_properties! dynamic_source, request, source_node, field
134
- dynamic_source.properties[READ_TABLE] = Contrast::Utils::StringUtils.force_utf8(source_node.class_name)
135
- dynamic_source.properties[READ_COLUMN] = Contrast::Utils::StringUtils.force_utf8(field)
136
- dynamic_source.properties[WRITE_QUERY_TIME] =
137
- Contrast::Utils::StringUtils.force_utf8(Contrast::Utils::Timer.now_ms)
138
- dynamic_source.properties[WRITE_QUERY_URL] =
139
- Contrast::Utils::StringUtils.force_utf8(request&.normalized_uri)
140
- end
141
-
142
- def append_events! dynamic_source, event
143
- return unless event
144
-
145
- event.parent_events&.each do |parent_event|
146
- append_events(dynamic_source, parent_event)
147
- end
148
- dynamic_source.events << event.to_dtm_event
149
- end
150
95
  end
151
96
  end
152
97
  end
@@ -2,7 +2,7 @@
2
2
  # frozen_string_literal: true
3
3
 
4
4
  require 'contrast/agent/patching/policy/policy_node'
5
- require 'contrast/api/decorators/trace_taint_range_tags'
5
+ require 'contrast/agent/reporting/reporting_events/finding_event_taint_range_tags'
6
6
  require 'contrast/utils/object_share'
7
7
  require 'contrast/agent/assess/policy/policy_node_utils'
8
8
  require 'contrast/components/logger'
@@ -123,8 +123,8 @@ module Contrast
123
123
  return unless tags
124
124
 
125
125
  tags.each do |tag|
126
- next if Contrast::Api::Decorators::TraceTaintRangeTags::VALID_TAGS.include?(tag) ||
127
- Contrast::Api::Decorators::TraceTaintRangeTags::VALID_SOURCE_TAGS.include?(tag)
126
+ next if Contrast::Agent::Reporting::FindingEventTaintRangeTags::VALID_TAGS.include?(tag) ||
127
+ Contrast::Agent::Reporting::FindingEventTaintRangeTags::VALID_SOURCE_TAGS.include?(tag)
128
128
 
129
129
  raise(ArgumentError, "#{ node_class } #{ id } had an invalid tag. #{ tag } is not a known value.")
130
130
  end
@@ -2,7 +2,6 @@
2
2
  # frozen_string_literal: true
3
3
 
4
4
  require 'contrast/agent/patching/policy/policy_node'
5
- require 'contrast/api/decorators/trace_taint_range_tags'
6
5
  require 'contrast/utils/object_share'
7
6
 
8
7
  module Contrast
@@ -2,7 +2,7 @@
2
2
  # frozen_string_literal: true
3
3
 
4
4
  require 'contrast/agent/assess/policy/policy_node'
5
- require 'contrast/api/decorators/trace_taint_range_tags'
5
+ require 'contrast/agent/reporting/reporting_events/finding_event_taint_range_tags'
6
6
  require 'contrast/components/logger'
7
7
 
8
8
  module Contrast
@@ -22,8 +22,8 @@ module Contrast
22
22
  JSON_PATCH_CLASS = 'patch_class'
23
23
  JSON_PATCH_METHOD = 'patch_method'
24
24
 
25
- attr_reader :untags, :patch_method
26
- attr_accessor :action, :patch_class
25
+ attr_reader :action, :untags, :patch_method
26
+ attr_accessor :patch_class
27
27
 
28
28
  TAGGER = 'Tagger'
29
29
  PROPAGATOR = 'Propagator'
@@ -90,7 +90,7 @@ module Contrast
90
90
  return unless untags
91
91
 
92
92
  untags.each do |tag|
93
- unless Contrast::Api::Decorators::TraceTaintRangeTags::VALID_TAGS.include?(tag)
93
+ unless Contrast::Agent::Reporting::FindingEventTaintRangeTags::VALID_TAGS.include?(tag)
94
94
  raise(ArgumentError,
95
95
  "#{ node_type } #{ id } did not have a valid untag. #{ tag } is not a known value.")
96
96
  end
@@ -3,6 +3,7 @@
3
3
 
4
4
  require 'set'
5
5
  require 'contrast/agent/assess/policy/source_validation/source_validation'
6
+ require 'contrast/agent/excluder'
6
7
  require 'contrast/components/logger'
7
8
  require 'contrast/utils/object_share'
8
9
  require 'contrast/utils/sha256_builder'
@@ -28,6 +29,8 @@ module Contrast
28
29
  HEADER_KEY_TYPE = 'HEADER_KEY'
29
30
  COOKIE_TYPE = 'COOKIE'
30
31
  COOKIE_KEY_TYPE = 'COOKIE_KEY'
32
+ BODY_TYPE = 'BODY'
33
+ QUERYSTRING_TYPE = 'QUERYSTRING'
31
34
 
32
35
  class << self
33
36
  # This is called from within our woven proc. It will be called as if it were inline in the Rack application.
@@ -42,6 +45,7 @@ module Contrast
42
45
  return unless analyze?(method_policy, object, ret, args)
43
46
  return if event_limit?(method_policy)
44
47
  return unless (source_node = method_policy.source_node)
48
+ return if excluded_by_url?
45
49
 
46
50
  # used to hold the object and ret
47
51
  source_data = Contrast::Agent::Assess::Events::EventData.new(nil, nil, object, ret, nil)
@@ -66,13 +70,16 @@ module Contrast
66
70
  # @param source_name [String, nil] the name of this source, i.e. the key used to accessed if from a map or
67
71
  # nil if a type like BODY
68
72
  # @param args [Array<Object>] the Arguments with which the method was invoked
69
- def process_source source_node, target, source_data, source_type, source_name = nil, *args
73
+ def process_source source_node, target, source_data, source_type, source_name = nil, *args # rubocop:disable Metrics/PerceivedComplexity
70
74
  context = Contrast::Agent::REQUEST_TRACKER.current
71
75
  return unless context && source_node && target
72
76
 
73
77
  increment_event_count(source_node)
74
78
 
75
79
  source_name ||= determine_source_name(source_node, source_data.object, source_data.ret, *args)
80
+
81
+ return if excluded_by_input?(source_type, source_name)
82
+
76
83
  # We know we only work on certain things.
77
84
  # Skip if this isn't one of them
78
85
  if Contrast::Agent::Assess::Tracker.trackable?(target)
@@ -177,6 +184,22 @@ module Contrast
177
184
  source_type
178
185
  end
179
186
  end
187
+
188
+ # Should a source be excluded because it matches one of the input exclusion rules?
189
+ #
190
+ # @return [Boolean]
191
+ def excluded_by_input? source_type, source_name
192
+ context = Contrast::Agent::REQUEST_TRACKER.current
193
+ Contrast::SETTINGS.excluder.assess_excluded_by_input?(context.request, source_type, source_name)
194
+ end
195
+
196
+ # Should a source be excluded because it matches one of the url exclusion rules?
197
+ #
198
+ # @return [Boolean]
199
+ def excluded_by_url?
200
+ context = Contrast::Agent::REQUEST_TRACKER.current
201
+ Contrast::SETTINGS.excluder.assess_excluded_by_url?(context.request)
202
+ end
180
203
  end
181
204
  end
182
205
  end
@@ -38,6 +38,7 @@ module Contrast
38
38
  ret,
39
39
  interpolated_inputs)
40
40
  properties.build_event(event_data)
41
+ properties.copy_from(erb_template_prerender, ret, 0)
41
42
  unless interpolated_inputs.empty?
42
43
  current_event = properties.event
43
44
  interpolated_inputs.each do |input|
@@ -49,11 +50,12 @@ module Contrast
49
50
  end
50
51
 
51
52
  if Contrast::Agent::Assess::Tracker.tracked?(ret)
52
- Contrast::Agent::Assess::Policy::TriggerMethod.build_finding(trigger_node,
53
- ret,
54
- erb_template_prerender,
55
- ret,
56
- interpolated_inputs)
53
+ finding = Contrast::Agent::Assess::Policy::TriggerMethod.build_finding(trigger_node,
54
+ ret,
55
+ erb_template_prerender,
56
+ ret,
57
+ interpolated_inputs)
58
+ Contrast::Agent::Assess::Policy::TriggerMethod.report_finding(finding) if finding
57
59
  end
58
60
 
59
61
  ret
@@ -38,7 +38,12 @@ module Contrast
38
38
  next unless Contrast::Agent::Assess::Tracker.tracked?(arg)
39
39
  next unless trigger_node.violated?(arg)
40
40
 
41
- Contrast::Agent::Assess::Policy::TriggerMethod.build_finding(trigger_node, arg, object, ret, *args)
41
+ finding = Contrast::Agent::Assess::Policy::TriggerMethod.build_finding(trigger_node,
42
+ arg,
43
+ object,
44
+ ret,
45
+ *args)
46
+ Contrast::Agent::Assess::Policy::TriggerMethod.report_finding(finding) if finding
42
47
  end
43
48
 
44
49
  ret