Çözüldü Windows Gezgini üzerinde tıklanan programların gerçek zamanlı olarak dosya yolunu edinme

Bu konu çözüldü olarak işaretlenmiştir. Çözülmediğini düşünüyorsanız konuyu rapor edebilirsiniz.
Katılım
12 Mayıs 2016
Mesajlar
1.558
Çözümler
5
Python:
import os
import win32file
import win32con
import win32gui
import win32api
import win32process
from parseJson import ParseJson
import pygetwindow as gw
import pynput.mouse
import threading
from queue import Queue

FILE_ACTION_ADDED = 0x00000001
FILE_ACTION_REMOVED = 0x00000002
FILE_ACTION_MODIFIED = 0x00000003

def systemWatcher(XylentScanner, SYSTEM_DRIVE, thread_resume):
    XYLENT_SCAN_CACHE = ParseJson('./config', 'xylent_scancache', {})
    XYLENT_CACHE_MAXSIZE = 500000  # 500KB
    file_queue = Queue()

    def on_mouse_click(x, y, button, pressed):
        if pressed:
            path_to_scan = get_file_path_from_click(x, y)
            print(f"Mouse clicked at ({x}, {y}) on file: {path_to_scan}")

            # Add file to the queue for processing in the main thread
            file_queue.put(path_to_scan)

    def get_file_path_from_click(x, y):
        hwnd = win32gui.WindowFromPoint((x, y))
        pid = win32process.GetWindowThreadProcessId(hwnd)[1]
        handle = win32api.OpenProcess(win32con.PROCESS_QUERY_INFORMATION | win32con.PROCESS_VM_READ, False, pid)
        return win32process.GetModuleFileNameEx(handle, 0)

    def process_file_queue():
        while thread_resume.is_set():
            try:
                path_to_scan = file_queue.get(timeout=1)  # Timeout to avoid blocking indefinitely
                print(f"Processing file: {path_to_scan}")

                try:
                    if os.path.isfile(path_to_scan):
                        verdict = XylentScanner.scanFile(path_to_scan)
                        XYLENT_SCAN_CACHE.setVal(path_to_scan, verdict)
                except Exception as e:
                    print(e)
                    print(f"Error scanning {path_to_scan}")

            except Queue.Empty:
                pass  # Queue is empty, continue checking

            if os.path.getsize(XYLENT_SCAN_CACHE.PATH) >= XYLENT_CACHE_MAXSIZE:
                XYLENT_SCAN_CACHE.purge()
                print("Purging")

    def file_monitor():
        while thread_resume.is_set():
            # File monitoring
            path_to_watch = SYSTEM_DRIVE + "\\"
            hDir = win32file.CreateFile(
                path_to_watch,
                1,
                win32con.FILE_SHARE_READ | win32con.FILE_SHARE_WRITE | win32con.FILE_SHARE_DELETE,
                None,
                win32con.OPEN_EXISTING,
                win32con.FILE_FLAG_BACKUP_SEMANTICS,
                None
            )

            results = win32file.ReadDirectoryChangesW(
                hDir,
                1024,
                True,
                win32con.FILE_NOTIFY_CHANGE_FILE_NAME |
                win32con.FILE_NOTIFY_CHANGE_DIR_NAME |
                win32con.FILE_NOTIFY_CHANGE_ATTRIBUTES |
                win32con.FILE_NOTIFY_CHANGE_SIZE |
                win32con.FILE_NOTIFY_CHANGE_LAST_WRITE |
                win32con.FILE_NOTIFY_CHANGE_SECURITY |
                FILE_ACTION_ADDED |
                FILE_ACTION_MODIFIED |
                FILE_ACTION_REMOVED,
                None,
                None
            )

            for action, file in results:
                path_to_scan = os.path.join(path_to_watch, file)
                print(path_to_scan)  # Print the path for debugging purposes

                # Add file to the queue for processing in the main thread
                file_queue.put(path_to_scan)

            if os.path.getsize(XYLENT_SCAN_CACHE.PATH) >= XYLENT_CACHE_MAXSIZE:
                XYLENT_SCAN_CACHE.purge()
                print("Purging")

    mouse_listener = threading.Thread(target=lambda: pynput.mouse.Listener(on_click=on_mouse_click).start())
    mouse_listener.start()

    monitor_thread = threading.Thread(target=file_monitor)
    monitor_thread.start()

    process_queue_thread = threading.Thread(target=process_file_queue)
    process_queue_thread.start()

    mouse_listener.join()  # Wait for mouse listener to finish (shouldn't happen in this case)
    monitor_thread.join()  # Wait for file monitor to finish
    process_queue_thread.join()  # Wait for file processing thread to finish

    print("RTP waiting to start...")

