contrast-agent 3.8.4
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 +7 -0
- data/.clang-format +5 -0
- data/.dockerignore +10 -0
- data/.gitignore +58 -0
- data/.gitmodules +6 -0
- data/.rspec +6 -0
- data/.simplecov +4 -0
- data/Gemfile +7 -0
- data/LICENSE.txt +12 -0
- data/Rakefile +15 -0
- data/exe/contrast_service +29 -0
- data/ext/build_funchook.rb +48 -0
- data/ext/cs__assess_active_record_named/cs__active_record_named.c +47 -0
- data/ext/cs__assess_active_record_named/cs__active_record_named.h +10 -0
- data/ext/cs__assess_active_record_named/extconf.rb +2 -0
- data/ext/cs__assess_array/cs__assess_array.c +38 -0
- data/ext/cs__assess_array/cs__assess_array.h +9 -0
- data/ext/cs__assess_array/extconf.rb +2 -0
- data/ext/cs__assess_basic_object/cs__assess_basic_object.c +50 -0
- data/ext/cs__assess_basic_object/cs__assess_basic_object.h +17 -0
- data/ext/cs__assess_basic_object/extconf.rb +2 -0
- data/ext/cs__assess_fiber_track/cs__assess_fiber_track.c +86 -0
- data/ext/cs__assess_fiber_track/cs__assess_fiber_track.h +34 -0
- data/ext/cs__assess_fiber_track/extconf.rb +2 -0
- data/ext/cs__assess_hash/cs__assess_hash.c +64 -0
- data/ext/cs__assess_hash/cs__assess_hash.h +24 -0
- data/ext/cs__assess_hash/extconf.rb +2 -0
- data/ext/cs__assess_kernel/cs__assess_kernel.c +36 -0
- data/ext/cs__assess_kernel/cs__assess_kernel.h +10 -0
- data/ext/cs__assess_kernel/extconf.rb +2 -0
- data/ext/cs__assess_marshal_module/cs__assess_marshal_module.c +47 -0
- data/ext/cs__assess_marshal_module/cs__assess_marshal_module.h +18 -0
- data/ext/cs__assess_marshal_module/extconf.rb +2 -0
- data/ext/cs__assess_module/cs__assess_module.c +78 -0
- data/ext/cs__assess_module/cs__assess_module.h +25 -0
- data/ext/cs__assess_module/extconf.rb +2 -0
- data/ext/cs__assess_regexp/cs__assess_regexp.c +48 -0
- data/ext/cs__assess_regexp/cs__assess_regexp.h +22 -0
- data/ext/cs__assess_regexp/extconf.rb +2 -0
- data/ext/cs__assess_regexp_track/cs__assess_regexp_track.c +63 -0
- data/ext/cs__assess_regexp_track/cs__assess_regexp_track.h +29 -0
- data/ext/cs__assess_regexp_track/extconf.rb +2 -0
- data/ext/cs__assess_string/cs__assess_string.c +38 -0
- data/ext/cs__assess_string/cs__assess_string.h +19 -0
- data/ext/cs__assess_string/extconf.rb +2 -0
- data/ext/cs__assess_string_interpolation26/cs__assess_string_interpolation26.c +31 -0
- data/ext/cs__assess_string_interpolation26/cs__assess_string_interpolation26.h +13 -0
- data/ext/cs__assess_string_interpolation26/extconf.rb +2 -0
- data/ext/cs__common/cs__common.c +60 -0
- data/ext/cs__common/cs__common.h +28 -0
- data/ext/cs__common/extconf.rb +20 -0
- data/ext/cs__contrast_patch/cs__contrast_patch.c +445 -0
- data/ext/cs__contrast_patch/cs__contrast_patch.h +196 -0
- data/ext/cs__contrast_patch/extconf.rb +2 -0
- data/ext/cs__protect_kernel/cs__protect_kernel.c +37 -0
- data/ext/cs__protect_kernel/cs__protect_kernel.h +11 -0
- data/ext/cs__protect_kernel/extconf.rb +2 -0
- data/ext/cs__scope/cs__scope.c +96 -0
- data/ext/cs__scope/cs__scope.h +33 -0
- data/ext/cs__scope/extconf.rb +2 -0
- data/ext/extconf_common.rb +49 -0
- data/funchook/LICENSE +360 -0
- data/funchook/Makefile +29 -0
- data/funchook/Makefile.in +29 -0
- data/funchook/README.md +121 -0
- data/funchook/appveyor.yml +42 -0
- data/funchook/autogen.sh +3 -0
- data/funchook/autom4te.cache/output.0 +4976 -0
- data/funchook/autom4te.cache/requests +78 -0
- data/funchook/autom4te.cache/traces.0 +364 -0
- data/funchook/config.guess +1530 -0
- data/funchook/config.log +490 -0
- data/funchook/config.status +1016 -0
- data/funchook/config.sub +1773 -0
- data/funchook/configure +4976 -0
- data/funchook/configure.ac +59 -0
- data/funchook/distorm/COPYING +26 -0
- data/funchook/distorm/MANIFEST +25 -0
- data/funchook/distorm/MANIFEST.in +4 -0
- data/funchook/distorm/README.md +12 -0
- data/funchook/distorm/disOps/disOps.py +795 -0
- data/funchook/distorm/disOps/x86db.py +404 -0
- data/funchook/distorm/disOps/x86header.py +247 -0
- data/funchook/distorm/disOps/x86sets.py +1664 -0
- data/funchook/distorm/examples/cs/TestdiStorm/Program.cs +79 -0
- data/funchook/distorm/examples/cs/TestdiStorm/Properties/AssemblyInfo.cs +36 -0
- data/funchook/distorm/examples/cs/TestdiStorm/TestdiStorm.csproj +69 -0
- data/funchook/distorm/examples/cs/distorm-net.sln +26 -0
- data/funchook/distorm/examples/cs/distorm-net/CodeInfo.cs +23 -0
- data/funchook/distorm/examples/cs/distorm-net/DecodedInst.cs +15 -0
- data/funchook/distorm/examples/cs/distorm-net/DecodedResult.cs +14 -0
- data/funchook/distorm/examples/cs/distorm-net/DecomposedInst.cs +36 -0
- data/funchook/distorm/examples/cs/distorm-net/DecomposedResult.cs +14 -0
- data/funchook/distorm/examples/cs/distorm-net/Opcodes.cs +1268 -0
- data/funchook/distorm/examples/cs/distorm-net/Opcodes.tt +37 -0
- data/funchook/distorm/examples/cs/distorm-net/Operand.cs +25 -0
- data/funchook/distorm/examples/cs/distorm-net/Properties/AssemblyInfo.cs +36 -0
- data/funchook/distorm/examples/cs/distorm-net/diStorm3.cs +411 -0
- data/funchook/distorm/examples/cs/distorm-net/distorm-net.csproj +80 -0
- data/funchook/distorm/examples/cs/readme +3 -0
- data/funchook/distorm/examples/ddk/README +48 -0
- data/funchook/distorm/examples/ddk/distorm.ini +11 -0
- data/funchook/distorm/examples/ddk/dummy.c +15 -0
- data/funchook/distorm/examples/ddk/main.c +91 -0
- data/funchook/distorm/examples/ddk/makefile +1 -0
- data/funchook/distorm/examples/ddk/sources +10 -0
- data/funchook/distorm/examples/java/Makefile +23 -0
- data/funchook/distorm/examples/java/distorm/src/Main.java +43 -0
- data/funchook/distorm/examples/java/distorm/src/diStorm3/CodeInfo.java +27 -0
- data/funchook/distorm/examples/java/distorm/src/diStorm3/DecodedInst.java +32 -0
- data/funchook/distorm/examples/java/distorm/src/diStorm3/DecodedResult.java +11 -0
- data/funchook/distorm/examples/java/distorm/src/diStorm3/DecomposedInst.java +89 -0
- data/funchook/distorm/examples/java/distorm/src/diStorm3/DecomposedResult.java +11 -0
- data/funchook/distorm/examples/java/distorm/src/diStorm3/OpcodeEnum.java +131 -0
- data/funchook/distorm/examples/java/distorm/src/diStorm3/Opcodes.java +1123 -0
- data/funchook/distorm/examples/java/distorm/src/diStorm3/Operand.java +24 -0
- data/funchook/distorm/examples/java/distorm/src/diStorm3/distorm3.java +41 -0
- data/funchook/distorm/examples/java/jdistorm.c +405 -0
- data/funchook/distorm/examples/java/jdistorm.h +40 -0
- data/funchook/distorm/examples/java/jdistorm.sln +20 -0
- data/funchook/distorm/examples/java/jdistorm.vcproj +208 -0
- data/funchook/distorm/examples/linux/Makefile +15 -0
- data/funchook/distorm/examples/linux/main.c +181 -0
- data/funchook/distorm/examples/tests/Makefile +15 -0
- data/funchook/distorm/examples/tests/main.cpp +42 -0
- data/funchook/distorm/examples/tests/main.py +66 -0
- data/funchook/distorm/examples/tests/test_distorm3.py +1672 -0
- data/funchook/distorm/examples/tests/tests.sln +20 -0
- data/funchook/distorm/examples/tests/tests.vcxproj +82 -0
- data/funchook/distorm/examples/tests/tests.vcxproj.filters +22 -0
- data/funchook/distorm/examples/win32/disasm.sln +25 -0
- data/funchook/distorm/examples/win32/disasm.vcxproj +201 -0
- data/funchook/distorm/examples/win32/disasm.vcxproj.filters +14 -0
- data/funchook/distorm/examples/win32/main.cpp +163 -0
- data/funchook/distorm/include/distorm.h +482 -0
- data/funchook/distorm/include/mnemonics.h +301 -0
- data/funchook/distorm/make/linux/Makefile +28 -0
- data/funchook/distorm/make/mac/Makefile +24 -0
- data/funchook/distorm/make/win32/cdistorm.vcxproj +239 -0
- data/funchook/distorm/make/win32/cdistorm.vcxproj.filters +80 -0
- data/funchook/distorm/make/win32/distorm.sln +25 -0
- data/funchook/distorm/make/win32/resource.h +14 -0
- data/funchook/distorm/make/win32/resource.rc +99 -0
- data/funchook/distorm/python/distorm3/__init__.py +957 -0
- data/funchook/distorm/python/distorm3/sample.py +51 -0
- data/funchook/distorm/setup.cfg +10 -0
- data/funchook/distorm/setup.py +266 -0
- data/funchook/distorm/src/config.h +169 -0
- data/funchook/distorm/src/decoder.c +641 -0
- data/funchook/distorm/src/decoder.h +33 -0
- data/funchook/distorm/src/distorm.c +413 -0
- data/funchook/distorm/src/instructions.c +597 -0
- data/funchook/distorm/src/instructions.h +463 -0
- data/funchook/distorm/src/insts.c +7939 -0
- data/funchook/distorm/src/insts.h +64 -0
- data/funchook/distorm/src/mnemonics.c +284 -0
- data/funchook/distorm/src/operands.c +1290 -0
- data/funchook/distorm/src/operands.h +28 -0
- data/funchook/distorm/src/prefix.c +368 -0
- data/funchook/distorm/src/prefix.h +64 -0
- data/funchook/distorm/src/textdefs.c +172 -0
- data/funchook/distorm/src/textdefs.h +57 -0
- data/funchook/distorm/src/wstring.c +47 -0
- data/funchook/distorm/src/wstring.h +35 -0
- data/funchook/distorm/src/x86defs.h +82 -0
- data/funchook/include/funchook.h +123 -0
- data/funchook/install-sh +527 -0
- data/funchook/src/Makefile +70 -0
- data/funchook/src/Makefile.in +70 -0
- data/funchook/src/__strerror.h +109 -0
- data/funchook/src/config.h +101 -0
- data/funchook/src/config.h.in +100 -0
- data/funchook/src/decoder.o +0 -0
- data/funchook/src/distorm.o +0 -0
- data/funchook/src/funchook.c +440 -0
- data/funchook/src/funchook.o +0 -0
- data/funchook/src/funchook_internal.h +155 -0
- data/funchook/src/funchook_io.c +182 -0
- data/funchook/src/funchook_io.h +64 -0
- data/funchook/src/funchook_io.o +0 -0
- data/funchook/src/funchook_syscall.S +134 -0
- data/funchook/src/funchook_syscall.o +0 -0
- data/funchook/src/funchook_unix.c +480 -0
- data/funchook/src/funchook_unix.o +0 -0
- data/funchook/src/funchook_windows.c +397 -0
- data/funchook/src/funchook_x86.c +622 -0
- data/funchook/src/funchook_x86.o +0 -0
- data/funchook/src/instructions.o +0 -0
- data/funchook/src/insts.o +0 -0
- data/funchook/src/libfunchook.so +0 -0
- data/funchook/src/mnemonics.o +0 -0
- data/funchook/src/operands.o +0 -0
- data/funchook/src/os_func.c +115 -0
- data/funchook/src/os_func.h +75 -0
- data/funchook/src/os_func.o +0 -0
- data/funchook/src/os_func_unix.c +94 -0
- data/funchook/src/os_func_unix.o +0 -0
- data/funchook/src/os_func_windows.c +32 -0
- data/funchook/src/prefix.o +0 -0
- data/funchook/src/printf_base.c +1688 -0
- data/funchook/src/printf_base.h +46 -0
- data/funchook/src/printf_base.o +0 -0
- data/funchook/src/textdefs.o +0 -0
- data/funchook/src/wstring.o +0 -0
- data/funchook/test/Makefile +43 -0
- data/funchook/test/Makefile.in +43 -0
- data/funchook/test/funchook_test +0 -0
- data/funchook/test/libfunchook_test.c +25 -0
- data/funchook/test/libfunchook_test.so +0 -0
- data/funchook/test/libfunchook_test2.c +18 -0
- data/funchook/test/suffix.list +600 -0
- data/funchook/test/test_main.c +430 -0
- data/funchook/test/test_main.o +0 -0
- data/funchook/test/x86_64_test.S +10 -0
- data/funchook/test/x86_64_test.o +0 -0
- data/funchook/test/x86_test.S +339 -0
- data/funchook/win32/config.h +1 -0
- data/funchook/win32/funchook.sln +52 -0
- data/funchook/win32/funchook.vcxproj +188 -0
- data/funchook/win32/funchook.vcxproj.filters +84 -0
- data/funchook/win32/funchook_test.vcxproj +170 -0
- data/funchook/win32/funchook_test.vcxproj.filters +22 -0
- data/funchook/win32/funchook_test_dll.vcxproj +184 -0
- data/funchook/win32/funchook_test_dll.vcxproj.filters +30 -0
- data/funchook/win32/funchook_test_exe.def +3 -0
- data/lib/contrast-agent.rb +8 -0
- data/lib/contrast.rb +57 -0
- data/lib/contrast/agent.rb +80 -0
- data/lib/contrast/agent/assess.rb +45 -0
- data/lib/contrast/agent/assess/adjusted_span.rb +25 -0
- data/lib/contrast/agent/assess/class_reverter.rb +82 -0
- data/lib/contrast/agent/assess/contrast_event.rb +398 -0
- data/lib/contrast/agent/assess/frozen_properties.rb +41 -0
- data/lib/contrast/agent/assess/insulator.rb +53 -0
- data/lib/contrast/agent/assess/policy/dynamic_source_factory.rb +78 -0
- data/lib/contrast/agent/assess/policy/patcher.rb +85 -0
- data/lib/contrast/agent/assess/policy/policy.rb +116 -0
- data/lib/contrast/agent/assess/policy/policy_node.rb +289 -0
- data/lib/contrast/agent/assess/policy/policy_scanner.rb +44 -0
- data/lib/contrast/agent/assess/policy/preshift.rb +94 -0
- data/lib/contrast/agent/assess/policy/propagation_method.rb +260 -0
- data/lib/contrast/agent/assess/policy/propagation_node.rb +127 -0
- data/lib/contrast/agent/assess/policy/propagator.rb +35 -0
- data/lib/contrast/agent/assess/policy/propagator/append.rb +54 -0
- data/lib/contrast/agent/assess/policy/propagator/base.rb +37 -0
- data/lib/contrast/agent/assess/policy/propagator/center.rb +73 -0
- data/lib/contrast/agent/assess/policy/propagator/custom.rb +36 -0
- data/lib/contrast/agent/assess/policy/propagator/database_write.rb +62 -0
- data/lib/contrast/agent/assess/policy/propagator/insert.rb +55 -0
- data/lib/contrast/agent/assess/policy/propagator/keep.rb +26 -0
- data/lib/contrast/agent/assess/policy/propagator/next.rb +42 -0
- data/lib/contrast/agent/assess/policy/propagator/prepend.rb +50 -0
- data/lib/contrast/agent/assess/policy/propagator/remove.rb +76 -0
- data/lib/contrast/agent/assess/policy/propagator/replace.rb +27 -0
- data/lib/contrast/agent/assess/policy/propagator/reverse.rb +38 -0
- data/lib/contrast/agent/assess/policy/propagator/select.rb +86 -0
- data/lib/contrast/agent/assess/policy/propagator/splat.rb +60 -0
- data/lib/contrast/agent/assess/policy/propagator/split.rb +49 -0
- data/lib/contrast/agent/assess/policy/propagator/substitution.rb +169 -0
- data/lib/contrast/agent/assess/policy/propagator/trim.rb +81 -0
- data/lib/contrast/agent/assess/policy/rewriter_patch.rb +79 -0
- data/lib/contrast/agent/assess/policy/source_method.rb +209 -0
- data/lib/contrast/agent/assess/policy/source_node.rb +62 -0
- data/lib/contrast/agent/assess/policy/trigger_method.rb +209 -0
- data/lib/contrast/agent/assess/policy/trigger_node.rb +198 -0
- data/lib/contrast/agent/assess/policy/trigger_validation/ssrf_validator.rb +77 -0
- data/lib/contrast/agent/assess/policy/trigger_validation/trigger_validation.rb +31 -0
- data/lib/contrast/agent/assess/policy/trigger_validation/xss_validator.rb +40 -0
- data/lib/contrast/agent/assess/properties.rb +392 -0
- data/lib/contrast/agent/assess/rule.rb +18 -0
- data/lib/contrast/agent/assess/rule/base.rb +72 -0
- data/lib/contrast/agent/assess/rule/csrf.rb +66 -0
- data/lib/contrast/agent/assess/rule/csrf/csrf_action.rb +28 -0
- data/lib/contrast/agent/assess/rule/csrf/csrf_applicator.rb +69 -0
- data/lib/contrast/agent/assess/rule/csrf/csrf_watcher.rb +132 -0
- data/lib/contrast/agent/assess/rule/provider.rb +21 -0
- data/lib/contrast/agent/assess/rule/provider/hardcoded_key.rb +62 -0
- data/lib/contrast/agent/assess/rule/provider/hardcoded_password.rb +73 -0
- data/lib/contrast/agent/assess/rule/provider/hardcoded_value_rule.rb +121 -0
- data/lib/contrast/agent/assess/rule/redos.rb +68 -0
- data/lib/contrast/agent/assess/rule/response_scanning_rule.rb +47 -0
- data/lib/contrast/agent/assess/rule/response_watcher.rb +36 -0
- data/lib/contrast/agent/assess/rule/watcher.rb +36 -0
- data/lib/contrast/agent/assess/tag.rb +151 -0
- data/lib/contrast/agent/at_exit_hook.rb +33 -0
- data/lib/contrast/agent/class_reopener.rb +195 -0
- data/lib/contrast/agent/deadzone/policy/deadzone_node.rb +26 -0
- data/lib/contrast/agent/deadzone/policy/policy.rb +57 -0
- data/lib/contrast/agent/disable_reaction.rb +24 -0
- data/lib/contrast/agent/exclusion_matcher.rb +190 -0
- data/lib/contrast/agent/feature_state.rb +379 -0
- data/lib/contrast/agent/inventory/policy/policy.rb +32 -0
- data/lib/contrast/agent/inventory/policy/trigger_node.rb +22 -0
- data/lib/contrast/agent/logger_manager.rb +116 -0
- data/lib/contrast/agent/middleware.rb +352 -0
- data/lib/contrast/agent/module_data.rb +16 -0
- data/lib/contrast/agent/patching/policy/after_load_patch.rb +37 -0
- data/lib/contrast/agent/patching/policy/after_load_patcher.rb +58 -0
- data/lib/contrast/agent/patching/policy/method_policy.rb +94 -0
- data/lib/contrast/agent/patching/policy/module_policy.rb +116 -0
- data/lib/contrast/agent/patching/policy/patch.rb +312 -0
- data/lib/contrast/agent/patching/policy/patch_status.rb +192 -0
- data/lib/contrast/agent/patching/policy/patcher.rb +310 -0
- data/lib/contrast/agent/patching/policy/policy.rb +138 -0
- data/lib/contrast/agent/patching/policy/policy_node.rb +80 -0
- data/lib/contrast/agent/patching/policy/policy_unpatcher.rb +28 -0
- data/lib/contrast/agent/patching/policy/trigger_node.rb +81 -0
- data/lib/contrast/agent/protect/policy/policy.rb +37 -0
- data/lib/contrast/agent/protect/policy/trigger_node.rb +23 -0
- data/lib/contrast/agent/protect/rule.rb +58 -0
- data/lib/contrast/agent/protect/rule/base.rb +300 -0
- data/lib/contrast/agent/protect/rule/base_service.rb +88 -0
- data/lib/contrast/agent/protect/rule/cmd_injection.rb +156 -0
- data/lib/contrast/agent/protect/rule/csrf.rb +118 -0
- data/lib/contrast/agent/protect/rule/csrf/csrf_evaluator.rb +103 -0
- data/lib/contrast/agent/protect/rule/csrf/csrf_token_injector.rb +85 -0
- data/lib/contrast/agent/protect/rule/default_scanner.rb +300 -0
- data/lib/contrast/agent/protect/rule/deserialization.rb +193 -0
- data/lib/contrast/agent/protect/rule/http_method_tampering.rb +80 -0
- data/lib/contrast/agent/protect/rule/no_sqli.rb +101 -0
- data/lib/contrast/agent/protect/rule/no_sqli/mongo_no_sql_scanner.rb +40 -0
- data/lib/contrast/agent/protect/rule/path_traversal.rb +143 -0
- data/lib/contrast/agent/protect/rule/sqli.rb +101 -0
- data/lib/contrast/agent/protect/rule/sqli/default_sql_scanner.rb +16 -0
- data/lib/contrast/agent/protect/rule/sqli/mysql_sql_scanner.rb +38 -0
- data/lib/contrast/agent/protect/rule/sqli/postgres_sql_scanner.rb +22 -0
- data/lib/contrast/agent/protect/rule/sqli/sqlite_sql_scanner.rb +19 -0
- data/lib/contrast/agent/protect/rule/unsafe_file_upload.rb +20 -0
- data/lib/contrast/agent/protect/rule/xss.rb +24 -0
- data/lib/contrast/agent/protect/rule/xxe.rb +120 -0
- data/lib/contrast/agent/protect/rule/xxe/entity_wrapper.rb +82 -0
- data/lib/contrast/agent/railtie.rb +30 -0
- data/lib/contrast/agent/reaction_processor.rb +47 -0
- data/lib/contrast/agent/request.rb +493 -0
- data/lib/contrast/agent/request_context.rb +225 -0
- data/lib/contrast/agent/require_state.rb +61 -0
- data/lib/contrast/agent/response.rb +215 -0
- data/lib/contrast/agent/rewriter.rb +244 -0
- data/lib/contrast/agent/scope.rb +28 -0
- data/lib/contrast/agent/service_heartbeat.rb +37 -0
- data/lib/contrast/agent/settings_state.rb +148 -0
- data/lib/contrast/agent/socket_client.rb +125 -0
- data/lib/contrast/agent/thread.rb +26 -0
- data/lib/contrast/agent/tracepoint_hook.rb +51 -0
- data/lib/contrast/agent/version.rb +8 -0
- data/lib/contrast/api.rb +17 -0
- data/lib/contrast/api/.gitkeep +0 -0
- data/lib/contrast/api/connection_status.rb +49 -0
- data/lib/contrast/api/socket.rb +43 -0
- data/lib/contrast/api/speedracer.rb +206 -0
- data/lib/contrast/api/tcp_socket.rb +31 -0
- data/lib/contrast/api/unix_socket.rb +25 -0
- data/lib/contrast/common_agent_configuration.rb +86 -0
- data/lib/contrast/components/agent.rb +85 -0
- data/lib/contrast/components/app_context.rb +188 -0
- data/lib/contrast/components/assess.rb +67 -0
- data/lib/contrast/components/config.rb +135 -0
- data/lib/contrast/components/contrast_service.rb +113 -0
- data/lib/contrast/components/heap_dump.rb +34 -0
- data/lib/contrast/components/interface.rb +178 -0
- data/lib/contrast/components/inventory.rb +23 -0
- data/lib/contrast/components/logger.rb +92 -0
- data/lib/contrast/components/protect.rb +38 -0
- data/lib/contrast/components/sampling.rb +41 -0
- data/lib/contrast/components/scope.rb +106 -0
- data/lib/contrast/components/settings.rb +140 -0
- data/lib/contrast/config.rb +33 -0
- data/lib/contrast/config/agent_configuration.rb +24 -0
- data/lib/contrast/config/application_configuration.rb +27 -0
- data/lib/contrast/config/assess_configuration.rb +22 -0
- data/lib/contrast/config/assess_rules_configuration.rb +18 -0
- data/lib/contrast/config/base_configuration.rb +105 -0
- data/lib/contrast/config/default_value.rb +16 -0
- data/lib/contrast/config/exception_configuration.rb +21 -0
- data/lib/contrast/config/heap_dump_configuration.rb +23 -0
- data/lib/contrast/config/inventory_configuration.rb +20 -0
- data/lib/contrast/config/logger_configuration.rb +20 -0
- data/lib/contrast/config/protect_configuration.rb +20 -0
- data/lib/contrast/config/protect_rule_configuration.rb +37 -0
- data/lib/contrast/config/protect_rules_configuration.rb +30 -0
- data/lib/contrast/config/root_configuration.rb +26 -0
- data/lib/contrast/config/ruby_configuration.rb +39 -0
- data/lib/contrast/config/sampling_configuration.rb +22 -0
- data/lib/contrast/config/server_configuration.rb +23 -0
- data/lib/contrast/config/service_configuration.rb +22 -0
- data/lib/contrast/configuration.rb +214 -0
- data/lib/contrast/core_extensions/assess.rb +51 -0
- data/lib/contrast/core_extensions/assess/array.rb +58 -0
- data/lib/contrast/core_extensions/assess/assess_extension.rb +145 -0
- data/lib/contrast/core_extensions/assess/basic_object.rb +15 -0
- data/lib/contrast/core_extensions/assess/erb.rb +42 -0
- data/lib/contrast/core_extensions/assess/exec_trigger.rb +48 -0
- data/lib/contrast/core_extensions/assess/fiber.rb +125 -0
- data/lib/contrast/core_extensions/assess/hash.rb +22 -0
- data/lib/contrast/core_extensions/assess/kernel.rb +95 -0
- data/lib/contrast/core_extensions/assess/module.rb +14 -0
- data/lib/contrast/core_extensions/assess/regexp.rb +206 -0
- data/lib/contrast/core_extensions/assess/string.rb +75 -0
- data/lib/contrast/core_extensions/assess/tilt_template_trigger.rb +73 -0
- data/lib/contrast/core_extensions/delegator.rb +14 -0
- data/lib/contrast/core_extensions/eval_trigger.rb +52 -0
- data/lib/contrast/core_extensions/inventory.rb +22 -0
- data/lib/contrast/core_extensions/inventory/datastores.rb +37 -0
- data/lib/contrast/core_extensions/module.rb +42 -0
- data/lib/contrast/core_extensions/object.rb +27 -0
- data/lib/contrast/core_extensions/protect.rb +20 -0
- data/lib/contrast/core_extensions/protect/applies_command_injection_rule.rb +70 -0
- data/lib/contrast/core_extensions/protect/applies_deserialization_rule.rb +58 -0
- data/lib/contrast/core_extensions/protect/applies_no_sqli_rule.rb +81 -0
- data/lib/contrast/core_extensions/protect/applies_path_traversal_rule.rb +119 -0
- data/lib/contrast/core_extensions/protect/applies_sqli_rule.rb +63 -0
- data/lib/contrast/core_extensions/protect/applies_xxe_rule.rb +141 -0
- data/lib/contrast/core_extensions/protect/kernel.rb +30 -0
- data/lib/contrast/core_extensions/protect/psych.rb +7 -0
- data/lib/contrast/core_extensions/thread.rb +31 -0
- data/lib/contrast/internal_exception.rb +8 -0
- data/lib/contrast/rails_extensions/assess/action_controller_inheritance.rb +48 -0
- data/lib/contrast/rails_extensions/assess/active_record.rb +32 -0
- data/lib/contrast/rails_extensions/assess/active_record_named.rb +61 -0
- data/lib/contrast/rails_extensions/assess/configuration.rb +26 -0
- data/lib/contrast/rails_extensions/buffer.rb +30 -0
- data/lib/contrast/rails_extensions/rack.rb +45 -0
- data/lib/contrast/security_exception.rb +14 -0
- data/lib/contrast/sinatra_extensions/assess/cookie.rb +26 -0
- data/lib/contrast/sinatra_extensions/inventory/sinatra_base.rb +59 -0
- data/lib/contrast/tasks/service.rb +95 -0
- data/lib/contrast/utils/assess/sampling_util.rb +96 -0
- data/lib/contrast/utils/assess/tracking_util.rb +39 -0
- data/lib/contrast/utils/boolean_util.rb +33 -0
- data/lib/contrast/utils/cache.rb +69 -0
- data/lib/contrast/utils/class_util.rb +58 -0
- data/lib/contrast/utils/comment_range.rb +19 -0
- data/lib/contrast/utils/data_store_util.rb +23 -0
- data/lib/contrast/utils/duck_utils.rb +58 -0
- data/lib/contrast/utils/env_configuration_item.rb +52 -0
- data/lib/contrast/utils/environment_util.rb +152 -0
- data/lib/contrast/utils/freeze_util.rb +36 -0
- data/lib/contrast/utils/gemfile_reader.rb +191 -0
- data/lib/contrast/utils/hash_digest.rb +148 -0
- data/lib/contrast/utils/heap_dump_util.rb +113 -0
- data/lib/contrast/utils/invalid_configuration_util.rb +88 -0
- data/lib/contrast/utils/inventory_util.rb +126 -0
- data/lib/contrast/utils/io_util.rb +61 -0
- data/lib/contrast/utils/object_share.rb +117 -0
- data/lib/contrast/utils/operating_environment.rb +38 -0
- data/lib/contrast/utils/os.rb +49 -0
- data/lib/contrast/utils/path_util.rb +151 -0
- data/lib/contrast/utils/performs_logging.rb +152 -0
- data/lib/contrast/utils/preflight_util.rb +13 -0
- data/lib/contrast/utils/prevent_serialization.rb +52 -0
- data/lib/contrast/utils/rack_assess_session_cookie.rb +104 -0
- data/lib/contrast/utils/rails_assess_configuration.rb +95 -0
- data/lib/contrast/utils/random_util.rb +22 -0
- data/lib/contrast/utils/resource_loader.rb +23 -0
- data/lib/contrast/utils/ruby_ast_rewriter.rb +74 -0
- data/lib/contrast/utils/scope_util.rb +99 -0
- data/lib/contrast/utils/service_response_util.rb +116 -0
- data/lib/contrast/utils/service_sender_util.rb +98 -0
- data/lib/contrast/utils/sha256_builder.rb +69 -0
- data/lib/contrast/utils/sinatra_helper.rb +49 -0
- data/lib/contrast/utils/stack_trace_utils.rb +209 -0
- data/lib/contrast/utils/string_utils.rb +72 -0
- data/lib/contrast/utils/tag_util.rb +139 -0
- data/lib/contrast/utils/thread_tracker.rb +54 -0
- data/lib/contrast/utils/timer.rb +78 -0
- data/resources/assess/policy.json +1673 -0
- data/resources/csrf/inject.js +44 -0
- data/resources/deadzone/policy.json +55 -0
- data/resources/factory-bot-spec/spec_helper.rb +30 -0
- data/resources/inventory/policy.json +110 -0
- data/resources/protect/policy.json +417 -0
- data/resources/rubocops/kernel/catch_cop.rb +37 -0
- data/resources/rubocops/kernel/require_cop.rb +37 -0
- data/resources/rubocops/kernel/require_relative_cop.rb +33 -0
- data/resources/rubocops/module/autoload_cop.rb +37 -0
- data/resources/rubocops/module/const_defined_cop.rb +37 -0
- data/resources/rubocops/module/const_get_cop.rb +37 -0
- data/resources/rubocops/module/const_set_cop.rb +37 -0
- data/resources/rubocops/module/constants_cop.rb +37 -0
- data/resources/rubocops/module/name_cop.rb +37 -0
- data/resources/rubocops/object/class_cop.rb +37 -0
- data/resources/rubocops/object/freeze_cop.rb +37 -0
- data/resources/rubocops/object/frozen_cop.rb +37 -0
- data/resources/rubocops/object/is_a_cop.rb +37 -0
- data/resources/rubocops/object/method_cop.rb +37 -0
- data/resources/rubocops/object/respond_to_cop.rb +37 -0
- data/resources/rubocops/object/singleton_class_cop.rb +37 -0
- data/resources/rubocops/regexp/spelling_cop.rb +44 -0
- data/resources/rubocops/thread/new_cop.rb +39 -0
- data/resources/ruby-spec/ancestors_spec.rb +70 -0
- data/resources/ruby-spec/modulo_spec.rb +831 -0
- data/resources/ruby-spec/parameters_spec.rb +261 -0
- data/resources/ruby-spec/ruby_spec_spec_helper.rb +35 -0
- data/resources/test_marker.txt +1 -0
- data/ruby-agent.gemspec +129 -0
- data/service_executables/.gitkeep +0 -0
- data/service_executables/VERSION +1 -0
- data/service_executables/linux/contrast-service +0 -0
- data/service_executables/mac/contrast-service +0 -0
- metadata +945 -0
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
# Copyright (c) 2020 Contrast Security, Inc. See https://www.contrastsecurity.com/enduser-terms-0317a for more details.
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
cs__scoped_require 'json'
|
|
5
|
+
cs__scoped_require 'contrast'
|
|
6
|
+
cs__scoped_require 'contrast/components/interface'
|
|
7
|
+
cs__scoped_require 'contrast/agent/patching/policy/module_policy'
|
|
8
|
+
cs__scoped_require 'contrast/agent/patching/policy/method_policy'
|
|
9
|
+
|
|
10
|
+
module Contrast
|
|
11
|
+
module Agent
|
|
12
|
+
module Patching
|
|
13
|
+
module Policy
|
|
14
|
+
# This is just a holder for our policy. Takes the policy JSON and
|
|
15
|
+
# converts it into hashes that we can access nicely
|
|
16
|
+
# @abstract
|
|
17
|
+
class Policy
|
|
18
|
+
include Singleton
|
|
19
|
+
include Contrast::Components::Interface
|
|
20
|
+
|
|
21
|
+
# Indicates the folder in `resources` where this policy lives.
|
|
22
|
+
def self.policy_folder
|
|
23
|
+
raise(NotImplementedError, 'specify policy_folder for patching')
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
# Indicates is this feature has been disabled by the configuration,
|
|
27
|
+
# read at startup, and therefore can never be enabled.
|
|
28
|
+
def disabled_globally?
|
|
29
|
+
raise(NotImplementedError, 'specify disabled_globally? conditions for patching')
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
def node_type
|
|
33
|
+
raise(NotImplementedError, 'specify the concrete node type for this poilcy')
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
access_component :logging, :analysis
|
|
37
|
+
|
|
38
|
+
attr_accessor :providers, :tracked_classes
|
|
39
|
+
attr_reader :sources, :propagators, :triggers, :patched_names
|
|
40
|
+
|
|
41
|
+
SOURCES_KEY = 'sources'
|
|
42
|
+
PROPAGATION_KEY = 'propagators'
|
|
43
|
+
RULES_KEY = 'rules'
|
|
44
|
+
TRIGGERS_KEY = 'triggers'
|
|
45
|
+
TRACKED_CLASSES_KEY = 'tracked_classes'
|
|
46
|
+
|
|
47
|
+
def self.policy_json
|
|
48
|
+
File.join(policy_folder, 'policy.json').cs__freeze
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
def initialize
|
|
52
|
+
@sources = []
|
|
53
|
+
@propagators = []
|
|
54
|
+
@triggers = []
|
|
55
|
+
@providers = {}
|
|
56
|
+
@tracked_classes = []
|
|
57
|
+
@patched_names = Set.new
|
|
58
|
+
|
|
59
|
+
json = Contrast::Utils::ResourceLoader.load(cs__class.policy_json)
|
|
60
|
+
from_hash_string(json)
|
|
61
|
+
end
|
|
62
|
+
|
|
63
|
+
# Our policy for patching rules is a 'dope ass' JSON file. Rather than
|
|
64
|
+
# hard code in a bunch of things to monkey patch, we let the JSON file
|
|
65
|
+
# define the conditions in which modifications are applied.
|
|
66
|
+
# This let's us be flexible and extensible.
|
|
67
|
+
def from_hash_string string
|
|
68
|
+
# The default behavior of the agent is to load the policy on startup,
|
|
69
|
+
# as at this point we do not know in which mode we'll be run.
|
|
70
|
+
#
|
|
71
|
+
# If the configuration file explicitly disables a feature, we know
|
|
72
|
+
# that we will not ever be able to enable it, so in that case, we
|
|
73
|
+
# can skip policy loading.
|
|
74
|
+
return if disabled_globally?
|
|
75
|
+
|
|
76
|
+
policy_data = JSON.parse(string)
|
|
77
|
+
|
|
78
|
+
policy_data[RULES_KEY].each do |rule_hash|
|
|
79
|
+
rule_hash[TRIGGERS_KEY].each do |trigger_hash|
|
|
80
|
+
trigger_node = node_type.new(trigger_hash, rule_hash)
|
|
81
|
+
add_node(trigger_node)
|
|
82
|
+
end
|
|
83
|
+
end
|
|
84
|
+
end
|
|
85
|
+
|
|
86
|
+
def add_node node, node_type = :trigger
|
|
87
|
+
unless node
|
|
88
|
+
logger.error(nil, 'Node was nil when adding node to policy')
|
|
89
|
+
return
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
begin
|
|
93
|
+
node.validate
|
|
94
|
+
rescue ArgumentError => e
|
|
95
|
+
logger.error(e, e.message)
|
|
96
|
+
return
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
case node_type
|
|
100
|
+
when :source
|
|
101
|
+
@sources << node
|
|
102
|
+
when :propagator
|
|
103
|
+
@propagators << node
|
|
104
|
+
when :trigger
|
|
105
|
+
@triggers << node
|
|
106
|
+
when :dynamic_source
|
|
107
|
+
module_names << node.class_name
|
|
108
|
+
@sources << node
|
|
109
|
+
else
|
|
110
|
+
logger.error(nil, "Invalid node_type: #{ node_type } provided when adding node to policy")
|
|
111
|
+
end
|
|
112
|
+
end
|
|
113
|
+
|
|
114
|
+
def module_names
|
|
115
|
+
@_module_names ||= begin
|
|
116
|
+
m = Set.new
|
|
117
|
+
tracked_classes.each { |tracked| m << tracked }
|
|
118
|
+
sources.each { |source| m << source.class_name }
|
|
119
|
+
propagators.each { |propagator| m << propagator.class_name }
|
|
120
|
+
triggers.each { |trigger| m << trigger.class_name }
|
|
121
|
+
m
|
|
122
|
+
end
|
|
123
|
+
end
|
|
124
|
+
|
|
125
|
+
def find_triggers_by_rule rule_id
|
|
126
|
+
triggers.select { |trigger| trigger.rule_id == rule_id }
|
|
127
|
+
end
|
|
128
|
+
|
|
129
|
+
def find_node rule_id, class_name, method_name, instance_method
|
|
130
|
+
find_triggers_by_rule(rule_id).find do |node|
|
|
131
|
+
node.class_name == class_name && node.method_name == method_name && node.instance_method == instance_method
|
|
132
|
+
end
|
|
133
|
+
end
|
|
134
|
+
end
|
|
135
|
+
end
|
|
136
|
+
end
|
|
137
|
+
end
|
|
138
|
+
end
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
# Copyright (c) 2020 Contrast Security, Inc. See https://www.contrastsecurity.com/enduser-terms-0317a for more details.
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
module Contrast
|
|
5
|
+
module Agent
|
|
6
|
+
module Patching
|
|
7
|
+
module Policy
|
|
8
|
+
# This class functions to translate our policy.json into an actionable
|
|
9
|
+
# Ruby object, allowing for dynamic patching over hardcoded patching.
|
|
10
|
+
#
|
|
11
|
+
# @abstract
|
|
12
|
+
class PolicyNode
|
|
13
|
+
attr_accessor :class_name, :instance_method, :method_name, :method_visibility
|
|
14
|
+
attr_reader :properties
|
|
15
|
+
|
|
16
|
+
def node_class
|
|
17
|
+
raise NotImplementedError, 'specify the type of the feature for which this node patches'
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
def feature
|
|
21
|
+
raise NotImplementedError, 'specify the name of the feature for which this node patches'
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def initialize policy_hash = {}
|
|
25
|
+
@class_name = policy_hash[JSON_CLASS_NAME]
|
|
26
|
+
@instance_method = policy_hash[JSON_INSTANCE_METHOD]
|
|
27
|
+
@method_name = policy_hash[JSON_METHOD_NAME]
|
|
28
|
+
@method_visibility = policy_hash[JSON_METHOD_VISIBILITY]
|
|
29
|
+
@properties = policy_hash[JSON_PROPERTIES]
|
|
30
|
+
symbolize
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
def id
|
|
34
|
+
@_id ||= "#{ feature }:#{ node_class }:#{ class_name }#{ instance_method? ? '#' : '.' }#{ method_name }"
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
# Don't let nodes be created that will be missing things we need
|
|
38
|
+
# later on. Really, if they don't have these things, they couldn't have
|
|
39
|
+
# done their jobs anyway.
|
|
40
|
+
def validate
|
|
41
|
+
raise(ArgumentError, "#{ node_class } #{ id } did not have a proper class name. Unable to create.") unless class_name
|
|
42
|
+
raise(ArgumentError, "#{ node_class } #{ id } did not have a proper method name. Unable to create.") unless method_name
|
|
43
|
+
raise(ArgumentError, "#{ node_class } #{ id } has a non symbol @method_name value. Unable to create.") unless method_name.is_a?(Symbol)
|
|
44
|
+
raise(ArgumentError, "#{ node_class } #{ id } has a non symbol @method_visibility value. Unable to create.") unless method_visibility.is_a?(Symbol)
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
# just turns this into a ruby-ism
|
|
48
|
+
def instance_method?
|
|
49
|
+
instance_method
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
def private?
|
|
53
|
+
@method_visibility == :private
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
def public?
|
|
57
|
+
@method_visibility == :public
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
private
|
|
61
|
+
|
|
62
|
+
# Convert strings to symbols here, once, to avoid doing so on every
|
|
63
|
+
# comparison at runtime
|
|
64
|
+
def symbolize
|
|
65
|
+
@method_name = @method_name.to_sym if @method_name
|
|
66
|
+
@method_visibility = @method_visibility.to_sym if @method_visibility
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
# The keys used to read from policy.json to create the individual
|
|
70
|
+
# policy nodes. These are common across node types
|
|
71
|
+
JSON_CLASS_NAME = 'class_name'
|
|
72
|
+
JSON_INSTANCE_METHOD = 'instance_method'
|
|
73
|
+
JSON_METHOD_NAME = 'method_name'
|
|
74
|
+
JSON_METHOD_VISIBILITY = 'method_visibility'
|
|
75
|
+
JSON_PROPERTIES = 'properties'
|
|
76
|
+
end
|
|
77
|
+
end
|
|
78
|
+
end
|
|
79
|
+
end
|
|
80
|
+
end
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
# Copyright (c) 2020 Contrast Security, Inc. See https://www.contrastsecurity.com/enduser-terms-0317a for more details.
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
cs__scoped_require 'contrast/agent/assess/class_reverter'
|
|
5
|
+
cs__scoped_require 'contrast/components/interface'
|
|
6
|
+
|
|
7
|
+
module Contrast
|
|
8
|
+
module Agent
|
|
9
|
+
module Patching
|
|
10
|
+
module Policy
|
|
11
|
+
# This is how we unpatch out of our customer's code. It provides a way
|
|
12
|
+
# to remove ourselves from those modules which have since had their
|
|
13
|
+
# definition of the patched method revoked, such as when running with
|
|
14
|
+
# FactoryBot
|
|
15
|
+
module PolicyUnpatcher
|
|
16
|
+
include Contrast::Components::Interface
|
|
17
|
+
access_component :logging
|
|
18
|
+
|
|
19
|
+
def self.revert_conflicting_patches
|
|
20
|
+
logger.debug_with_time("\t\tRunning reversions") do
|
|
21
|
+
Contrast::Agent::Assess::ClassReverter.unpatch!
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
end
|
|
28
|
+
end
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
# Copyright (c) 2020 Contrast Security, Inc. See https://www.contrastsecurity.com/enduser-terms-0317a for more details.
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
cs__scoped_require 'contrast/core_extensions/module'
|
|
5
|
+
cs__scoped_require 'contrast/agent/patching/policy/policy_node'
|
|
6
|
+
|
|
7
|
+
module Contrast
|
|
8
|
+
module Agent
|
|
9
|
+
module Patching
|
|
10
|
+
module Policy
|
|
11
|
+
# This class functions to translate our policy.json into an actionable
|
|
12
|
+
# Ruby object, allowing for dynamic patching over hardcoded patching,
|
|
13
|
+
# specifically for those methods which result in the trigger of an
|
|
14
|
+
# attack (indicate points in the application where uncontrolled user
|
|
15
|
+
# input attempted to or did do damage).
|
|
16
|
+
class TriggerNode < PolicyNode
|
|
17
|
+
JSON_NAME = 'name'
|
|
18
|
+
JSON_NODES = 'nodes'
|
|
19
|
+
JSON_APPLICATOR = 'applicator'
|
|
20
|
+
JSON_APPLICATOR_METHOD = 'applicator_method'
|
|
21
|
+
JSON_REQUIRED_PROPS = 'required_properties'
|
|
22
|
+
JSON_OPTIONAL_PROPS = 'optional_properties'
|
|
23
|
+
JSON_ON_EXCEPTION = 'on_exception'
|
|
24
|
+
|
|
25
|
+
attr_reader :rule_id
|
|
26
|
+
attr_accessor :applicator_method, :applicator, :on_exception, :required_properties, :optional_properties
|
|
27
|
+
|
|
28
|
+
def initialize trigger_hash = {}, rule_hash = {}
|
|
29
|
+
super(trigger_hash)
|
|
30
|
+
@rule_id = rule_hash[JSON_NAME]
|
|
31
|
+
@on_exception = rule_hash[JSON_ON_EXCEPTION] # returns nil in most cases
|
|
32
|
+
@required_properties = rule_hash[JSON_REQUIRED_PROPS]
|
|
33
|
+
@optional_properties = rule_hash[JSON_OPTIONAL_PROPS]
|
|
34
|
+
@applicator = class_from_string(rule_hash[JSON_APPLICATOR])
|
|
35
|
+
# if a unique applicator method is defined for this method (rare case), preference getting that one.
|
|
36
|
+
# otherwise, fall back to the normal applicator method for this rule
|
|
37
|
+
@applicator_method = (trigger_hash[JSON_APPLICATOR_METHOD] || rule_hash[JSON_APPLICATOR_METHOD]).to_sym
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
NODE = 'Trigger'
|
|
41
|
+
def node_class
|
|
42
|
+
NODE
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
def validate
|
|
46
|
+
super
|
|
47
|
+
unless applicator.public_methods(false).any? { |method| method == applicator_method }
|
|
48
|
+
raise(ArgumentError,
|
|
49
|
+
"#{ id } did not have a proper applicator method: #{ applicator } does not respond to #{ applicator_method }. Unable to create.")
|
|
50
|
+
end
|
|
51
|
+
if (required_properties & optional_properties).any?
|
|
52
|
+
raise(ArgumentError, "#{ rule_id } had overlapping elements between required and optional properties. Unable to create.")
|
|
53
|
+
end
|
|
54
|
+
if (properties.keys - (required_properties | optional_properties)).any?
|
|
55
|
+
raise(ArgumentError, "#{ id } had an unexpected property. Unable to create.")
|
|
56
|
+
end
|
|
57
|
+
raise(ArgumentError, "#{ id } did not have a required property. Unable to create.") if (required_properties - properties.keys).any?
|
|
58
|
+
|
|
59
|
+
validate_rule
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
def validate_rule
|
|
63
|
+
raise(ArgumentError, 'Unknown rule did not have a proper name. Unable to create.') unless rule_id
|
|
64
|
+
raise(ArgumentError, "#{ id } did not have a proper applicator. Unable to create.") unless applicator
|
|
65
|
+
raise(ArgumentError, "#{ id } did not have a proper applicator method. Unable to create.") unless applicator_method
|
|
66
|
+
raise(ArgumentError, "#{ id } did not have a proper set of required properties. Unable to create.") unless required_properties
|
|
67
|
+
raise(ArgumentError, "#{ id } did not have a proper set of optional properties. Unable to create.") unless optional_properties
|
|
68
|
+
end
|
|
69
|
+
|
|
70
|
+
private
|
|
71
|
+
|
|
72
|
+
def class_from_string str
|
|
73
|
+
return unless str
|
|
74
|
+
|
|
75
|
+
Object.cs__const_get(str)
|
|
76
|
+
end
|
|
77
|
+
end
|
|
78
|
+
end
|
|
79
|
+
end
|
|
80
|
+
end
|
|
81
|
+
end
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
# Copyright (c) 2020 Contrast Security, Inc. See https://www.contrastsecurity.com/enduser-terms-0317a for more details.
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
cs__scoped_require 'contrast/agent/patching/policy/policy'
|
|
5
|
+
|
|
6
|
+
# classes required by patches in the policy
|
|
7
|
+
cs__scoped_require 'contrast/core_extensions/protect/applies_command_injection_rule'
|
|
8
|
+
cs__scoped_require 'contrast/core_extensions/protect/applies_deserialization_rule'
|
|
9
|
+
cs__scoped_require 'contrast/core_extensions/protect/applies_no_sqli_rule'
|
|
10
|
+
cs__scoped_require 'contrast/core_extensions/protect/applies_path_traversal_rule'
|
|
11
|
+
cs__scoped_require 'contrast/core_extensions/protect/applies_sqli_rule'
|
|
12
|
+
cs__scoped_require 'contrast/core_extensions/protect/applies_xxe_rule'
|
|
13
|
+
cs__scoped_require 'contrast/agent/protect/policy/trigger_node'
|
|
14
|
+
|
|
15
|
+
module Contrast
|
|
16
|
+
module Agent
|
|
17
|
+
module Protect
|
|
18
|
+
module Policy
|
|
19
|
+
# This is just a holder for our policy. Takes the policy JSON and
|
|
20
|
+
# converts it into hashes that we can access nicely
|
|
21
|
+
class Policy < Contrast::Agent::Patching::Policy::Policy
|
|
22
|
+
def self.policy_folder
|
|
23
|
+
'protect'
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
def disabled_globally?
|
|
27
|
+
PROTECT.forcibly_disabled?
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def node_type
|
|
31
|
+
Contrast::Agent::Protect::Policy::TriggerNode
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
end
|
|
37
|
+
end
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# Copyright (c) 2020 Contrast Security, Inc. See https://www.contrastsecurity.com/enduser-terms-0317a for more details.
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
cs__scoped_require 'contrast/agent/patching/policy/trigger_node'
|
|
5
|
+
|
|
6
|
+
module Contrast
|
|
7
|
+
module Agent
|
|
8
|
+
module Protect
|
|
9
|
+
module Policy
|
|
10
|
+
# This class functions to translate our policy.json into an actionable
|
|
11
|
+
# Ruby object, allowing for dynamic patching over hardcoded patching,
|
|
12
|
+
# specifically for those methods which result in the trigger of an
|
|
13
|
+
# attack (indicate points in the application where uncontrolled user
|
|
14
|
+
# input can do damage).
|
|
15
|
+
class TriggerNode < Contrast::Agent::Patching::Policy::TriggerNode
|
|
16
|
+
def feature
|
|
17
|
+
'Protect'
|
|
18
|
+
end
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
# Copyright (c) 2020 Contrast Security, Inc. See https://www.contrastsecurity.com/enduser-terms-0317a for more details.
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
module Contrast
|
|
5
|
+
module Agent
|
|
6
|
+
module Protect
|
|
7
|
+
# This is the base module for our assess rule classes. It is intended to
|
|
8
|
+
# facilitate the patching of the application for Protect functionality.
|
|
9
|
+
# Any class under this namespace should be required here, providing a
|
|
10
|
+
# single point of require for this functionality.
|
|
11
|
+
module Rule
|
|
12
|
+
end
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
# The classes required for All Rasp Rules
|
|
18
|
+
cs__scoped_require 'contrast/agent/protect/rule/base'
|
|
19
|
+
cs__scoped_require 'contrast/agent/protect/rule/base_service'
|
|
20
|
+
|
|
21
|
+
# The classes required for the XSS Rasp Rule
|
|
22
|
+
cs__scoped_require 'contrast/agent/protect/rule/xss'
|
|
23
|
+
|
|
24
|
+
# The classes required for the SQLI
|
|
25
|
+
cs__scoped_require 'contrast/agent/protect/rule/default_scanner'
|
|
26
|
+
cs__scoped_require 'contrast/agent/protect/rule/sqli'
|
|
27
|
+
cs__scoped_require 'contrast/agent/protect/rule/sqli/default_sql_scanner'
|
|
28
|
+
cs__scoped_require 'contrast/agent/protect/rule/sqli/mysql_sql_scanner'
|
|
29
|
+
cs__scoped_require 'contrast/agent/protect/rule/sqli/postgres_sql_scanner'
|
|
30
|
+
cs__scoped_require 'contrast/agent/protect/rule/sqli/sqlite_sql_scanner'
|
|
31
|
+
|
|
32
|
+
# The classes required for Path Traversal
|
|
33
|
+
cs__scoped_require 'contrast/agent/protect/rule/path_traversal'
|
|
34
|
+
|
|
35
|
+
# The classes required for Command Injection
|
|
36
|
+
cs__scoped_require 'contrast/agent/protect/rule/cmd_injection'
|
|
37
|
+
|
|
38
|
+
# The classes required for CSRF
|
|
39
|
+
cs__scoped_require 'contrast/agent/protect/rule/csrf'
|
|
40
|
+
cs__scoped_require 'contrast/agent/protect/rule/csrf/csrf_evaluator'
|
|
41
|
+
cs__scoped_require 'contrast/agent/protect/rule/csrf/csrf_token_injector'
|
|
42
|
+
|
|
43
|
+
# The classes required for XXE
|
|
44
|
+
cs__scoped_require 'contrast/agent/protect/rule/xxe'
|
|
45
|
+
cs__scoped_require 'contrast/agent/protect/rule/xxe/entity_wrapper'
|
|
46
|
+
|
|
47
|
+
# The classes required for Untrusted Deserialization
|
|
48
|
+
cs__scoped_require 'contrast/agent/protect/rule/deserialization'
|
|
49
|
+
|
|
50
|
+
# The classes required for the NoSQLi
|
|
51
|
+
cs__scoped_require 'contrast/agent/protect/rule/no_sqli'
|
|
52
|
+
cs__scoped_require 'contrast/agent/protect/rule/no_sqli/mongo_no_sql_scanner'
|
|
53
|
+
|
|
54
|
+
# The classes required for Http Method Tampering
|
|
55
|
+
cs__scoped_require 'contrast/agent/protect/rule/http_method_tampering'
|
|
56
|
+
|
|
57
|
+
# The classes required for Unsafe File Upload
|
|
58
|
+
cs__scoped_require 'contrast/agent/protect/rule/unsafe_file_upload'
|