redgap 0.1.0__tar.gz
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.
- redgap-0.1.0/.gitignore +33 -0
- redgap-0.1.0/LICENSE +21 -0
- redgap-0.1.0/NOTICE +46 -0
- redgap-0.1.0/PKG-INFO +153 -0
- redgap-0.1.0/README.md +103 -0
- redgap-0.1.0/docs/DEPLOY.md +56 -0
- redgap-0.1.0/docs/architecture.md +41 -0
- redgap-0.1.0/docs/architecture.svg +78 -0
- redgap-0.1.0/docs/index.html +483 -0
- redgap-0.1.0/docs/samples/baseline/coverage.json +158 -0
- redgap-0.1.0/docs/samples/baseline/coverage.md +31 -0
- redgap-0.1.0/docs/samples/baseline/navigator-layer.json +127 -0
- redgap-0.1.0/docs/samples/demo.txt +20 -0
- redgap-0.1.0/docs/samples/fixed/coverage.json +171 -0
- redgap-0.1.0/docs/samples/fixed/coverage.md +31 -0
- redgap-0.1.0/docs/samples/fixed/navigator-layer.json +127 -0
- redgap-0.1.0/fixtures/replay/T1057/events.jsonl +3 -0
- redgap-0.1.0/fixtures/replay/T1057/provenance.json +16 -0
- redgap-0.1.0/fixtures/replay/T1057/raw/exec.log +3 -0
- redgap-0.1.0/fixtures/replay/T1070.006/events.jsonl +5 -0
- redgap-0.1.0/fixtures/replay/T1070.006/provenance.json +18 -0
- redgap-0.1.0/fixtures/replay/T1070.006/raw/exec.log +5 -0
- redgap-0.1.0/fixtures/replay/T1087.001/events.jsonl +3 -0
- redgap-0.1.0/fixtures/replay/T1087.001/provenance.json +16 -0
- redgap-0.1.0/fixtures/replay/T1087.001/raw/exec.log +3 -0
- redgap-0.1.0/fixtures/replay/T1136.001/events.jsonl +5 -0
- redgap-0.1.0/fixtures/replay/T1136.001/provenance.json +18 -0
- redgap-0.1.0/fixtures/replay/T1136.001/raw/exec.log +5 -0
- redgap-0.1.0/fixtures/replay/T1548.001/events.jsonl +9 -0
- redgap-0.1.0/fixtures/replay/T1548.001/provenance.json +19 -0
- redgap-0.1.0/fixtures/replay/T1548.001/raw/exec.log +9 -0
- redgap-0.1.0/lab/Dockerfile +30 -0
- redgap-0.1.0/lab/collector/redgap_exec.c +82 -0
- redgap-0.1.0/lab/compose.yaml +24 -0
- redgap-0.1.0/pyproject.toml +68 -0
- redgap-0.1.0/rules/proc_creation_lnx_setgid_setuid.yml +32 -0
- redgap-0.1.0/rules/redgap/account_discovery_etc_passwd.yml +36 -0
- redgap-0.1.0/rules/redgap/create_account_useradd.yml +32 -0
- redgap-0.1.0/rules/roundtrip/timestomp_touch.yml +32 -0
- redgap-0.1.0/scripts/gen_samples.py +41 -0
- redgap-0.1.0/src/redgap/__init__.py +9 -0
- redgap-0.1.0/src/redgap/_resources.py +44 -0
- redgap-0.1.0/src/redgap/allowlist.py +147 -0
- redgap-0.1.0/src/redgap/catalog.py +63 -0
- redgap-0.1.0/src/redgap/cli.py +134 -0
- redgap-0.1.0/src/redgap/detection/__init__.py +5 -0
- redgap-0.1.0/src/redgap/detection/coverage.py +133 -0
- redgap-0.1.0/src/redgap/detection/engine.py +276 -0
- redgap-0.1.0/src/redgap/detection/sigma_ast.py +238 -0
- redgap-0.1.0/src/redgap/engine_facade.py +75 -0
- redgap-0.1.0/src/redgap/lab.py +118 -0
- redgap-0.1.0/src/redgap/models.py +149 -0
- redgap-0.1.0/src/redgap/pipeline.py +68 -0
- redgap-0.1.0/src/redgap/planner.py +179 -0
- redgap-0.1.0/src/redgap/report/__init__.py +10 -0
- redgap-0.1.0/src/redgap/report/build.py +87 -0
- redgap-0.1.0/src/redgap/report/markdown.py +84 -0
- redgap-0.1.0/src/redgap/report/navigator.py +92 -0
- redgap-0.1.0/src/redgap/target.py +119 -0
- redgap-0.1.0/src/redgap/techniques/__init__.py +11 -0
- redgap-0.1.0/src/redgap/techniques/base.py +21 -0
- redgap-0.1.0/src/redgap/techniques/registry.py +277 -0
- redgap-0.1.0/src/redgap/telemetry/__init__.py +1 -0
- redgap-0.1.0/src/redgap/telemetry/schema.py +104 -0
- redgap-0.1.0/src/redgap/telemetry/snoopy.py +73 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/LICENSE +6 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/README.md +32 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_apt_shell_execution.yml +28 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_at_command.yml +28 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_auditctl_clear_rules.yml +26 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_av_kaspersky_av_disabled.yml +31 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_awk_shell_spawn.yml +38 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_base64_decode.yml +23 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_base64_execution.yml +34 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_base64_shebang_cli.yml +27 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_bash_interactive_shell.yml +23 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_bpf_kprob_tracing_enabled.yml +28 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_bpftrace_unsafe_option_usage.yml +23 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_cap_setgid.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_cap_setuid.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_capa_discovery.yml +25 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_capsh_shell_invocation.yml +24 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_chattr_immutable_removal.yml +25 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_chmod_targeting_sensitive_directories.yml +46 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_chroot_execution.yml +28 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_clear_logs.yml +37 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_clear_syslog.yml +87 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_clipboard_collection.yml +28 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_cp_passwd_or_shadow_tmp.yml +28 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_crontab_enumeration.yml +25 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_crontab_removal.yml +23 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_crypto_mining.yml +42 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_curl_usage.yml +22 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_curl_wget_exec_tmp.yml +36 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_dd_file_overwrite.yml +30 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_dd_process_injection.yml +27 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_disable_ufw.yml +38 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_doas_execution.yml +22 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_env_shell_invocation.yml +30 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_esxcli_network_discovery.yml +31 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_esxcli_permission_change_admin.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_esxcli_storage_discovery.yml +32 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_esxcli_syslog_config_change.yml +30 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_esxcli_system_discovery.yml +30 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_esxcli_user_account_creation.yml +27 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_esxcli_vm_discovery.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_esxcli_vm_kill.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_esxcli_vsan_discovery.yml +32 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_file_and_directory_discovery.yml +35 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_file_deletion.yml +25 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_find_shell_execution.yml +33 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_flock_shell_execution.yml +31 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_gcc_shell_execution.yml +36 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_git_shell_execution.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_grep_os_arch_discovery.yml +33 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_groupdel.yml +24 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_install_root_certificate.yml +24 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_install_suspicious_packages.yml +49 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_iptables_flush_ufw.yml +41 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_local_account.yml +52 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_local_groups.yml +34 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_malware_gobrat_grep_payload_discovery.yml +28 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_mkfifo_named_pipe_creation.yml +21 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_mkfifo_named_pipe_creation_susp_location.yml +26 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_mount_hidepid.yml +27 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_netcat_reverse_shell.yml +59 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_nice_shell_execution.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_nohup.yml +23 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_nohup_susp_execution.yml +27 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_omigod_scx_runasprovider_executescript.yml +35 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_omigod_scx_runasprovider_executeshellcommand.yml +33 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_perl_reverse_shell.yml +31 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_php_reverse_shell.yml +36 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_pnscan_binary_cli_pattern.yml +26 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_proxy_connection.yml +22 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_pua_trufflehog.yml +43 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_python_base64_encoded_execution.yml +43 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_python_http_server_execution.yml +36 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_python_pty_spawn.yml +38 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_python_reverse_shell.yml +32 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_python_shell_os_system.yml +38 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_remote_access_tools_teamviewer_incoming_connection.yml +31 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_remote_system_discovery.yml +46 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_remove_package.yml +42 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_rsync_shell_execution.yml +44 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_rsync_shell_spawn.yml +37 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_ruby_reverse_shell.yml +34 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_schedule_task_job_cron.yml +25 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_security_software_discovery.yml +34 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_security_tools_disabling.yml +83 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_services_stop_and_disable.yml +50 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_setgid_setuid.yml +27 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_ssh_shell_execution.yml +36 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_ssm_agent_abuse.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_container_residence_discovery.yml +38 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_curl_fileupload.yml +42 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_curl_useragent.yml +28 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_dockerenv_recon.yml +32 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_exec_from_dev_shm.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_execution_tmp_folder.yml +27 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_find_execution.yml +33 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_git_clone.yml +41 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_history_delete.yml +34 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_history_recon.yml +35 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_hktl_execution.yml +97 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_inod_listing.yml +31 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_interactive_bash.yml +35 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_java_children.yml +32 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_network_utilities_execution.yml +43 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_pipe_shell.yml +35 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_process_reading_sudoers.yml +34 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_recon_indicators.yml +25 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_script_interpretor_spawn_credential_scanner.yml +43 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_sensitive_file_access.yml +60 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_shell_child_process_from_parent_tmp_folder.yml +31 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_susp_shell_script_exec_from_susp_location.yml +35 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_system_info_discovery.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_system_network_connections_discovery.yml +30 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_system_network_discovery.yml +33 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_systemctl_mask_power_settings.yml +32 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_touch_susp.yml +24 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_triple_cross_rootkit_execve_hijack.yml +22 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_triple_cross_rootkit_install.yml +27 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_userdel.yml +24 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_usermod_susp_group.yml +25 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_vim_shell_execution.yml +52 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_webshell_detection.yml +50 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_wget_download_suspicious_directory.yml +29 -0
- redgap-0.1.0/tests/corpus/sigmahq_linux_process_creation/proc_creation_lnx_xterm_reverse_shell.yml +24 -0
- redgap-0.1.0/tests/test_allowlist.py +152 -0
- redgap-0.1.0/tests/test_coverage.py +84 -0
- redgap-0.1.0/tests/test_determinism.py +47 -0
- redgap-0.1.0/tests/test_engine_golden.py +128 -0
- redgap-0.1.0/tests/test_engine_semantics.py +264 -0
- redgap-0.1.0/tests/test_engine_semantics2.py +161 -0
- redgap-0.1.0/tests/test_fixture_integrity.py +69 -0
- redgap-0.1.0/tests/test_import_hygiene.py +38 -0
- redgap-0.1.0/tests/test_pipeline.py +45 -0
- redgap-0.1.0/tests/test_planner.py +121 -0
- redgap-0.1.0/tests/test_report.py +91 -0
- redgap-0.1.0/tests/test_rule_loading.py +53 -0
- redgap-0.1.0/tests/test_setuid_inert.py +100 -0
- redgap-0.1.0/tests/test_sigma_ast_smoke.py +89 -0
- redgap-0.1.0/tests/test_sigmahq_corpus.py +70 -0
- redgap-0.1.0/tests/test_snoopy.py +69 -0
- redgap-0.1.0/tests/test_techniques.py +38 -0
redgap-0.1.0/.gitignore
ADDED
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# Python
|
|
2
|
+
__pycache__/
|
|
3
|
+
*.py[cod]
|
|
4
|
+
*.egg-info/
|
|
5
|
+
.eggs/
|
|
6
|
+
build/
|
|
7
|
+
dist/
|
|
8
|
+
.venv/
|
|
9
|
+
venv/
|
|
10
|
+
env/
|
|
11
|
+
|
|
12
|
+
# Tooling
|
|
13
|
+
.pytest_cache/
|
|
14
|
+
.ruff_cache/
|
|
15
|
+
.mypy_cache/
|
|
16
|
+
.coverage
|
|
17
|
+
htmlcov/
|
|
18
|
+
|
|
19
|
+
# Secrets / local config — never commit an API key
|
|
20
|
+
.env
|
|
21
|
+
*.key
|
|
22
|
+
secrets.*
|
|
23
|
+
|
|
24
|
+
# OS / editor
|
|
25
|
+
.DS_Store
|
|
26
|
+
Thumbs.db
|
|
27
|
+
.idea/
|
|
28
|
+
.vscode/
|
|
29
|
+
|
|
30
|
+
# Runtime output (reports are regenerated; only committed samples live under docs/ or fixtures/)
|
|
31
|
+
out/
|
|
32
|
+
out-*/
|
|
33
|
+
*.tmp
|
redgap-0.1.0/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 befnoz
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
redgap-0.1.0/NOTICE
ADDED
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
RedGap — third-party components and attributions
|
|
2
|
+
=================================================
|
|
3
|
+
|
|
4
|
+
RedGap itself is licensed under the MIT License (see LICENSE).
|
|
5
|
+
|
|
6
|
+
This project depends on, references, or derives benign test procedures from the
|
|
7
|
+
following third-party works. Each remains under its own license; RedGap claims
|
|
8
|
+
no ownership of them and thanks their authors.
|
|
9
|
+
|
|
10
|
+
Runtime dependencies
|
|
11
|
+
--------------------
|
|
12
|
+
- pySigma (SigmaHQ) — LGPL-2.1 — Sigma rule parsing.
|
|
13
|
+
https://github.com/SigmaHQ/pySigma
|
|
14
|
+
- Typer — MIT — command-line interface.
|
|
15
|
+
- Rich — MIT — terminal rendering.
|
|
16
|
+
- PyYAML — MIT — YAML loading.
|
|
17
|
+
|
|
18
|
+
Optional dependency
|
|
19
|
+
--------------------
|
|
20
|
+
- anthropic (Anthropic SDK) — MIT — optional LLM orchestration only.
|
|
21
|
+
|
|
22
|
+
Detection content
|
|
23
|
+
-----------------
|
|
24
|
+
- Sigma community rules (SigmaHQ) are distributed under the Detection Rule
|
|
25
|
+
License (DRL-1.1). Any SigmaHQ rule vendored under rules/ retains its original
|
|
26
|
+
header, author, and license reference. See:
|
|
27
|
+
https://github.com/SigmaHQ/sigma/blob/master/LICENSE.Detection.Rules.md
|
|
28
|
+
- The full SigmaHQ linux/process_creation ruleset (122 rules) is vendored verbatim
|
|
29
|
+
under tests/corpus/sigmahq_linux_process_creation/ as TEST INPUT only (engine
|
|
30
|
+
validation), under DRL-1.1. Source commit and refresh steps are in that directory's
|
|
31
|
+
README. These rules are not loaded at runtime.
|
|
32
|
+
|
|
33
|
+
Technique provenance
|
|
34
|
+
-------------------
|
|
35
|
+
- The benign techniques executed by RedGap are derived from Atomic Red Team
|
|
36
|
+
(Red Canary), MIT License. RedGap runs only well-known, published, benign
|
|
37
|
+
detection tests against its own disposable local lab — never novel offense.
|
|
38
|
+
https://github.com/redcanaryco/atomic-red-team
|
|
39
|
+
|
|
40
|
+
Telemetry / tooling referenced (not redistributed)
|
|
41
|
+
--------------------------------------------------
|
|
42
|
+
- snoopy (a2o/snoopy) — GPL-2.0 — execve command logger used as
|
|
43
|
+
an independent telemetry collector in the lab image.
|
|
44
|
+
- Sysmon for Linux (Microsoft) — MIT — optional high-fidelity collector.
|
|
45
|
+
- MITRE ATT&CK / ATT&CK Navigator layer format — MITRE terms of use. ATT&CK(R) is
|
|
46
|
+
a registered trademark of The MITRE Corporation.
|
redgap-0.1.0/PKG-INFO
ADDED
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
Metadata-Version: 2.5
|
|
2
|
+
Name: redgap
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Automated, MITRE ATT&CK-mapped offense<->detection coverage harness. Finds the red gaps in your detection coverage.
|
|
5
|
+
Author: befnoz
|
|
6
|
+
License: MIT License
|
|
7
|
+
|
|
8
|
+
Copyright (c) 2026 befnoz
|
|
9
|
+
|
|
10
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
11
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
12
|
+
in the Software without restriction, including without limitation the rights
|
|
13
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
14
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
15
|
+
furnished to do so, subject to the following conditions:
|
|
16
|
+
|
|
17
|
+
The above copyright notice and this permission notice shall be included in all
|
|
18
|
+
copies or substantial portions of the Software.
|
|
19
|
+
|
|
20
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
21
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
22
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
23
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
24
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
25
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
26
|
+
SOFTWARE.
|
|
27
|
+
License-File: LICENSE
|
|
28
|
+
License-File: NOTICE
|
|
29
|
+
Keywords: coverage,detection-engineering,mitre-attack,purple-team,security,sigma
|
|
30
|
+
Classifier: Development Status :: 3 - Alpha
|
|
31
|
+
Classifier: Intended Audience :: Information Technology
|
|
32
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
33
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
34
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
35
|
+
Classifier: Topic :: Security
|
|
36
|
+
Requires-Python: >=3.11
|
|
37
|
+
Requires-Dist: pysigma==1.5.0
|
|
38
|
+
Requires-Dist: pyyaml>=6.0
|
|
39
|
+
Requires-Dist: rich>=13.7
|
|
40
|
+
Requires-Dist: typer>=0.12
|
|
41
|
+
Provides-Extra: dev
|
|
42
|
+
Requires-Dist: mypy>=1.11; extra == 'dev'
|
|
43
|
+
Requires-Dist: pre-commit>=3.8; extra == 'dev'
|
|
44
|
+
Requires-Dist: pytest-cov>=5; extra == 'dev'
|
|
45
|
+
Requires-Dist: pytest>=8; extra == 'dev'
|
|
46
|
+
Requires-Dist: ruff>=0.6; extra == 'dev'
|
|
47
|
+
Provides-Extra: llm
|
|
48
|
+
Requires-Dist: anthropic>=0.40; extra == 'llm'
|
|
49
|
+
Description-Content-Type: text/markdown
|
|
50
|
+
|
|
51
|
+
# RedGap
|
|
52
|
+
|
|
53
|
+
**Find the red gaps in your detection coverage.**
|
|
54
|
+
|
|
55
|
+
RedGap is an automated, MITRE ATT&CK-mapped **offense↔detection coverage harness**. It runs a small set of *benign* ATT&CK techniques against its own disposable local lab, collects real telemetry with an **independent collector**, and then **deterministically** — from logs and Sigma rules, with no AI in the loop — decides whether each technique was *detected* or is a *gap*. The output is a coverage report (`technique → detected? → gap type`) plus an ATT&CK Navigator layer.
|
|
56
|
+
|
|
57
|
+
The name is the output: in the coverage grid, detected techniques are green and gaps are **red**. RedGap finds the red.
|
|
58
|
+
|
|
59
|
+
[](https://github.com/befnoz/redgap/actions/workflows/ci.yml)
|
|
60
|
+
<!-- Uncomment once Pages is enabled / the package is on PyPI: -->
|
|
61
|
+
<!-- [](https://befnoz.github.io/redgap/) -->
|
|
62
|
+
<!-- [](https://pypi.org/project/redgap/) -->
|
|
63
|
+
|
|
64
|
+
> **v0.1 — what this is and is not.** RedGap v0.1 is a deterministic harness over a *fixed* set of techniques. It is **not** an autonomous agent that continuously attacks and adapts. Adaptive, gap-driven technique chaining (the agent choosing its next attack from the last result) is the honest **next step**, tracked on the roadmap. Precise scope on purpose.
|
|
65
|
+
|
|
66
|
+
**Status.** RedGap's own parser + evaluator ingests **all 122 real SigmaHQ `linux/process_creation` rules** with zero parser errors and zero evaluator crashes — that ruleset is vendored under [`tests/corpus/`](tests/corpus/sigmahq_linux_process_creation/) and checked by [`test_sigmahq_corpus.py`](tests/test_sigmahq_corpus.py), so the claim is reproducible, not asserted. **290 tests** run fully offline in CI. Coverage is computed from **5 committed real-telemetry captures** — one per technique, each with a raw log + parsed events + sha256 provenance — not authored logs. See [docs/architecture.md](docs/architecture.md) · committed output in [docs/samples/](docs/samples/).
|
|
67
|
+
|
|
68
|
+
---
|
|
69
|
+
|
|
70
|
+
## The one idea: the verdict is not the AI's to make
|
|
71
|
+
|
|
72
|
+
Every `detected` verdict is a **pure function of `(logs, rules)`**, computed and written to disk **before** any language model is ever called. An optional LLM planner may (a) choose the order of techniques and decide when to stop, and (b) narrate the report. It **cannot** decide whether something was detected — both the deterministic and the LLM planner return the engine's coverage, never model text. A test asserts the coverage report is byte-identical with and without the LLM.
|
|
73
|
+
|
|
74
|
+
This is deliberate. LLMs hallucinate confident verdicts; a coverage tool whose ground truth an LLM can fabricate is worthless. RedGap draws the trust boundary in code.
|
|
75
|
+
|
|
76
|
+

|
|
77
|
+
|
|
78
|
+
The verdict is a pure function of logs and rules, written to disk **before** any model runs. The LLM (dashed red) can only order techniques and narrate — it sits **outside** the verdict path.
|
|
79
|
+
|
|
80
|
+
---
|
|
81
|
+
|
|
82
|
+
## Quickstart (offline, no API key, no cloud)
|
|
83
|
+
|
|
84
|
+
The default path is `REPLAY`: it re-evaluates **real telemetry captured from a prior live run** (committed as fixtures with provenance) through the exact same engine used in LIVE mode. No Docker, no key, no network.
|
|
85
|
+
|
|
86
|
+
```bash
|
|
87
|
+
pip install redgap
|
|
88
|
+
redgap run # REPLAY: prints the coverage table + writes out/coverage.{json,md} + navigator-layer.json
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
From source instead (or before the first PyPI release):
|
|
92
|
+
|
|
93
|
+
```bash
|
|
94
|
+
git clone https://github.com/befnoz/redgap && cd redgap
|
|
95
|
+
pip install -e .
|
|
96
|
+
redgap run
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
**Live dashboard:** the same coverage, as an interactive web page — `https://befnoz.github.io/redgap/` (see [docs/DEPLOY.md](docs/DEPLOY.md) to switch it on).
|
|
100
|
+
|
|
101
|
+
To run the real thing against the local Docker lab:
|
|
102
|
+
|
|
103
|
+
```bash
|
|
104
|
+
redgap run --live # brings up the disposable lab, executes techniques, captures fresh telemetry
|
|
105
|
+
```
|
|
106
|
+
|
|
107
|
+
To try the optional LLM planner (needs the `llm` extra and `ANTHROPIC_API_KEY`):
|
|
108
|
+
|
|
109
|
+
```bash
|
|
110
|
+
pip install -e ".[llm]" # adds the optional anthropic SDK
|
|
111
|
+
redgap run --llm # equivalently: COVERAGE_LLM=1 redgap run
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
The committed `coverage.json` is identical whichever planner ran — a test asserts it.
|
|
115
|
+
|
|
116
|
+
---
|
|
117
|
+
|
|
118
|
+
## What a run shows
|
|
119
|
+
|
|
120
|
+
A v0.1 run is a five-technique mini kill-chain that deliberately produces **both** detections and gaps — and two *different kinds* of gap, because a coverage tool that is all-green is just a checklist:
|
|
121
|
+
|
|
122
|
+
| # | ATT&CK | Tactic | Result |
|
|
123
|
+
|---|--------|--------|--------|
|
|
124
|
+
| 1 | T1087.001 Account Discovery: Local | Discovery | detected |
|
|
125
|
+
| 2 | T1057 Process Discovery | Discovery | **gap (base-rate)** — too noisy for a single-event rule; needs correlation (roadmap) |
|
|
126
|
+
| 3 | T1136.001 Create Account: Local | Persistence | detected |
|
|
127
|
+
| 4 | T1548.001 Setuid/Setgid | Priv. Esc / Defense Evasion | detected (matches a shipped SigmaHQ rule) |
|
|
128
|
+
| 5 | T1070.006 Timestomp | Defense Evasion | **gap (rule)** → closed live in the remediation round-trip |
|
|
129
|
+
|
|
130
|
+
**The remediation round-trip** is the point: technique 5 fires but no rule catches it (a *rule gap*). Write one Sigma rule, re-run the same command, and watch the verdict flip red→green. Both the before and after coverage reports are committed — RedGap is a tool that finds a real blind spot and closes it, not a status printer.
|
|
131
|
+
|
|
132
|
+
---
|
|
133
|
+
|
|
134
|
+
## Ethics & scope
|
|
135
|
+
|
|
136
|
+
⚠️ **RedGap attacks only its own disposable local lab.** There is deliberately no free-form target flag; the live lab runs with **no network**, and every container launch is gated at runtime by an allowlist (`assert_lab_only`) that the test suite proves cannot be widened. Every technique is a benign, published Atomic-Red-Team-derived detection test with no exploit payload, no off-box action, and no runtime downloads. See [ETHICS.md](ETHICS.md), [SCOPE.md](SCOPE.md), and [SECURITY.md](SECURITY.md).
|
|
137
|
+
|
|
138
|
+
Not shipped: weaponizable breadth, real exploits, credential material, or anything that runs against a system you do not own.
|
|
139
|
+
|
|
140
|
+
---
|
|
141
|
+
|
|
142
|
+
## Roadmap (honest next steps)
|
|
143
|
+
|
|
144
|
+
- Adaptive, gap-driven technique chaining (agent picks the next attack from the last verdict).
|
|
145
|
+
- Effect / syscall-level detection (e.g. `utimensat` for timestomp) via a higher-fidelity collector.
|
|
146
|
+
- Correlation rules (turn the base-rate gap into a real detection).
|
|
147
|
+
- Portability: the rules are standard Sigma, so they already run unchanged in Zircolite or any SIEM.
|
|
148
|
+
|
|
149
|
+
---
|
|
150
|
+
|
|
151
|
+
## License
|
|
152
|
+
|
|
153
|
+
MIT — see [LICENSE](LICENSE). Third-party attributions in [NOTICE](NOTICE). ATT&CK® is a registered trademark of The MITRE Corporation.
|
redgap-0.1.0/README.md
ADDED
|
@@ -0,0 +1,103 @@
|
|
|
1
|
+
# RedGap
|
|
2
|
+
|
|
3
|
+
**Find the red gaps in your detection coverage.**
|
|
4
|
+
|
|
5
|
+
RedGap is an automated, MITRE ATT&CK-mapped **offense↔detection coverage harness**. It runs a small set of *benign* ATT&CK techniques against its own disposable local lab, collects real telemetry with an **independent collector**, and then **deterministically** — from logs and Sigma rules, with no AI in the loop — decides whether each technique was *detected* or is a *gap*. The output is a coverage report (`technique → detected? → gap type`) plus an ATT&CK Navigator layer.
|
|
6
|
+
|
|
7
|
+
The name is the output: in the coverage grid, detected techniques are green and gaps are **red**. RedGap finds the red.
|
|
8
|
+
|
|
9
|
+
[](https://github.com/befnoz/redgap/actions/workflows/ci.yml)
|
|
10
|
+
<!-- Uncomment once Pages is enabled / the package is on PyPI: -->
|
|
11
|
+
<!-- [](https://befnoz.github.io/redgap/) -->
|
|
12
|
+
<!-- [](https://pypi.org/project/redgap/) -->
|
|
13
|
+
|
|
14
|
+
> **v0.1 — what this is and is not.** RedGap v0.1 is a deterministic harness over a *fixed* set of techniques. It is **not** an autonomous agent that continuously attacks and adapts. Adaptive, gap-driven technique chaining (the agent choosing its next attack from the last result) is the honest **next step**, tracked on the roadmap. Precise scope on purpose.
|
|
15
|
+
|
|
16
|
+
**Status.** RedGap's own parser + evaluator ingests **all 122 real SigmaHQ `linux/process_creation` rules** with zero parser errors and zero evaluator crashes — that ruleset is vendored under [`tests/corpus/`](tests/corpus/sigmahq_linux_process_creation/) and checked by [`test_sigmahq_corpus.py`](tests/test_sigmahq_corpus.py), so the claim is reproducible, not asserted. **290 tests** run fully offline in CI. Coverage is computed from **5 committed real-telemetry captures** — one per technique, each with a raw log + parsed events + sha256 provenance — not authored logs. See [docs/architecture.md](docs/architecture.md) · committed output in [docs/samples/](docs/samples/).
|
|
17
|
+
|
|
18
|
+
---
|
|
19
|
+
|
|
20
|
+
## The one idea: the verdict is not the AI's to make
|
|
21
|
+
|
|
22
|
+
Every `detected` verdict is a **pure function of `(logs, rules)`**, computed and written to disk **before** any language model is ever called. An optional LLM planner may (a) choose the order of techniques and decide when to stop, and (b) narrate the report. It **cannot** decide whether something was detected — both the deterministic and the LLM planner return the engine's coverage, never model text. A test asserts the coverage report is byte-identical with and without the LLM.
|
|
23
|
+
|
|
24
|
+
This is deliberate. LLMs hallucinate confident verdicts; a coverage tool whose ground truth an LLM can fabricate is worthless. RedGap draws the trust boundary in code.
|
|
25
|
+
|
|
26
|
+

|
|
27
|
+
|
|
28
|
+
The verdict is a pure function of logs and rules, written to disk **before** any model runs. The LLM (dashed red) can only order techniques and narrate — it sits **outside** the verdict path.
|
|
29
|
+
|
|
30
|
+
---
|
|
31
|
+
|
|
32
|
+
## Quickstart (offline, no API key, no cloud)
|
|
33
|
+
|
|
34
|
+
The default path is `REPLAY`: it re-evaluates **real telemetry captured from a prior live run** (committed as fixtures with provenance) through the exact same engine used in LIVE mode. No Docker, no key, no network.
|
|
35
|
+
|
|
36
|
+
```bash
|
|
37
|
+
pip install redgap
|
|
38
|
+
redgap run # REPLAY: prints the coverage table + writes out/coverage.{json,md} + navigator-layer.json
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
From source instead (or before the first PyPI release):
|
|
42
|
+
|
|
43
|
+
```bash
|
|
44
|
+
git clone https://github.com/befnoz/redgap && cd redgap
|
|
45
|
+
pip install -e .
|
|
46
|
+
redgap run
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
**Live dashboard:** the same coverage, as an interactive web page — `https://befnoz.github.io/redgap/` (see [docs/DEPLOY.md](docs/DEPLOY.md) to switch it on).
|
|
50
|
+
|
|
51
|
+
To run the real thing against the local Docker lab:
|
|
52
|
+
|
|
53
|
+
```bash
|
|
54
|
+
redgap run --live # brings up the disposable lab, executes techniques, captures fresh telemetry
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
To try the optional LLM planner (needs the `llm` extra and `ANTHROPIC_API_KEY`):
|
|
58
|
+
|
|
59
|
+
```bash
|
|
60
|
+
pip install -e ".[llm]" # adds the optional anthropic SDK
|
|
61
|
+
redgap run --llm # equivalently: COVERAGE_LLM=1 redgap run
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
The committed `coverage.json` is identical whichever planner ran — a test asserts it.
|
|
65
|
+
|
|
66
|
+
---
|
|
67
|
+
|
|
68
|
+
## What a run shows
|
|
69
|
+
|
|
70
|
+
A v0.1 run is a five-technique mini kill-chain that deliberately produces **both** detections and gaps — and two *different kinds* of gap, because a coverage tool that is all-green is just a checklist:
|
|
71
|
+
|
|
72
|
+
| # | ATT&CK | Tactic | Result |
|
|
73
|
+
|---|--------|--------|--------|
|
|
74
|
+
| 1 | T1087.001 Account Discovery: Local | Discovery | detected |
|
|
75
|
+
| 2 | T1057 Process Discovery | Discovery | **gap (base-rate)** — too noisy for a single-event rule; needs correlation (roadmap) |
|
|
76
|
+
| 3 | T1136.001 Create Account: Local | Persistence | detected |
|
|
77
|
+
| 4 | T1548.001 Setuid/Setgid | Priv. Esc / Defense Evasion | detected (matches a shipped SigmaHQ rule) |
|
|
78
|
+
| 5 | T1070.006 Timestomp | Defense Evasion | **gap (rule)** → closed live in the remediation round-trip |
|
|
79
|
+
|
|
80
|
+
**The remediation round-trip** is the point: technique 5 fires but no rule catches it (a *rule gap*). Write one Sigma rule, re-run the same command, and watch the verdict flip red→green. Both the before and after coverage reports are committed — RedGap is a tool that finds a real blind spot and closes it, not a status printer.
|
|
81
|
+
|
|
82
|
+
---
|
|
83
|
+
|
|
84
|
+
## Ethics & scope
|
|
85
|
+
|
|
86
|
+
⚠️ **RedGap attacks only its own disposable local lab.** There is deliberately no free-form target flag; the live lab runs with **no network**, and every container launch is gated at runtime by an allowlist (`assert_lab_only`) that the test suite proves cannot be widened. Every technique is a benign, published Atomic-Red-Team-derived detection test with no exploit payload, no off-box action, and no runtime downloads. See [ETHICS.md](ETHICS.md), [SCOPE.md](SCOPE.md), and [SECURITY.md](SECURITY.md).
|
|
87
|
+
|
|
88
|
+
Not shipped: weaponizable breadth, real exploits, credential material, or anything that runs against a system you do not own.
|
|
89
|
+
|
|
90
|
+
---
|
|
91
|
+
|
|
92
|
+
## Roadmap (honest next steps)
|
|
93
|
+
|
|
94
|
+
- Adaptive, gap-driven technique chaining (agent picks the next attack from the last verdict).
|
|
95
|
+
- Effect / syscall-level detection (e.g. `utimensat` for timestomp) via a higher-fidelity collector.
|
|
96
|
+
- Correlation rules (turn the base-rate gap into a real detection).
|
|
97
|
+
- Portability: the rules are standard Sigma, so they already run unchanged in Zircolite or any SIEM.
|
|
98
|
+
|
|
99
|
+
---
|
|
100
|
+
|
|
101
|
+
## License
|
|
102
|
+
|
|
103
|
+
MIT — see [LICENSE](LICENSE). Third-party attributions in [NOTICE](NOTICE). ATT&CK® is a registered trademark of The MITRE Corporation.
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
# Deploying RedGap
|
|
2
|
+
|
|
3
|
+
Two independent things: the **web dashboard** (GitHub Pages) and the **`pip install redgap`**
|
|
4
|
+
package (PyPI). Both are wired with GitHub Actions; you only do a little one-time setup.
|
|
5
|
+
|
|
6
|
+
## 1. Web dashboard → GitHub Pages
|
|
7
|
+
|
|
8
|
+
`docs/index.html` is a self-contained dashboard (no external assets). It renders the real
|
|
9
|
+
coverage output — the ATT&CK heatmap, the coverage table, and the `--fix` round-trip toggle.
|
|
10
|
+
|
|
11
|
+
**One-time:** repo **Settings → Pages → Source = "GitHub Actions"**.
|
|
12
|
+
|
|
13
|
+
After that, every push to `main` that touches `docs/**` runs `.github/workflows/pages.yml`
|
|
14
|
+
and publishes to:
|
|
15
|
+
|
|
16
|
+
```
|
|
17
|
+
https://<your-username>.github.io/redgap/
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
That URL is the clickable proof to put in the CES application. (Prefer the branch method
|
|
21
|
+
instead? Settings → Pages → "Deploy from a branch" → `main` → `/docs` also works — then you
|
|
22
|
+
can delete `pages.yml`.)
|
|
23
|
+
|
|
24
|
+
## 2. `pip install redgap` → PyPI
|
|
25
|
+
|
|
26
|
+
The package is already wheel/sdist-clean (`python -m build` + `twine check` pass, and CI's
|
|
27
|
+
`install-smoke` job proves a non-editable install runs from any directory).
|
|
28
|
+
|
|
29
|
+
**First, check the name is free:** open <https://pypi.org/project/redgap/>. If it is taken,
|
|
30
|
+
rename the project in `pyproject.toml` (`name = "..."`, e.g. `redgap-coverage`) and update the
|
|
31
|
+
`url:` lines in `.github/workflows/publish.yml`.
|
|
32
|
+
|
|
33
|
+
**Set up Trusted Publishing (recommended — no tokens/secrets):**
|
|
34
|
+
1. On PyPI: your account → **Publishing** → **Add a pending publisher**.
|
|
35
|
+
2. Fill in: PyPI project name `redgap`, owner = your GitHub user, repository `redgap`,
|
|
36
|
+
workflow `publish.yml`, environment `pypi`.
|
|
37
|
+
3. Save. (A "pending" publisher lets the very first release create the project.)
|
|
38
|
+
|
|
39
|
+
**Release:**
|
|
40
|
+
```bash
|
|
41
|
+
git tag v0.1.0
|
|
42
|
+
git push origin v0.1.0
|
|
43
|
+
```
|
|
44
|
+
The tag fires `.github/workflows/publish.yml`, which builds and publishes. Then anyone can:
|
|
45
|
+
```bash
|
|
46
|
+
pip install redgap
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
**Token fallback** (if you skip Trusted Publishing): create a PyPI API token, add it as the
|
|
50
|
+
repo secret `PYPI_API_TOKEN`, and pass `with: { password: ${{ secrets.PYPI_API_TOKEN }} }` to
|
|
51
|
+
the `pypa/gh-action-pypi-publish` step.
|
|
52
|
+
|
|
53
|
+
## Update the version
|
|
54
|
+
|
|
55
|
+
Bump `version` in `pyproject.toml`, then tag `v<that version>`. Keep the tag and the
|
|
56
|
+
`pyproject.toml` version in sync.
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
# Architecture
|
|
2
|
+
|
|
3
|
+

|
|
4
|
+
|
|
5
|
+
RedGap runs a small set of benign, MITRE ATT&CK-mapped techniques against a disposable
|
|
6
|
+
lab, collects real process-execution telemetry with an **independent** collector, and
|
|
7
|
+
decides — deterministically, from logs and Sigma rules — whether each technique was
|
|
8
|
+
*detected* or is a *gap*.
|
|
9
|
+
|
|
10
|
+
## The trust boundary
|
|
11
|
+
|
|
12
|
+
The single load-bearing property is that the `detected` verdict is a **pure function of
|
|
13
|
+
`(events, rules)`**, computed and written to disk **before** any language model is
|
|
14
|
+
called. The optional LLM planner may choose the order of techniques and narrate the
|
|
15
|
+
report; it drives the same validated tool executor the deterministic planner uses and
|
|
16
|
+
**cannot** produce or change a verdict. `tests/test_planner.py` asserts the coverage is
|
|
17
|
+
byte-identical with and without the LLM — even when the model finishes early, runs a
|
|
18
|
+
subset, or requests a technique that does not exist.
|
|
19
|
+
|
|
20
|
+
## The pieces
|
|
21
|
+
|
|
22
|
+
| Component | File | Role |
|
|
23
|
+
|-----------|------|------|
|
|
24
|
+
| Technique catalog | `src/redgap/catalog.py`, `techniques/registry.py` | 5 benign techniques + their commands and cleanup |
|
|
25
|
+
| Lab | `lab/`, `src/redgap/lab.py` | Disposable Docker container + a ~40-line `LD_PRELOAD` execve collector |
|
|
26
|
+
| Target | `src/redgap/target.py` | `ReplayTarget` (committed real fixtures, offline) / `LiveDockerTarget` |
|
|
27
|
+
| Telemetry | `src/redgap/telemetry/` | snoopy-format parser → SigmaHQ `process_creation` events |
|
|
28
|
+
| Detection | `src/redgap/detection/` | pySigma parser + RedGap's own AST evaluator; coverage join |
|
|
29
|
+
| Planner | `src/redgap/planner.py` | Heuristic (default) / LLM (optional), one `ToolExecutor` |
|
|
30
|
+
| Report | `src/redgap/report/` | `coverage.json`, `coverage.md`, ATT&CK Navigator layer |
|
|
31
|
+
|
|
32
|
+
## Two modes, one engine
|
|
33
|
+
|
|
34
|
+
- **REPLAY** (default): re-evaluate committed real-telemetry fixtures. Offline, no key,
|
|
35
|
+
no Docker — what CI runs and what a reviewer reproduces in one command.
|
|
36
|
+
- **LIVE** (`--live`): bring up the Docker lab, execute the techniques, capture fresh
|
|
37
|
+
telemetry, and run the **same** engine.
|
|
38
|
+
|
|
39
|
+
Fixtures are verbatim captures with `provenance.json` (sha256, kernel, image id, exact
|
|
40
|
+
commands, timestamp) and are regenerable via `redgap capture`; the nightly LIVE CI job
|
|
41
|
+
re-captures on a clean runner so the fixtures are auditable, not hand-authored.
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 900 360" font-family="-apple-system, Segoe UI, Roboto, Helvetica, Arial, sans-serif">
|
|
2
|
+
<defs>
|
|
3
|
+
<marker id="arrow" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="7" markerHeight="7" orient="auto-start-reverse">
|
|
4
|
+
<path d="M0,0 L10,5 L0,10 z" fill="#57606a"/>
|
|
5
|
+
</marker>
|
|
6
|
+
<marker id="arrowR" viewBox="0 0 10 10" refX="9" refY="5" markerWidth="7" markerHeight="7" orient="auto-start-reverse">
|
|
7
|
+
<path d="M0,0 L10,5 L0,10 z" fill="#cf222e"/>
|
|
8
|
+
</marker>
|
|
9
|
+
</defs>
|
|
10
|
+
|
|
11
|
+
<rect x="0" y="0" width="900" height="360" fill="#ffffff"/>
|
|
12
|
+
<text x="24" y="34" font-size="18" font-weight="700" fill="#1f2328">RedGap — offense ↔ detection coverage</text>
|
|
13
|
+
<text x="24" y="54" font-size="12" fill="#57606a">The verdict is deterministic; the LLM is an optional layer that sits outside it.</text>
|
|
14
|
+
|
|
15
|
+
<!-- optional LLM box -->
|
|
16
|
+
<rect x="330" y="88" width="380" height="52" rx="8" fill="#fdeff0" stroke="#cf222e" stroke-width="1.5" stroke-dasharray="6 4"/>
|
|
17
|
+
<text x="520" y="110" font-size="13" font-weight="700" fill="#cf222e" text-anchor="middle">LLM planner · optional</text>
|
|
18
|
+
<text x="520" y="128" font-size="11" fill="#a4404a" text-anchor="middle">orders techniques · narrates — cannot set a verdict</text>
|
|
19
|
+
|
|
20
|
+
<!-- pipeline boxes -->
|
|
21
|
+
<g font-size="13" font-weight="700" fill="#1f2328">
|
|
22
|
+
<g>
|
|
23
|
+
<rect x="20" y="200" width="120" height="80" rx="8" fill="#f6f8fa" stroke="#d0d7de"/>
|
|
24
|
+
<text x="80" y="234" text-anchor="middle">Technique</text>
|
|
25
|
+
<text x="80" y="250" text-anchor="middle">catalog</text>
|
|
26
|
+
<text x="80" y="268" text-anchor="middle" font-size="10.5" font-weight="400" fill="#57606a">5 benign · MITRE</text>
|
|
27
|
+
</g>
|
|
28
|
+
<g>
|
|
29
|
+
<rect x="168" y="200" width="120" height="80" rx="8" fill="#f6f8fa" stroke="#d0d7de"/>
|
|
30
|
+
<text x="228" y="242" text-anchor="middle">Lab</text>
|
|
31
|
+
<text x="228" y="262" text-anchor="middle" font-size="10.5" font-weight="400" fill="#57606a">Docker · Replay</text>
|
|
32
|
+
</g>
|
|
33
|
+
<g>
|
|
34
|
+
<rect x="316" y="200" width="120" height="80" rx="8" fill="#f6f8fa" stroke="#d0d7de"/>
|
|
35
|
+
<text x="376" y="234" text-anchor="middle">Collector</text>
|
|
36
|
+
<text x="376" y="250" text-anchor="middle" font-size="10.5" font-weight="400" fill="#57606a">independent</text>
|
|
37
|
+
<text x="376" y="266" text-anchor="middle" font-size="10.5" font-weight="400" fill="#57606a">execve → events</text>
|
|
38
|
+
</g>
|
|
39
|
+
<g>
|
|
40
|
+
<rect x="464" y="200" width="120" height="80" rx="8" fill="#e9f6ef" stroke="#1a7f4b" stroke-width="1.5"/>
|
|
41
|
+
<text x="524" y="234" text-anchor="middle" fill="#12633a">Sigma engine</text>
|
|
42
|
+
<text x="524" y="252" text-anchor="middle" font-size="10.5" font-weight="700" fill="#1a7f4b">deterministic</text>
|
|
43
|
+
<text x="524" y="268" text-anchor="middle" font-size="10.5" font-weight="400" fill="#57606a">verdict = f(logs, rules)</text>
|
|
44
|
+
</g>
|
|
45
|
+
<g>
|
|
46
|
+
<rect x="612" y="200" width="120" height="80" rx="8" fill="#f6f8fa" stroke="#d0d7de"/>
|
|
47
|
+
<text x="672" y="242" text-anchor="middle">Coverage</text>
|
|
48
|
+
<text x="672" y="262" text-anchor="middle" font-size="10.5" font-weight="400" fill="#57606a">detected / gap</text>
|
|
49
|
+
</g>
|
|
50
|
+
<g>
|
|
51
|
+
<rect x="760" y="200" width="120" height="80" rx="8" fill="#f6f8fa" stroke="#d0d7de"/>
|
|
52
|
+
<text x="820" y="234" text-anchor="middle">Reports</text>
|
|
53
|
+
<text x="820" y="252" text-anchor="middle" font-size="10.5" font-weight="400" fill="#57606a">JSON · Markdown</text>
|
|
54
|
+
<text x="820" y="268" text-anchor="middle" font-size="10.5" font-weight="400" fill="#57606a">ATT&CK Navigator</text>
|
|
55
|
+
</g>
|
|
56
|
+
</g>
|
|
57
|
+
|
|
58
|
+
<!-- pipeline arrows -->
|
|
59
|
+
<g stroke="#57606a" stroke-width="1.6" marker-end="url(#arrow)">
|
|
60
|
+
<line x1="140" y1="240" x2="166" y2="240"/>
|
|
61
|
+
<line x1="288" y1="240" x2="314" y2="240"/>
|
|
62
|
+
<line x1="436" y1="240" x2="462" y2="240"/>
|
|
63
|
+
<line x1="584" y1="240" x2="610" y2="240"/>
|
|
64
|
+
<line x1="732" y1="240" x2="758" y2="240"/>
|
|
65
|
+
</g>
|
|
66
|
+
|
|
67
|
+
<!-- LLM connectors (dashed, red) -->
|
|
68
|
+
<g stroke="#cf222e" stroke-width="1.4" stroke-dasharray="5 4" fill="none">
|
|
69
|
+
<path d="M400,140 C400,175 300,165 260,199" marker-end="url(#arrowR)"/>
|
|
70
|
+
<path d="M672,200 C672,168 640,150 632,141" marker-end="url(#arrowR)"/>
|
|
71
|
+
</g>
|
|
72
|
+
<text x="300" y="182" font-size="10" fill="#cf222e">chooses next</text>
|
|
73
|
+
<text x="686" y="176" font-size="10" fill="#cf222e" text-anchor="start">read-only</text>
|
|
74
|
+
|
|
75
|
+
<!-- caption -->
|
|
76
|
+
<text x="24" y="320" font-size="12" fill="#1f2328">The <tspan font-weight="700">detected / gap</tspan> verdict is a pure function of logs and Sigma rules, written to disk <tspan font-weight="700">before</tspan> any model is called.</text>
|
|
77
|
+
<text x="24" y="340" font-size="12" fill="#57606a">REPLAY re-evaluates real captured telemetry offline; a test asserts the coverage is byte-identical with and without the LLM.</text>
|
|
78
|
+
</svg>
|