Mesela Windows Gezgini üzerinde a.exe'ye tıkladım. Bunu antivirüs motoru nasıl elde edebilir? Antivirüs motoru yapıyorum da. Antivirüs böyle:
1703498450007.png
 
Çözüm
Python ile yapılamaz, çözümü kaldırman sadece bu konuyu okuyan başka kişilere boş ümitler verip yanlış yere yönlendirecektir. Python asla Low-level call hooking için kullanılamaz, özellikle bahsedilen fonksiyonlar yukarıdaki gibi kritik fonksiyonlarsa C/++ harici alternatifin yok.
Python ile bunu yapabileceğini iddia ederek sadece konuya ne kadar uzak olduğunu gösteriyorsun.

"Bu kadar bilgiliysen neden yazmıyorsun" derken yazmadığımı nereden biliyorsun? Veya neden yazayım? Belki zaten benim işim budur? Veya tam tersi?
Benim amacım dosya açılıp açılmadığı kontrol etmek tıklanıp tıklanmadığını kontrol etmek saçmaymış onu fark ettim. Antivirüsler bunu yapmıyor. clamonacc bunu Linux üzerinde yapıyor. Windows üzerinde yapmak mümkünmüş. Monitör ediyorsun C:\ klasörünü öyle.

Kod:
import os
import psutil
import time

def find_processes_opening_files(folder_path):
    processes = []
    for process in psutil.process_iter(['pid', 'name']):
        try:
            open_files = process.open_files()
            for file in open_files:
                if folder_path.lower() in file.path.lower():
                    processes.append({
                        'pid': process.info['pid'],
                        'name': process.info['name'],
                        'file_path': file.path,
                    })
        except (psutil.AccessDenied, psutil.NoSuchProcess, psutil.ZombieProcess):
            pass
    return processes

if __name__ == "__main__":
    target_folder_path = r'C:\Users'

    print(f"Monitoring for processes opening files in the {target_folder_path} directory")

    try:
        while True:
            processes = find_processes_opening_files(target_folder_path)
            if processes:
                print("Processes opening files:")
                for proc in processes:
                    print(f"- PID: {proc['pid']}, Name: {proc['name']}, File Path: {proc['file_path']}")
            else:
                print("No processes opening files.")
            time.sleep(1)
    except KeyboardInterrupt:
        pass
Konu çözülmüştür.

Kodu biraz geliştirince yenisini atacağım sürekli ama öne çıkarmayacağım konuyu.

Python:
import psutil
import time
import json
from notifypy import Notify

NEW_PROCESSES_FILE = "new_processes.json"

def load_new_processes():
    try:
        with open(NEW_PROCESSES_FILE, "r") as file:
            return json.load(file)
    except (FileNotFoundError, json.JSONDecodeError):
        return []

def save_new_processes(new_processes):
    with open(NEW_PROCESSES_FILE, "w") as file:
        json.dump(new_processes, file)

def get_running_processes():
    return set((p.info['name'], p.info['exe']) for p in psutil.process_iter(['name', 'exe']))

def send_notification(title, message):
    notification = Notify()
    notification.title = title
    notification.message = message
    notification.send()

def main_program():
    previous_list = set()
    new_processes = load_new_processes()

    while True:
        # Get current running processes
        current_list = get_running_processes()

        # Compare with the previous list and find new processes
        newly_started_processes = current_list - previous_list
        new_processes.extend(newly_started_processes)

        if newly_started_processes:
            message = "\n".join([f"Path: {exe}" for name, exe in newly_started_processes])
            print("Newly started processes:", newly_started_processes)
            send_notification("New Processes", message)

        # Update the previous list
        previous_list = current_list

        # Save the updated new processes list to the file
        save_new_processes(new_processes)

        # Wait for a short period before checking again
        time.sleep(0.1)

if __name__ == "__main__":
    # Print the initially running processes
    print("Initially running processes:")
    print(get_running_processes())

    # Run the main program
    main_program()
Bu kadar yeter.

Kardeşim şimdi bu yapanı bulamaz diyenlere:
Python:
import os
import psutil
import time
import json
from notifypy import Notify
import win32evtlog
import win32security

CONFIG_FOLDER = "config"
NEW_PROCESSES_FILE = os.path.join(CONFIG_FOLDER, "new_processes.json")

# Ensure the config folder exists
if not os.path.exists(CONFIG_FOLDER):
    os.makedirs(CONFIG_FOLDER)

def load_new_processes():
    try:
        with open(NEW_PROCESSES_FILE, "r") as file:
            return json.load(file)
    except (FileNotFoundError, json.JSONDecodeError):
        return []

def save_new_processes(new_processes):
    with open(NEW_PROCESSES_FILE, "w") as file:
        json.dump(new_processes, file)

def get_running_processes():
    return set((p.info['name'], p.info['exe'], p.pid, p.ppid()) for p in psutil.process_iter(['name', 'exe', 'pid', 'ppid']))

def get_parent_process_info(pid):
    try:
        parent_pid = psutil.Process(pid).ppid()
        parent_process = psutil.Process(parent_pid)
        return {
            'name': parent_process.name(),
            'exe': parent_process.exe(),
            'pid': parent_process.pid,
        }
    except (psutil.NoSuchProcess, psutil.AccessDenied) as e:
        print(f"Error getting parent process info for PID {pid}: {e}")
        return None
    except Exception as e:
        print(f"An unexpected error occurred while getting parent process info: {e}")
        return None

def get_user_from_event_log(process_name):
    try:
        # Open the Security event log
        handle = win32evtlog.OpenEventLog(None, "Security")

        # Set the starting record to the end of the log
        flags = win32evtlog.EVENTLOG_BACKWARDS_READ | win32evtlog.EVENTLOG_SEQUENTIAL_READ
        total_records = win32evtlog.GetNumberOfEventLogRecords(handle)
        starting_record = total_records

        while True:
            # Read a batch of records
            events = win32evtlog.ReadEventLog(handle, flags, starting_record)

            if not events:
                break

            for event in events:
                # Check if the event is a process creation event (Event ID 4688)
                if event.EventID == 4688:
                    data = event.StringInserts

                    # Check if the process name matches the target process
                    if process_name.lower() in data[5].lower():
                        # Get the security identifier (SID) of the user
                        user_sid = data[1]

                        # Convert the SID to a username
                        username, _, _ = win32security.LookupAccountSid(None, win32security.GetBinarySid(user_sid))

                        return username

            # Update the starting record for the next batch
            starting_record -= len(events)

        # Close the event log handle
        win32evtlog.CloseEventLog(handle)
    except Exception as e:
        print(f"Error retrieving username from event log: {e}")
        return "Unknown"

def send_notification(title, message):
    notification = Notify()
    notification.title = title
    notification.message = message
    notification.send()

def main_program():
    previous_list = set()
    new_processes = load_new_processes()
    printed_processes = set()

    while True:
        # Get current running processes
        current_list = get_running_processes()

        # Compare with the previous list and find new processes
        newly_started_processes = current_list - previous_list
        new_processes.extend(newly_started_processes)

        if newly_started_processes:
            messages = []
            for name, exe, pid, parent_pid in newly_started_processes:
                if exe not in printed_processes:
                    # Print the running file only once
                    print(f"Running File: {exe}")
                    printed_processes.add(exe)

                parent_process_info = get_parent_process_info(pid)
                if parent_process_info is None:
                    continue  # Skip printing if parent process info is None

                parent_path = parent_process_info['exe']

                # Check if parent and child have the same location
                if parent_path != "Unknown" and exe.startswith(parent_path):
                    continue  # Skip printing if they have the same location

                # Check if parent and child have the same full path
                if os.path.abspath(exe) == os.path.abspath(parent_path):
                    continue  # Skip printing if they have the same full path

                # Retrieve the username from Windows logs
                user = get_user_from_event_log(exe)

                messages.append(f"Path: {exe}, Parent Process Path: {parent_path}, User: {user}")

                # Send notification
                send_notification("New Process Detected", f"Path: {exe}, Parent Process Path: {parent_path}, User: {user}")

            console_output = "\n".join(messages)
            print("Console Output:", console_output)

        # Update the previous list
        previous_list = current_list

        # Save the updated new processes list to the file
        save_new_processes(new_processes)

        # Wait for a short period before checking again
        time.sleep(0.1)

if __name__ == "__main__":
    # Print the initially running processes
    print("Initially running processes:")
    print(get_running_processes())

    # Run the main program
    main_program()

Abi şaka mı ya wscript.exe'yi başlatan explorer.exe evet doğru ama onun kodu prank.vbs'den geliyor.

Konu kesin olarak çözüldü: New Process Detected: Path: C:\Windows\System32\wscript.exe, Parent Process Path: C:\Windows\explorer.exe, Command Line: ('C:\\Windows\\System32\\WScript.exe', 'C:\\Users\\victim\\Desktop\\prank.vbs') Oha işe yaradı. Sonunda be.
Python:
import os
import psutil
import time
import json
from notifypy import Notify
import win32evtlog
import win32security

CONFIG_FOLDER = "config"
NEW_PROCESSES_FILE = os.path.join(CONFIG_FOLDER, "new_processes.json")

# Ensure the config folder exists
if not os.path.exists(CONFIG_FOLDER):
    os.makedirs(CONFIG_FOLDER)

def load_new_processes():
    try:
        with open(NEW_PROCESSES_FILE, "r") as file:
            return json.load(file)
    except (FileNotFoundError, json.JSONDecodeError):
        return []

def save_new_processes(new_processes):
    with open(NEW_PROCESSES_FILE, "w") as file:
        json.dump(new_processes, file)
        
def get_running_processes():
    processes = set()
    for p in psutil.process_iter(['name', 'exe', 'cmdline', 'pid', 'ppid']):
        try:
            if p.info is not None and 'name' in p.info and 'exe' in p.info:
                name = p.info['name']
                exe = p.info['exe']
                cmdline = tuple(p.info.get('cmdline', []))
                pid = p.pid
                ppid = p.ppid()
                processes.add((name, exe, cmdline, pid, ppid))
        except (psutil.NoSuchProcess, psutil.AccessDenied, psutil.ZombieProcess):
            pass  # Skip processes that are inaccessible or no longer exist
        except Exception as e:
            print(f"Error getting process info: {e}")
    return processes

def get_parent_process_info(pid):
    try:
        parent_pid = psutil.Process(pid).ppid()
        parent_process = psutil.Process(parent_pid)
        return {
            'name': parent_process.name(),
            'exe': parent_process.exe(),
            'cmdline': parent_process.cmdline(),
            'pid': parent_process.pid,
        }
    except (psutil.NoSuchProcess, psutil.AccessDenied) as e:
        print(f"Error getting parent process info for PID {pid}: {e}")
        return None
    except Exception as e:
        print(f"An unexpected error occurred while getting parent process info: {e}")
        return None

def get_user_from_event_log(process_name):
    try:
        # Open the Security event log
        handle = win32evtlog.OpenEventLog(None, "Security")

        # Set the starting record to the end of the log
        flags = win32evtlog.EVENTLOG_BACKWARDS_READ | win32evtlog.EVENTLOG_SEQUENTIAL_READ
        total_records = win32evtlog.GetNumberOfEventLogRecords(handle)
        starting_record = total_records

        while True:
            # Read a batch of records
            events = win32evtlog.ReadEventLog(handle, flags, starting_record)

            if not events:
                break

            for event in events:
                # Check if the event is a process creation event (Event ID 4688)
                if event.EventID == 4688:
                    data = event.StringInserts

                    # Check if the process name matches the target process
                    if process_name.lower() in data[5].lower():
                        return "Unknown"

            # Update the starting record for the next batch
            starting_record -= len(events)

        # Close the event log handle
        win32evtlog.CloseEventLog(handle)
    except Exception as e:
        print(f"Error retrieving username from event log: {e}")
        return "Unknown"

def send_notification(title, message):
    notification = Notify()
    notification.title = title
    notification.message = message
    notification.send()

def main_program():
    previous_list = set()
    new_processes = load_new_processes()
    printed_processes = set()

    while True:
        # Get current running processes
        current_list = get_running_processes()

        # Compare with the previous list and find new processes
        newly_started_processes = current_list - previous_list
        new_processes.extend(newly_started_processes)

        if newly_started_processes:
            messages = []
            for name, exe, cmdline, pid, parent_pid in newly_started_processes:
                if exe not in printed_processes:
                    # Print the running file only once
                    print(f"Running File: {exe}")
                    printed_processes.add(exe)

                parent_process_info = get_parent_process_info(pid)
                if parent_process_info is None:
                    continue  # Skip printing if parent process info is None

                parent_path = parent_process_info['exe']

                # Check if parent and child have the same location
                if parent_path != "Unknown" and exe.startswith(parent_path):
                    continue  # Skip printing if they have the same location

                # Check if parent and child have the same full path
                if os.path.abspath(exe) == os.path.abspath(parent_path):
                    continue  # Skip printing if they have the same full path

                # Retrieve the username from Windows logs
                user = get_user_from_event_log(exe)

                message = f"Path: {exe}, Parent Process Path: {parent_path}, Command Line: {cmdline}"

                # Print to the console
                print("New Process Detected:", message)

                messages.append(message)

            # Send notification
            if messages:
                console_output = "\n".join(messages)
                send_notification("New Process Detected", console_output)

        # Update the previous list
        previous_list = current_list

        # Save the updated new processes list to the file
        save_new_processes(new_processes)

        # Wait for a short period before checking again
        time.sleep(0.1)

if __name__ == "__main__":
    # Print the initially running processes
    print("Initially running processes:")
    print(get_running_processes())

    # Run the main program
    main_program()

Python ile yapılamaz, çözümü kaldırman sadece bu konuyu okuyan başka kişilere boş ümitler verip yanlış yere yönlendirecektir. Python asla Low-level call hooking için kullanılamaz, özellikle bahsedilen fonksiyonlar yukarıdaki gibi kritik fonksiyonlarsa C/++ harici alternatifin yok.
Python ile bunu yapabileceğini iddia ederek sadece konuya ne kadar uzak olduğunu gösteriyorsun.

"Bu kadar bilgiliysen neden yazmıyorsun" derken yazmadığımı nereden biliyorsun? Veya neden yazayım? Belki zaten benim işim budur? Veya tam tersi?
Yardımın için teşekkür ederim ama sorunu çözdüm pythonla, inanmıyorsan bakabilirsin. Ben inanmıyorum nasıl becerdiğime. Hala şoktayım. Bugün olan ikinci şokum.

Cachy OS geliştiricis jomo'ya teşekkür ederim. Log alma fikrini o söylemişti aylar önce ama ben pratiğe geçirmemiştim.

Python:
import os
import psutil
import time
import json
from notifypy import Notify
import win32evtlog
import concurrent.futures

CONFIG_FOLDER = "config"
NEW_PROCESSES_FILE = os.path.join(CONFIG_FOLDER, "new_processes.json")

# Ensure the config folder exists
if not os.path.exists(CONFIG_FOLDER):
    os.makedirs(CONFIG_FOLDER)

def load_new_processes():
    try:
        with open(NEW_PROCESSES_FILE, "r") as file:
            return json.load(file)
    except (FileNotFoundError, json.JSONDecodeError):
        return []

def save_new_processes(new_processes):
    with open(NEW_PROCESSES_FILE, "w") as file:
        json.dump(new_processes, file)

def get_running_processes():
    processes = set()
    for p in psutil.process_iter(['name', 'exe', 'cmdline', 'pid', 'ppid']):
        try:
            if p.info is not None and 'name' in p.info and 'exe' in p.info:
                name = p.info['name']
                exe = p.info['exe']
                cmdline = tuple(p.info.get('cmdline', []))
                pid = p.pid
                ppid = p.ppid()
                processes.add((name, exe, cmdline, pid, ppid))
        except (psutil.NoSuchProcess, psutil.AccessDenied, psutil.ZombieProcess):
            pass  # Skip processes that are inaccessible or no longer exist
        except Exception as e:
            print(f"Error getting process info: {e}")
    return processes

def get_parent_process_info(pid):
    try:
        parent_pid = psutil.Process(pid).ppid()
        parent_process = psutil.Process(parent_pid)
        return {
            'name': parent_process.name(),
            'exe': parent_process.exe(),
            'cmdline': parent_process.cmdline(),
            'pid': parent_process.pid,
        }
    except (psutil.NoSuchProcess, psutil.AccessDenied) as e:
        pass
    except Exception as e:
        print(f"An unexpected error occurred while getting parent process info: {e}")
        return None

def get_user_from_event_log(process_name):
    try:
        # Open the Security event log
        handle = win32evtlog.OpenEventLog(None, "Security")

        # Set the starting record to the end of the log
        flags = win32evtlog.EVENTLOG_BACKWARDS_READ | win32evtlog.EVENTLOG_SEQUENTIAL_READ
        total_records = win32evtlog.GetNumberOfEventLogRecords(handle)
        starting_record = total_records

        while True:
            # Read a batch of records
            events = win32evtlog.ReadEventLog(handle, flags, starting_record)

            if not events:
                break

            for event in events:
                # Check if the event is a process creation event (Event ID 4688)
                if event.EventID == 4688:
                    data = event.StringInserts

                    # Check if the process name matches the target process
                    if process_name.lower() in data[5].lower():
                        return "Unknown"

            # Update the starting record for the next batch
            starting_record -= len(events)

        # Close the event log handle
        win32evtlog.CloseEventLog(handle)
    except Exception as e:
        print(f"Error retrieving username from event log: {e}")
        return "Unknown"

def send_notification(title, message):
    notification = Notify()
    notification.title = title
    notification.message = message
    notification.send()

def process_checker(process_info, printed_processes):
    name, exe, cmdline, pid, parent_pid = process_info

    if exe not in printed_processes:
        # Print the running file only once
        print(f"Running File: {exe}")
        printed_processes.add(exe)

    parent_process_info = get_parent_process_info(pid)
    if parent_process_info is None or parent_process_info.get('exe') is None:
        return  # Skip processing if parent process info is None or has no executable information

    parent_path = parent_process_info['exe']

    # Check if parent and child have the same location
    if parent_path != "Unknown" and exe.startswith(parent_path):
        return  # Skip processing if they have the same location

    # Check if parent and child have the same full path
    if os.path.abspath(exe) == os.path.abspath(parent_path):
        return  # Skip processing if they have the same full path

    # Retrieve the username from Windows logs
    user = get_user_from_event_log(exe)

    message = f"Path: {exe}, Parent Process Path: {parent_path}, Command Line: {cmdline}"

    # Print to the console
    print("New Process Detected:", message)

    # Send notification
    send_notification("New Process Detected", message)

def main_program():
    previous_list = set()
    new_processes = load_new_processes()
    printed_processes = set()

    while True:
        # Get current running processes
        current_list = get_running_processes()

        # Compare with the previous list and find new processes
        newly_started_processes = current_list - previous_list
        new_processes.extend(newly_started_processes)

        if newly_started_processes:
            with concurrent.futures.ThreadPoolExecutor() as executor:
                executor.map(lambda info: process_checker(info, printed_processes), newly_started_processes)

        # Update the previous list
        previous_list = current_list

        # Save the updated new processes list to the file
        save_new_processes(new_processes)

        # Wait for a short period before checking again
        time.sleep(0.1)

if __name__ == "__main__":
    # Print the initially running processes
    print("Initially running processes:")
    print(get_running_processes())

    # Run the main program
    main_program()
Çok fazla bildirim geliyor birde sanki yeni işlemler yerine eskiden yürütülmüş yeni işlemleri bakıyor yani loga göre bakıyor gibi. Onu düzeltmek zaman alır neyse benden bu kadar yeter daha uzatmayacağım. Bundan daha iyi kod arıyorsanız kodun son halini atabilirim. Şu anlık elimde olan son kod bu ama ileride değişecektir illa.

Pardon yokmuş öyle bir şey meğerse prank.vbs null hatası vermiş ondan böyle bir ekran çıkmış. Neyse kodda sorun yok gibi.
Boşuna bu kadar uğraşmışsın. C dilinde bunu kolayca yapabilirsin. Hatta kullanıcı fareyi üstüne getirip tıklamaması bile yeterli bu kodun tespit etmesi için.
C:
#include <windows.h>
#include <stdio.h>

#define BUF_LEN (10 * (sizeof(FILE_NOTIFY_INFORMATION) + MAX_PATH))

void main() {
    char buffer[BUF_LEN];
    DWORD bytes_returned;
    HANDLE dir;

    char downloads_path[MAX_PATH];
    DWORD path_len = GetEnvironmentVariable("USERPROFILE", downloads_path, MAX_PATH);
    strcat(downloads_path, "\Downloads");

    dir = CreateFile(
        downloads_path,
        FILE_LIST_DIRECTORY,
        FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE,
        NULL,
        OPEN_EXISTING,
        FILE_FLAG_BACKUP_SEMANTICS,
        NULL
    );

    if (dir == INVALID_HANDLE_VALUE) {
        printf("Failed to open directory.\n");
        return;
    }

    while (1) {
        if (!ReadDirectoryChangesW(
            dir,
            buffer,
            BUF_LEN,
            TRUE,
            FILE_NOTIFY_CHANGE_LAST_ACCESS,
            &bytes_returned,
            NULL,
            NULL
        )) {
            printf("Failed to read directory changes.\n");
        } else {
            FILE_NOTIFY_INFORMATION* fni = (FILE_NOTIFY_INFORMATION*)buffer;
            WCHAR filename[MAX_PATH];
            memcpy(filename, fni->FileName, fni->FileNameLength);
            filename[fni->FileNameLength / sizeof(WCHAR)] = '\0';
            wprintf(L"File accessed: %s\n", filename);
        }
    }

    CloseHandle(dir);
}
1704462481572.png
1704462620025.png
Fareyle üstüne geldiğimde algıladı.
Birde diğer önerim lzma kullanarak veri tabanlarını sıkıştır. Python'da bunun için pylazma var. Kaliteli açık kaynak antivirüs projelerinde illa görmüşsündür pylazma'yı. Hayret, bu kadar kolay şeyi kimse yapamamış çok garip. Gerçek zamanlı koruma kodunda python'u bırakıp C diline geç daha mantıklı. Zaten en iyi bildiğin dil C. C olmazsa C++ o da olmazsa Rust'u seç. Fakat önerim en iyi bildiğin dilden ve düşük seviyeli bir dilden devam etmen.

Tıklamadan falan yokmuş kodda kusura bakmayın. Tıkladıktan sonraymış. İllüzyonmuş.
 
Son düzenleme:
Boşuna bu kadar uğraşmışsın. C dilinde bunu kolayca yapabilirsin. Hatta kullanıcı fareyi üstüne getirip tıklamaması bile yeterli bu kodun tespit etmesi için.
C:
#include <windows.h>
#include <stdio.h>

#define BUF_LEN (10 * (sizeof(FILE_NOTIFY_INFORMATION) + MAX_PATH))

void main() {
    char buffer[BUF_LEN];
    DWORD bytes_returned;
    HANDLE dir;

    char downloads_path[MAX_PATH];
    DWORD path_len = GetEnvironmentVariable("USERPROFILE", downloads_path, MAX_PATH);
    strcat(downloads_path, "\Downloads");

    dir = CreateFile(
        downloads_path,
        FILE_LIST_DIRECTORY,
        FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE,
        NULL,
        OPEN_EXISTING,
        FILE_FLAG_BACKUP_SEMANTICS,
        NULL
    );

    if (dir == INVALID_HANDLE_VALUE) {
        printf("Failed to open directory.\n");
        return;
    }

    while (1) {
        if (!ReadDirectoryChangesW(
            dir,
            buffer,
            BUF_LEN,
            TRUE,
            FILE_NOTIFY_CHANGE_LAST_ACCESS,
            &bytes_returned,
            NULL,
            NULL
        )) {
            printf("Failed to read directory changes.\n");
        } else {
            FILE_NOTIFY_INFORMATION* fni = (FILE_NOTIFY_INFORMATION*)buffer;
            WCHAR filename[MAX_PATH];
            memcpy(filename, fni->FileName, fni->FileNameLength);
            filename[fni->FileNameLength / sizeof(WCHAR)] = '\0';
            wprintf(L"File accessed: %s\n", filename);
        }
    }

    CloseHandle(dir);
}
Eki Görüntüle 2074984Eki Görüntüle 2074986 Fareyle üstüne geldiğimde algıladı.
Birde diğer önerim lzma kullanarak veri tabanlarını sıkıştır. Python'da bunun için pylazma var. Kaliteli açık kaynak antivirüs projelerinde illa görmüşsündür pylazma'yı. Hayret, bu kadar kolay şeyi kimse yapamamış çok garip. Gerçek zamanlı koruma kodunda python'u bırakıp C diline geç daha mantıklı. Zaten en iyi bildiğin dil C. C olmazsa C++ o da olmazsa Rust'u seç. Fakat önerim en iyi bildiğin dilden ve düşük seviyeli bir dilden devam etmen.

Tıklamadan falan yokmuş kodda kusura bakmayın. Tıkladıktan sonraymış. İllüzyonmuş.
Hocam arkadaşın Python'a fetişi olduğu için diğer dillerle yazacaklarımızı kabul etmezdi. Üstte C'nin ve C++'ın ne kadar "güvensiz" olduğundan yakınmış kullanılmamalı demiş. (hem low level'in verdiği özgürlüklerden hem de güvenlikten yararlanmak istiyor (bkz.: hem ayranım dökülmesin ..))..
 
Hocam arkadaşın Python'a fetişi olduğu için diğer dillerle yazacaklarımızı kabul etmezdi. Üstte C'nin ve C++'ın ne kadar "güvensiz" olduğundan yakınmış kullanılmamalı demiş. (hem low level'in verdiği özgürlüklerden hem de güvenlikten yararlanmak istiyor (bkz.: hem ayranım dökülmesin ..))..
Aslında python'da da yapabilir ama C diline dönüştürmek daha mantıklı. Mesela python'da böyle:
Python:
import os
import time

def get_files_with_access_time(directory):
    return {f: os.path.getatime(os.path.join(directory, f)) for f in os.listdir(directory)}

def main():
    downloads_path = os.path.expanduser('~/Downloads')
    files = get_files_with_access_time(downloads_path)
    while True:
        new_files = get_files_with_access_time(downloads_path)
        for file, access_time in new_files.items():
            if file not in files or files[file] != access_time:
                print(f"File: {file}, Last Accessed: {time.ctime(access_time)}")
        files = new_files

if name == "main":
    main()
İkinci yolu herkes biliyor zaten. C diliyle FILE_NOTIFY_CHANGE_LAST_ACCESS ile yapmak ve bunu ctypes ile veya pywin32 ile yapabilir. C dilinde kodlama yapmak daha kolay bence, şahsi fikrim.

Hocam arkadaşın Python'a fetişi olduğu için diğer dillerle yazacaklarımızı kabul etmezdi. Üstte C'nin ve C++'ın ne kadar "güvensiz" olduğundan yakınmış kullanılmamalı demiş. (hem low level'in verdiği özgürlüklerden hem de güvenlikten yararlanmak istiyor (bkz.: hem ayranım dökülmesin ..))..
Şu an arkadaş C dilinde yapıyor. gerçek zamanlı korumayı. C dili sadece dosya yollarını print ediyor pythonla alıyor çıktıları ve taratıyor. C dilini daha iyi bildiği için ve ben yardım ettiğim için rahatladı. C diline geçişin ilk aşaması bu. Birazdan github reposuna ekler C diliyle yapılmış şeyi. Konu kesin çözüldü.

Hocam arkadaşın Python'a fetişi olduğu için diğer dillerle yazacaklarımızı kabul etmezdi. Üstte C'nin ve C++'ın ne kadar "güvensiz" olduğundan yakınmış kullanılmamalı demiş. (hem low level'in verdiği özgürlüklerden hem de güvenlikten yararlanmak istiyor (bkz.: hem ayranım dökülmesin ..))..
Bu arada C++'mış attığım pardon. C++ daha iyi çünkü standart kütüphanelerle rahatlıkla çok basit düzeyde gerçek zamanlı koruma yapabilirsin.
C++:
#include <windows.h>
#include <tchar.h>
#include <stdio.h>

#ifdef UNICODE
#define tcout wprintf
#else
#define tcout printf
#endif

#define BUF_LEN (10 * (sizeof(FILE_NOTIFY_INFORMATION) + MAX_PATH))

int _tmain(int argc, _TCHAR* argv[]) {
    TCHAR buffer[BUF_LEN];
    DWORD bytes_returned;
    HANDLE dir;

    _TCHAR monitored_path[MAX_PATH] = _T("C:\\");

    dir = CreateFile(
        monitored_path,
        FILE_LIST_DIRECTORY,
        FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE,
        NULL,
        OPEN_EXISTING,
        FILE_FLAG_BACKUP_SEMANTICS,
        NULL
    );

    if (dir == INVALID_HANDLE_VALUE) {
        tcout(_T("Failed to open directory.\n"));
        return 1;
    }

    while (1) {
        if (!ReadDirectoryChangesW(
            dir,
            buffer,
            BUF_LEN,
            TRUE,
            FILE_NOTIFY_CHANGE_FILE_NAME |
            FILE_NOTIFY_CHANGE_DIR_NAME |
            FILE_NOTIFY_CHANGE_ATTRIBUTES |
            FILE_NOTIFY_CHANGE_SIZE |
            FILE_NOTIFY_CHANGE_LAST_WRITE |
            FILE_NOTIFY_CHANGE_SECURITY |
            FILE_NOTIFY_CHANGE_LAST_ACCESS,
            &bytes_returned,
            NULL,
            NULL
        )) {
            tcout(_T("Failed to read directory changes.\n"));
        }
        else {
            FILE_NOTIFY_INFORMATION* fni = (FILE_NOTIFY_INFORMATION*)buffer;
            _TCHAR full_path[MAX_PATH];
            _tcscpy_s(full_path, monitored_path);

            _tcsncat_s(full_path, fni->FileName, fni->FileNameLength / sizeof(WCHAR));
            tcout(_T("%s\n"), full_path);
        }
    }

    CloseHandle(dir);
    return 0;
}
 
Son düzenleme:

Technopat Haberler

Geri
Yukarı