Jump to content

Leaderboard

Popular Content

Showing content with the highest reputation since 11/15/2025 in all areas

  1. Wow, that looks wild. To be honest, I haven't delved deep enough into your script to really understand how the path strings for _JSON_Get() are constructed there. As I understand it, you want to map this highly hierarchical structure to a 2D arrayโ€”is that correct? From my point of view, neither manual fixed loops nor the use of _JSON_Get() are the ideal way to do this. Instead of manual nested loops, the format here literally cries out for recursion. And since _JSON_Get starts from the beginning again with each call and you can quickly get confused with the path string, you don't really need it here. You have the structure available as AutoIt data structures. So you can also process it directly to access it โ€“ you don't need _JSON_Get() for that. That is more for conveniently accessing certain values whose path you know in advance. On the other hand, first putting together a path and then using _JSON_Get to retrieve the element is artificially cumbersome, since you basically already have the element when you put the path together. So I simply implemented the whole thing recursively, and from my point of view, it seems to make sense: #include <JSON.au3> #include <Array.au3> ; extract array of devices from the json structure Global $aDevices = _extractDevices(_JSON_Parse(FileRead('Argumentum.json'))) ; display the result _ArrayDisplay($aDevices, "Devices", "", 64, "|", "Index|JSON-Path|ID|Text|Min|Value|Max|SensorID|Type|ImageURL") Func _extractDevices($mDevice, $bMaster = True, $sIndex = 0) Local Static $aDevices[0][0], $iElements Local Enum $eIdx, $ePath, $eID, $eText, $eMin, $eValue, $eMax, $eSensorID, $eType, $eImg ; check Input validity If Not IsMap($mDevice) Then Return SetError(1, 0, Null) ; first recursion level has to initialize things If $bMaster Then Redim $aDevices[8][$eImg + 1] $iElements = 0 EndIf ; add current device to result array If UBound($aDevices) <= $iElements Then Redim $aDevices[UBound($aDevices) * 2][$eImg + 1] ; resize array if necessary $aDevices[$iElements][$eIdx] = $sIndex $aDevices[$iElements][$ePath] = StringReplace(StringRegExpReplace(StringTrimLeft($sIndex, 2), "(\d+)", 'Children[$1]'), ',', '.') $aDevices[$iElements][$eID] = $mDevice["id"] $aDevices[$iElements][$eText] = $mDevice["Text"] $aDevices[$iElements][$eMin] = $mDevice["Min"] $aDevices[$iElements][$eValue] = $mDevice["Value"] $aDevices[$iElements][$eMax] = $mDevice["Max"] $aDevices[$iElements][$eSensorID] = $mDevice["SensorId"] $aDevices[$iElements][$eType] = $mDevice["Type"] $aDevices[$iElements][$eImg] = $mDevice["ImageURL"] $iElements += 1 ; process the childrens Local $aChildren = $mDevice["Children"] If IsArray($aChildren) And UBound($aChildren, 1) > 0 And UBound($aChildren, 0) = 1 Then For $i = 0 To UBound($aChildren) - 1 _extractDevices($aChildren[$i], False, $sIndex & "," & $i) Next EndIf If $bMaster Then Redim $aDevices[$iElements][$eImg + 1] Return $aDevices EndIf EndFunc I am therefore unable to assess where the problem lies in your script or whether there may even be a bug in the JSON UDF. In my script, I have therefore generated the query string for _JSON_Get() for each element in parallel, and when I use these with _JSON_Get(), it works as desired. Yes, that was highly unprofessional of me - I agree with you there. To me, it seemed logical to adjust the function to return a null instead of an empty string in the event of an error, so I simply changed it without further ado. Of course, I completely ignored the fact that this was a script-breaking change and didn't even mention it in the commit message. That's really not acceptable - sorry! I have therefore rolled it back in the GitHub repo.
    3 points
  2. 3 points
  3. WinSockUDF - TCP/UDP Networking Library for AutoIt Version: 1.1 | Author: Dao Van Trong - TRONG.PRO | AutoIt: 3.3.14.2+ ๐Ÿ“– Overview WinSockUDF is a powerful, production-ready TCP/UDP networking library for AutoIt that brings enterprise-level networking capabilities to your scripts. Built on top of the Windows Sockets API (Winsock2), it provides asynchronous, event-driven communication with advanced features that go far beyond AutoIt's built-in networking functions. This library is designed for developers who need reliable, high-performance network communication in their AutoIt applications - whether you're building chat systems, file transfer utilities, remote administration tools, or IoT device controllers. โšก Key Features Core Networking โœ… Asynchronous Event-Driven Architecture - True non-blocking I/O with elegant callback system โœ… Full Winsock2 API Access - Direct Windows Sockets implementation for maximum performance โœ… TCP Server & Client - Production-ready server with multi-client support โœ… UDP Support - Connectionless datagram communication (SendTo/RecvFrom) โœ… Multiple Simultaneous Connections - Handle hundreds of clients with ease Advanced Features ๐Ÿ”’ Binary Data Transfer - Safe transmission with automatic Base64 encoding/decoding ๐ŸŽฏ Smart Connection Management - Automatic reconnection, timeouts, and error recovery ๐Ÿ“ก Broadcasting - Send messages to all connected clients instantly ๐Ÿ” Client Management - Track, query, and control individual client connections โš™๏ธ Flexible Event System - Register custom callbacks for all network events Developer Experience ๐Ÿ“š Comprehensive Error Handling - Detailed @error/@extended codes for debugging ๐ŸŽจ Clean API Design - Intuitive function names and consistent parameter patterns ๐Ÿ“ Well Documented - Complete function reference with examples ๐Ÿš€ Production Ready - Battle-tested in real-world applications ๐Ÿ“ฆ Installation Method 1: Quick Start Download WinSockUDF.au3 from this repository Place it in your AutoIt include directory (usually C:\Program Files (x86)\AutoIt3\Include) Include it in your script: #include <WinSockUDF.au3> Method 2: Project-Local Copy WinSockUDF.au3 to your project folder Include with relative path: #include "WinSockUDF.au3" Requirements: AutoIt v3.3.14.2 or higher Windows OS (XP or later) No external dependencies required Quick Start TCP Server Example #include "WinSockUDF.au3" _TCP_Startup() ; Create server on port 8080 $hServer = _TCP_Server_Create(8080) ; Register event callbacks _TCP_Server_OnNewClient($hServer, "OnNewClient") _TCP_Server_OnReceive($hServer, "OnReceive") _TCP_Server_OnDisconnect($hServer, "OnDisconnect") ; Event loop While 1 Sleep(10) WEnd Func OnNewClient($hClient, $iError) ConsoleWrite("New client connected: " & $hClient & @CRLF) _TCP_Send($hClient, "Welcome to server!" & @CRLF) EndFunc Func OnReceive($hClient, $sData, $iError) ConsoleWrite("Received: " & $sData & @CRLF) _TCP_Send($hClient, "Echo: " & $sData) EndFunc Func OnDisconnect($hClient, $iError) ConsoleWrite("Client disconnected: " & $hClient & @CRLF) EndFunc TCP Client Example #include "WinSockUDF.au3" _TCP_Startup() ; Connect to server $hClient = _TCP_Client_Create("127.0.0.1", 8080) ; Register event callbacks _TCP_Client_OnConnect($hClient, "OnConnect") _TCP_Client_OnReceive($hClient, "OnReceive") _TCP_Client_OnDisconnect($hClient, "OnDisconnect") ; Event loop While 1 Sleep(10) WEnd Func OnConnect($hSocket, $iError) If $iError Then ConsoleWrite("Connection failed: " & $iError & @CRLF) Else ConsoleWrite("Connected successfully!" & @CRLF) _TCP_Send($hSocket, "Hello Server!") EndIf EndFunc Func OnReceive($hSocket, $sData, $iError) ConsoleWrite("Received: " & $sData & @CRLF) EndFunc Func OnDisconnect($hSocket, $iError) ConsoleWrite("Disconnected from server" & @CRLF) EndFunc Function Reference Initialization Functions Function Description _TCP_Startup() Initialize Winsock and async system _TCP_Shutdown() Close all connections and free resources TCP Server Functions Function Description _TCP_Server_Create($iPort[, $sIP = "0.0.0.0"[, $iMaxPending = 5]]) Create TCP server _TCP_Server_Stop($hSocket) Stop server and close all clients _TCP_Server_ClientList() Get array of connected clients _TCP_Server_ClientIP($hSocket) Get client IP address _TCP_Server_DisconnectClient($hSocket) Disconnect specific client _TCP_Server_Broadcast($vData) Send data to all clients _TCP_Server_OnNewClient($hServer, $sCallback) Register new client callback _TCP_Server_OnReceive($hServer, $sCallback) Register receive callback _TCP_Server_OnSend($hServer, $sCallback) Register send ready callback _TCP_Server_OnDisconnect($hServer, $sCallback) Register disconnect callback TCP Client Functions Function Description _TCP_Client_Create($sIP, $iPort[, $sSourceIP = ""[, $iSourcePort = 0[, $iTimeout = 0]]]) Create TCP client connection _TCP_Client_Stop($hSocket) Close client connection _TCP_Client_OnConnect($hClient, $sCallback) Register connect callback _TCP_Client_OnReceive($hClient, $sCallback) Register receive callback _TCP_Client_OnSend($hClient, $sCallback) Register send ready callback _TCP_Client_OnDisconnect($hClient, $sCallback) Register disconnect callback Common TCP Functions Function Description _TCP_Send($hSocket, $vData[, $iFlag = 0]) Send data through socket _TCP_Recv($hSocket, $iMaxLen[, $iFlag = 0]) Receive data from socket _TCP_Send_Ex($hSocket, $vData[, $iFlag = 0]) Send with automatic Base64 encoding _TCP_Recv_Ex($hSocket, $iMaxLen[, $iFlag = 0]) Receive with automatic Base64 decoding _TCP_NameToIP($sName) Convert hostname to IP address _TCP_GetIPs([$sServerName = ""]) Get local and public IP addresses UDP Functions Function Description _UDP_Startup() Initialize UDP system _UDP_Shutdown() Shutdown UDP system _UDP_Bind([$sSourceIP = ""[, $iSourcePort = 0]]) Create and bind UDP socket _UDP_SendTo($sIP, $iPort, $vData[, $hSocket = 0]) Send UDP packet _UDP_RecvFrom($hSocket, $iMaxLen[, $iFlag = 0]) Receive UDP packet _UDP_CloseSocket($vSocket) Close UDP socket Base64 Functions Function Description _Base64Encode($bInput[, $bNoCRLF = True]) Encode binary data to Base64 string _Base64Decode($sInput[, $bReturnBinary = False[, $iDecodeType = 1]]) Decode Base64 string _Base64EncodeStr($sInput[, $iEncodeType = 4[, $bNoCRLF = True]]) Encode string to Base64 _Base64DecodeStr($sInput[, $iDecodeType = 4]) Decode Base64 to string Path Utility Functions Function Description _PathWithSlash($sPath) Add trailing backslash to path _PathRemoveTrail($sPath) Remove trailing backslashes from path Constants Data Flags $TCP_DEFAULT_DATA = 0 ; Default string data $TCP_BINARY_DATA = 1 ; Binary data mode $TCP_EOT_DATA = 2 ; End-of-transmission marker Event Types $TCP_EVENT_SEND = 1 ; Send ready event $TCP_EVENT_RECEIVE = 2 ; Data received event $TCP_EVENT_CONNECT = 4 ; Connection established $TCP_EVENT_DISCONNECT = 8 ; Connection closed $TCP_EVENT_NEWCLIENT = 16 ; New client connected (server) Advanced Features Binary File Transfer Use _TCP_Send_Ex() and _TCP_Recv_Ex() for automatic Base64 encoding/decoding of binary data: ; Send binary file Local $bData = FileRead("image.jpg") _TCP_Send_Ex($hSocket, $bData) ; Receive binary file Local $bData = _TCP_Recv_Ex($hSocket, 8192, $TCP_BINARY_DATA) FileWrite("received.jpg", $bData) Multiple Server Support The library supports running multiple servers on different ports simultaneously with independent callback handlers. Connection Timeout Client connections support timeout parameter: ; Wait up to 5 seconds for connection $hClient = _TCP_Client_Create("192.168.1.100", 8080, "", 0, 5000) Error Handling All functions set @error on failure: -1 = General error (check @extended for WSA error code) -2 = Failed to load Winsock DLL -4 = Invalid parameters or socket not found -5 = Connection failed -6 = Timeout Example: $hServer = _TCP_Server_Create(8080) If @error Then ConsoleWrite("Failed to create server. Error: " & @error & ", Extended: " & @extended & @CRLF) Exit EndIf ๐Ÿ“š Example Applications This repository includes three complete, production-ready example applications: TCP Chat System - Full-featured chat room with authentication, private messaging, and user management UDP Chat Application - Lightweight UDP-based chat demonstrating connectionless communication Lab Manager System - Professional client-server remote administration tool with system monitoring Each example includes both client and server implementations with complete source code. ๐Ÿ’ก Use Cases ๐Ÿ’ฌ Chat Applications - Real-time messaging systems with multi-user support ๐Ÿ“ File Transfer Tools - Binary file sharing with Base64 encoding ๐Ÿ–ฅ๏ธ Remote Administration - Control and monitor computers over network ๐ŸŽฎ Game Servers - Multiplayer game networking and matchmaking ๐ŸŒ IoT Communication - Device-to-device communication and control ๐Ÿ”Œ API Servers - Custom protocol implementations and microservices ๐Ÿ“Š Data Collection - Sensor data aggregation and monitoring systems ๐Ÿ”” Notification Systems - Push notification and alert distribution Note: This library uses direct Winsock API calls for advanced networking features. Make sure to call _TCP_Startup() before using any TCP/UDP functions and _TCP_Shutdown() when done. UDF: ; #INDEX# ======================================================================================================================= ; Title .........: WinSockUDF ; AutoIt Version : 3.3.14.2+ ; Language ......: English ; Description ...: Advanced TCP/UDP networking library with async events, error handling, full Winsock2 API support ; Author(s) .....: Dao Van Trong - TRONG.PRO ; Version .......: 1.1 ; =============================================================================================================================== #include-once ; #CONSTANTS# =================================================================================================================== Global Const $TCP_DEFAULT_DATA = 0 Global Const $TCP_BINARY_DATA = 1 Global Const $TCP_EOT_DATA = 2 ; Async Events Global Const $TCP_EVENT_SEND = 1 Global Const $TCP_EVENT_RECEIVE = 2 Global Const $TCP_EVENT_CONNECT = 4 Global Const $TCP_EVENT_DISCONNECT = 8 Global Const $TCP_EVENT_NEWCLIENT = 16 ; Winsock Events (internal) Global Const $FD_READ = 1 Global Const $FD_WRITE = 2 Global Const $FD_OOB = 4 Global Const $FD_ACCEPT = 8 Global Const $FD_CONNECT = 16 Global Const $FD_CLOSE = 32 ; =============================================================================================================================== ; #VARIABLES# =================================================================================================================== Global $__TCP_hWs2_32 = -1 Global $__TCP_AsyncWindow = 0 Global $__TCP_Sockets[1][11] ; [socket, msgID, onRecv, onSend, onConnect, onDisconnect, onNewClient, ip, port, isServer, parentServer] Global $__TCP_Initialized = False ; =============================================================================================================================== ; #CURRENT# ===================================================================================================================== ; Initialization ; _TCP_Startup ; _TCP_Shutdown ; ; Server Functions ; _TCP_Server_Create ; _TCP_Server_Stop ; _TCP_Server_ClientList ; _TCP_Server_ClientIP ; _TCP_Server_DisconnectClient ; _TCP_Server_Broadcast ; _TCP_Server_OnNewClient ; _TCP_Server_OnReceive ; _TCP_Server_OnSend ; _TCP_Server_OnDisconnect ; ; Client Functions ; _TCP_Client_Create ; _TCP_Client_Stop ; _TCP_Client_OnConnect ; _TCP_Client_OnReceive ; _TCP_Client_OnSend ; _TCP_Client_OnDisconnect ; ; Common Functions ; _TCP_Send ; _TCP_Recv ; _TCP_Send_Ex ; _TCP_Recv_Ex ; _TCP_RegisterEvent ; _TCP_NameToIP ; _TCP_GetIPs ; _TCP_OnConnect (alias for Client) ; _TCP_OnDisconnect (universal) ; _TCP_OnReceive (universal) ; _TCP_OnSend (universal) ; ; UDP Functions ; _UDP_Startup ; _UDP_Shutdown ; _UDP_Bind ; _UDP_SendTo ; _UDP_RecvFrom ; _UDP_CloseSocket ; ; Base64 Functions ; _Base64Encode ; _Base64Decode ; _Base64EncodeStr ; _Base64DecodeStr ; ; Path Functions ; _PathWithSlash ; _PathRemoveTrail ; ; =============================================================================================================================== ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Startup ; Description ...: Initialize Winsock and async system ; Syntax ........: _TCP_Startup() ; Return values .: Success - 1, Failure - 0 and sets @error ; =============================================================================================================================== Func _TCP_Startup() If $__TCP_Initialized Then Return 1 Local $iResult = TCPStartup() If @error Then Return SetError(@error, 0, 0) $__TCP_hWs2_32 = DllOpen("Ws2_32.dll") If $__TCP_hWs2_32 = -1 Then Return SetError(-2, 0, 0) $__TCP_AsyncWindow = GUICreate("TCP_AsyncWindow_" & Random(1000, 9999, 1)) $__TCP_Initialized = True Return SetError(0, 0, 1) EndFunc ;==>_TCP_Startup ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Shutdown ; Description ...: Close all connections and free resources ; Syntax ........: _TCP_Shutdown() ; Return values .: Success - 1 ; =============================================================================================================================== Func _TCP_Shutdown() If Not $__TCP_Initialized Then Return 1 ; Close all sockets For $i = UBound($__TCP_Sockets) - 1 To 0 Step -1 If $__TCP_Sockets[$i][0] Then ___TCP_CloseSocket($__TCP_Sockets[$i][0]) EndIf Next ReDim $__TCP_Sockets[1][11] If $__TCP_hWs2_32 <> -1 Then DllClose($__TCP_hWs2_32) $__TCP_hWs2_32 = -1 TCPShutdown() $__TCP_Initialized = False Return 1 EndFunc ;==>_TCP_Shutdown ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_Create ; Description ...: Create TCP server with async support ; Syntax ........: _TCP_Server_Create($iPort[, $sIP = "0.0.0.0"[, $iMaxPending = 5]]) ; Parameters ....: $iPort - Port to listen on ; $sIP - [optional] IP address (default = "0.0.0.0" - all interfaces) ; $iMaxPending - [optional] Max pending connections (default = 5) ; Return values .: Success - Socket handle ; Failure - -1 and sets @error ; =============================================================================================================================== Func _TCP_Server_Create($iPort, $sIP = "0.0.0.0", $iMaxPending = 5) If Not $__TCP_Initialized Then If Not _TCP_Startup() Then Return SetError(@error, 0, -1) EndIf Local $hSocket = ___TCP_Socket() If @error Then Return SetError(@error, 0, -1) ; Bind socket Local $tSockAddr = ___TCP_SockAddr($sIP, $iPort) If @error Then ___TCP_CloseSocket($hSocket) Return SetError(@error, 0, -1) EndIf Local $aRet = DllCall($__TCP_hWs2_32, "int", "bind", "uint", $hSocket, "ptr", DllStructGetPtr($tSockAddr), "int", DllStructGetSize($tSockAddr)) If @error Or $aRet[0] <> 0 Then ___TCP_CloseSocket($hSocket) Return SetError(-1, ___TCP_WSAGetLastError(), -1) EndIf ; Listen $aRet = DllCall($__TCP_hWs2_32, "int", "listen", "uint", $hSocket, "int", $iMaxPending) If @error Or $aRet[0] <> 0 Then ___TCP_CloseSocket($hSocket) Return SetError(-1, ___TCP_WSAGetLastError(), -1) EndIf ; Setup async Local $iMsgID = 0x0400 + UBound($__TCP_Sockets) If Not ___TCP_AsyncSelect($hSocket, $__TCP_AsyncWindow, $iMsgID, $FD_ACCEPT) Then ___TCP_CloseSocket($hSocket) Return SetError(@error, @extended, -1) EndIf GUIRegisterMsg($iMsgID, "___TCP_Server_OnAccept") ; Store socket info ReDim $__TCP_Sockets[UBound($__TCP_Sockets) + 1][11] Local $idx = UBound($__TCP_Sockets) - 1 $__TCP_Sockets[$idx][0] = $hSocket $__TCP_Sockets[$idx][1] = $iMsgID $__TCP_Sockets[$idx][7] = $sIP $__TCP_Sockets[$idx][8] = $iPort $__TCP_Sockets[$idx][9] = True ; isServer $__TCP_Sockets[$idx][10] = 0 ; parentServer Return $hSocket EndFunc ;==>_TCP_Server_Create ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_Stop ; Description ...: Stop server and close all client connections ; Syntax ........: _TCP_Server_Stop($hSocket) ; Parameters ....: $hSocket - Server socket handle ; Return values .: Success - 1 ; Failure - 0 and sets @error ; =============================================================================================================================== Func _TCP_Server_Stop($hSocket) Local $iServerIdx = ___TCP_FindSocket($hSocket) If $iServerIdx < 0 Then Return SetError(-4, 0, 0) ; Close all clients of this server For $i = UBound($__TCP_Sockets) - 1 To 0 Step -1 If $i <> $iServerIdx And $__TCP_Sockets[$i][0] Then If Not $__TCP_Sockets[$i][9] Then ; Not a server ___TCP_CloseSocket($__TCP_Sockets[$i][0]) ___TCP_ArrayDelete($__TCP_Sockets, $i) EndIf EndIf Next ; Close server socket ___TCP_CloseSocket($hSocket) ___TCP_ArrayDelete($__TCP_Sockets, $iServerIdx) Return 1 EndFunc ;==>_TCP_Server_Stop ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Client_Create ; Description ...: Create TCP client connection with timeout and async support ; Syntax ........: _TCP_Client_Create($sIP, $iPort[, $sSourceIP = ""[, $iSourcePort = 0[, $iTimeout = 0]]]) ; Parameters ....: $sIP - Server IP address ; $iPort - Server port ; $sSourceIP - [optional] Local IP to bind (default = "") ; $iSourcePort - [optional] Local port to bind (default = 0) ; $iTimeout - [optional] Connection timeout in ms (0 = async without waiting) ; Return values .: Success - Socket handle ; Failure - -1 and sets @error ; =============================================================================================================================== Func _TCP_Client_Create($sIP, $iPort, $sSourceIP = "", $iSourcePort = 0, $iTimeout = 0) If Not $__TCP_Initialized Then If Not _TCP_Startup() Then Return SetError(@error, 0, -1) EndIf ; Validate parameters If Not ($iPort > 0 And $iPort < 65535) Then Return SetError(-4, 0, -1) If Not ($iSourcePort >= 0 And $iSourcePort < 65535) Then Return SetError(-4, 0, -1) Local $hSocket = ___TCP_Socket() If @error Then Return SetError(@error, 0, -1) ; Bind source if specified If $sSourceIP <> "" Or $iSourcePort > 0 Then Local $tSockAddr = ___TCP_SockAddr($sSourceIP <> "" ? $sSourceIP : "0.0.0.0", $iSourcePort) If @error Then ___TCP_CloseSocket($hSocket) Return SetError(@error, 0, -1) EndIf Local $aRet = DllCall($__TCP_hWs2_32, "int", "bind", "uint", $hSocket, "ptr", DllStructGetPtr($tSockAddr), "int", DllStructGetSize($tSockAddr)) If @error Or $aRet[0] <> 0 Then ___TCP_CloseSocket($hSocket) Return SetError(-1, ___TCP_WSAGetLastError(), -1) EndIf EndIf ; Store socket info BEFORE async setup ReDim $__TCP_Sockets[UBound($__TCP_Sockets) + 1][11] Local $idx = UBound($__TCP_Sockets) - 1 $__TCP_Sockets[$idx][0] = $hSocket $__TCP_Sockets[$idx][7] = $sIP $__TCP_Sockets[$idx][8] = $iPort $__TCP_Sockets[$idx][9] = False ; isClient $__TCP_Sockets[$idx][10] = 0 ; parentServer ; Setup async - IMPORTANT: Do this before connect Local $iMsgID = 0x0400 + $idx $__TCP_Sockets[$idx][1] = $iMsgID If Not ___TCP_AsyncSelect($hSocket, $__TCP_AsyncWindow, $iMsgID, BitOR($FD_READ, $FD_WRITE, $FD_CONNECT, $FD_CLOSE)) Then ___TCP_CloseSocket($hSocket) ___TCP_ArrayDelete($__TCP_Sockets, $idx) Return SetError(@error, @extended, -1) EndIf GUIRegisterMsg($iMsgID, "___TCP_Client_OnSocketEvent") ; Connect Local $tSockAddr = ___TCP_SockAddr($sIP, $iPort) If @error Then ___TCP_CloseSocket($hSocket) ___TCP_ArrayDelete($__TCP_Sockets, $idx) Return SetError(@error, 0, -1) EndIf Local $aRet = DllCall($__TCP_hWs2_32, "int", "connect", "uint", $hSocket, "ptr", DllStructGetPtr($tSockAddr), "int", DllStructGetSize($tSockAddr)) ; For async sockets, connect() returns SOCKET_ERROR with WSAEWOULDBLOCK Local $iError = ___TCP_WSAGetLastError() ; Check if connected immediately (rare for TCP) If Not @error And $aRet[0] = 0 Then ; Connected immediately - call connect callback if set Return $hSocket EndIf ; WSAEWOULDBLOCK (10035) is normal for async connect If $iError <> 10035 And $iError <> 0 Then ___TCP_CloseSocket($hSocket) ___TCP_ArrayDelete($__TCP_Sockets, $idx) Return SetError(-1, $iError, -1) EndIf ; Wait for connection if timeout specified If $iTimeout > 0 Then Local $hTimer = TimerInit() Local $bConnected = False While TimerDiff($hTimer) < $iTimeout Sleep(10) ; Check if socket still exists (might have been connected via callback) Local $iCheckIdx = ___TCP_FindSocket($hSocket) If $iCheckIdx >= 0 Then ; Try to check connection status Local $tErr = DllStructCreate("int") Local $aCheck = DllCall($__TCP_hWs2_32, "int", "getsockopt", _ "uint", $hSocket, "int", 0xFFFF, "int", 0x1007, _ "ptr", DllStructGetPtr($tErr), "int*", DllStructGetSize($tErr)) ; SOL_SOCKET, SO_ERROR If Not @error And $aCheck[0] = 0 Then Local $iSockErr = DllStructGetData($tErr, 1) If $iSockErr = 0 Then ; Connected successfully $bConnected = True ExitLoop ElseIf $iSockErr <> 10035 Then ; Not WSAEWOULDBLOCK ; Connection error ___TCP_CloseSocket($hSocket) ___TCP_ArrayDelete($__TCP_Sockets, $iCheckIdx) Return SetError(-1, $iSockErr, -1) EndIf EndIf Else ; Socket was removed (probably connected and then disconnected) ExitLoop EndIf WEnd ; Check timeout If Not $bConnected And TimerDiff($hTimer) >= $iTimeout Then Local $iCheckIdx = ___TCP_FindSocket($hSocket) If $iCheckIdx >= 0 Then ___TCP_CloseSocket($hSocket) ___TCP_ArrayDelete($__TCP_Sockets, $iCheckIdx) EndIf Return SetError(-6, 0, -1) ; Timeout EndIf EndIf Return $hSocket EndFunc ;==>_TCP_Client_Create ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Client_Stop ; Description ...: Close client connection ; Syntax ........: _TCP_Client_Stop($hSocket) ; Parameters ....: $hSocket - Client socket handle ; Return values .: Success - 1 ; Failure - 0 and sets @error ; =============================================================================================================================== Func _TCP_Client_Stop($hSocket) Local $idx = ___TCP_FindSocket($hSocket) If $idx < 0 Then Return SetError(-4, 0, 0) ___TCP_Shutdown($hSocket) ___TCP_CloseSocket($hSocket) ___TCP_ArrayDelete($__TCP_Sockets, $idx) Return 1 EndFunc ;==>_TCP_Client_Stop ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Send ; Description ...: Send data through socket ; Syntax ........: _TCP_Send($hSocket, $vData[, $iFlag = 0]) ; Parameters ....: $hSocket - Socket handle ; $vData - Data to send (string or binary) ; $iFlag - [optional] $TCP_DEFAULT_DATA (0) or $TCP_EOT_DATA (2) ; Return values .: Success - Number of bytes sent ; Failure - -1 and sets @error ; =============================================================================================================================== Func _TCP_Send($hSocket, $vData, $iFlag = 0) If BitAND($iFlag, $TCP_EOT_DATA) Then $vData = String($vData) & Chr(3) Local $iResult = TCPSend($hSocket, $vData) Return SetError(@error, 0, $iResult) EndFunc ;==>_TCP_Send ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Recv ; Description ...: Receive data from socket ; Syntax ........: _TCP_Recv($hSocket, $iMaxLen[, $iFlag = 0]) ; Parameters ....: $hSocket - Socket handle ; $iMaxLen - Max bytes to receive ; $iFlag - [optional] $TCP_DEFAULT_DATA (0), $TCP_BINARY_DATA (1), or $TCP_EOT_DATA (2) ; Return values .: Success - Data received ; Failure - "" and sets @error/@extended ; Remarks .......: @extended = 1 if connection closed, = 2 if EOT reached ; =============================================================================================================================== Func _TCP_Recv($hSocket, $iMaxLen, $iFlag = 0) If Not $__TCP_Initialized Then Return SetError(-1, 0, "") Local $tBuf If BitAND($iFlag, $TCP_BINARY_DATA) Then $tBuf = DllStructCreate("byte[" & $iMaxLen & "]") Else $tBuf = DllStructCreate("char[" & $iMaxLen & "]") EndIf If Not ___TCP_SetNonBlocking($hSocket) Then Return SetError(@error, 0, "") Local $aRet = DllCall($__TCP_hWs2_32, "int", "recv", "uint", $hSocket, "ptr", DllStructGetPtr($tBuf), "int", $iMaxLen, "int", 0) If @error Then Return SetError(-1, 0, "") If $aRet[0] = -1 Or $aRet[0] = 4294967295 Then Local $iError = ___TCP_WSAGetLastError() If $iError = 0 Or $iError = 10035 Then Return SetError(0, 0, "") ; WSAEWOULDBLOCK - no data Return SetError($iError, 0, "") EndIf If $aRet[0] = 0 Then Return SetError(0, 1, "") ; Connection closed Local $sResult = DllStructGetData($tBuf, 1) If BitAND($iFlag, $TCP_EOT_DATA) Then If StringRight($sResult, 1) = Chr(3) Then $sResult = StringTrimRight($sResult, 1) Return SetError(0, 2, $sResult) ; EOT reached EndIf EndIf Return SetError(0, 0, $sResult) EndFunc ;==>_TCP_Recv ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_OnNewClient ; Description ...: Register callback when new client connects ; Syntax ........: _TCP_Server_OnNewClient($hServerSocket, $sFunction) ; Parameters ....: $hServerSocket - Server socket handle ; $sFunction - Callback function name: Func OnNewClient($hClientSocket, $iError) ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Example .......: _TCP_Server_OnNewClient($hServer, "OnNewClient") ; Func OnNewClient($hClient, $iError) ; If $iError Then ConsoleWrite("Accept error: " & $iError & @CRLF) ; Else ConsoleWrite("New client: " & $hClient & @CRLF) ; EndFunc ; =============================================================================================================================== Func _TCP_Server_OnNewClient($hServerSocket, $sFunction) Return _TCP_RegisterEvent($hServerSocket, $TCP_EVENT_NEWCLIENT, $sFunction) EndFunc ;==>_TCP_Server_OnNewClient ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_OnReceive ; Description ...: Register callback when server receives data from client ; Syntax ........: _TCP_Server_OnReceive($hServerSocket, $sFunction) ; Parameters ....: $hServerSocket - Server socket handle ; $sFunction - Callback function name: Func OnReceive($hClientSocket, $sData, $iError) ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Example .......: _TCP_Server_OnReceive($hServer, "OnReceive") ; Func OnReceive($hClient, $sData, $iError) ; If Not $iError Then _TCP_Send($hClient, "Echo: " & $sData) ; EndFunc ; =============================================================================================================================== Func _TCP_Server_OnReceive($hServerSocket, $sFunction) Return _TCP_RegisterEvent($hServerSocket, $TCP_EVENT_RECEIVE, $sFunction) EndFunc ;==>_TCP_Server_OnReceive ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_OnSend ; Description ...: Register callback when server is ready to send data ; Syntax ........: _TCP_Server_OnSend($hServerSocket, $sFunction) ; Parameters ....: $hServerSocket - Server socket handle ; $sFunction - Callback function name: Func OnSend($hClientSocket, $iError) ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Example .......: _TCP_Server_OnSend($hServer, "OnSend") ; Func OnSend($hClient, $iError) ; If Not $iError Then ConsoleWrite("Ready to send on: " & $hClient & @CRLF) ; EndFunc ; =============================================================================================================================== Func _TCP_Server_OnSend($hServerSocket, $sFunction) Return _TCP_RegisterEvent($hServerSocket, $TCP_EVENT_SEND, $sFunction) EndFunc ;==>_TCP_Server_OnSend ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_OnDisconnect ; Description ...: Register callback when client disconnects ; Syntax ........: _TCP_Server_OnDisconnect($hServerSocket, $sFunction) ; Parameters ....: $hServerSocket - Server socket handle ; $sFunction - Callback function name: Func OnDisconnect($hClientSocket, $iError) ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Example .......: _TCP_Server_OnDisconnect($hServer, "OnDisconnect") ; Func OnDisconnect($hClient, $iError) ; ConsoleWrite("Client disconnected: " & $hClient & @CRLF) ; EndFunc ; =============================================================================================================================== Func _TCP_Server_OnDisconnect($hServerSocket, $sFunction) Return _TCP_RegisterEvent($hServerSocket, $TCP_EVENT_DISCONNECT, $sFunction) EndFunc ;==>_TCP_Server_OnDisconnect ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Client_OnConnect ; Description ...: Register callback when client connection succeeds/fails ; Syntax ........: _TCP_Client_OnConnect($hClientSocket, $sFunction) ; Parameters ....: $hClientSocket - Client socket handle ; $sFunction - Callback function name: Func OnConnect($hSocket, $iError) ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Example .......: _TCP_Client_OnConnect($hClient, "OnConnect") ; Func OnConnect($hSocket, $iError) ; If $iError Then ConsoleWrite("Connect failed: " & $iError & @CRLF) ; Else ConsoleWrite("Connected successfully!" & @CRLF) ; EndFunc ; =============================================================================================================================== Func _TCP_Client_OnConnect($hClientSocket, $sFunction) Return _TCP_RegisterEvent($hClientSocket, $TCP_EVENT_CONNECT, $sFunction) EndFunc ;==>_TCP_Client_OnConnect ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Client_OnReceive ; Description ...: Register callback when client receives data from server ; Syntax ........: _TCP_Client_OnReceive($hClientSocket, $sFunction) ; Parameters ....: $hClientSocket - Client socket handle ; $sFunction - Callback function name: Func OnReceive($hSocket, $sData, $iError) ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Example .......: _TCP_Client_OnReceive($hClient, "OnReceive") ; Func OnReceive($hSocket, $sData, $iError) ; If Not $iError Then ConsoleWrite("Received: " & $sData & @CRLF) ; EndFunc ; =============================================================================================================================== Func _TCP_Client_OnReceive($hClientSocket, $sFunction) Return _TCP_RegisterEvent($hClientSocket, $TCP_EVENT_RECEIVE, $sFunction) EndFunc ;==>_TCP_Client_OnReceive ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Client_OnSend ; Description ...: Register callback when client is ready to send data ; Syntax ........: _TCP_Client_OnSend($hClientSocket, $sFunction) ; Parameters ....: $hClientSocket - Client socket handle ; $sFunction - Callback function name: Func OnSend($hSocket, $iError) ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Example .......: _TCP_Client_OnSend($hClient, "OnSend") ; Func OnSend($hSocket, $iError) ; If Not $iError Then ConsoleWrite("Ready to send" & @CRLF) ; EndFunc ; =============================================================================================================================== Func _TCP_Client_OnSend($hClientSocket, $sFunction) Return _TCP_RegisterEvent($hClientSocket, $TCP_EVENT_SEND, $sFunction) EndFunc ;==>_TCP_Client_OnSend ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Client_OnDisconnect ; Description ...: Register callback when client disconnects ; Syntax ........: _TCP_Client_OnDisconnect($hClientSocket, $sFunction) ; Parameters ....: $hClientSocket - Client socket handle ; $sFunction - Callback function name: Func OnDisconnect($hSocket, $iError) ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Example .......: _TCP_Client_OnDisconnect($hClient, "OnDisconnect") ; Func OnDisconnect($hSocket, $iError) ; ConsoleWrite("Disconnected from server" & @CRLF) ; EndFunc ; =============================================================================================================================== Func _TCP_Client_OnDisconnect($hClientSocket, $sFunction) Return _TCP_RegisterEvent($hClientSocket, $TCP_EVENT_DISCONNECT, $sFunction) EndFunc ;==>_TCP_Client_OnDisconnect ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_OnConnect ; Description ...: Alias of _TCP_Client_OnConnect for simpler syntax ; Syntax ........: _TCP_OnConnect($hSocket, $sFunction) ; Parameters ....: $hSocket - Socket handle ; $sFunction - Callback function name ; Return values .: Success - 1 ; Failure - 0 and sets @error ; =============================================================================================================================== Func _TCP_OnConnect($hSocket, $sFunction) Return _TCP_Client_OnConnect($hSocket, $sFunction) EndFunc ;==>_TCP_OnConnect ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_OnReceive ; Description ...: Universal callback for both client and server ; Syntax ........: _TCP_OnReceive($hSocket, $sFunction) ; Parameters ....: $hSocket - Socket handle (client or server) ; $sFunction - Callback function name ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Remarks .......: Can be used for both client and server sockets ; =============================================================================================================================== Func _TCP_OnReceive($hSocket, $sFunction) Return _TCP_RegisterEvent($hSocket, $TCP_EVENT_RECEIVE, $sFunction) EndFunc ;==>_TCP_OnReceive ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_OnSend ; Description ...: Universal callback for both client and server ; Syntax ........: _TCP_OnSend($hSocket, $sFunction) ; Parameters ....: $hSocket - Socket handle (client or server) ; $sFunction - Callback function name ; Return values .: Success - 1 ; Failure - 0 and sets @error ; =============================================================================================================================== Func _TCP_OnSend($hSocket, $sFunction) Return _TCP_RegisterEvent($hSocket, $TCP_EVENT_SEND, $sFunction) EndFunc ;==>_TCP_OnSend ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_OnDisconnect ; Description ...: Universal callback for both client and server ; Syntax ........: _TCP_OnDisconnect($hSocket, $sFunction) ; Parameters ....: $hSocket - Socket handle (client or server) ; $sFunction - Callback function name ; Return values .: Success - 1 ; Failure - 0 and sets @error ; =============================================================================================================================== Func _TCP_OnDisconnect($hSocket, $sFunction) Return _TCP_RegisterEvent($hSocket, $TCP_EVENT_DISCONNECT, $sFunction) EndFunc ;==>_TCP_OnDisconnect ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_RegisterEvent ; Description ...: Internal function to register event callbacks ; Syntax ........: _TCP_RegisterEvent($hSocket, $iEvent, $sFunction) ; Parameters ....: $hSocket - Socket handle ; $iEvent - Event type constant ; $sFunction - Callback function name ; Return values .: Success - 1 ; Failure - 0 and sets @error ; Remarks .......: This is an internal function. Use specific _TCP_*_On* functions instead ; =============================================================================================================================== Func _TCP_RegisterEvent($hSocket, $iEvent, $sFunction) Local $idx = ___TCP_FindSocket($hSocket) If $idx < 0 Then Return SetError(-4, 0, 0) Switch $iEvent Case $TCP_EVENT_SEND $__TCP_Sockets[$idx][3] = $sFunction Case $TCP_EVENT_RECEIVE $__TCP_Sockets[$idx][2] = $sFunction Case $TCP_EVENT_CONNECT $__TCP_Sockets[$idx][4] = $sFunction Case $TCP_EVENT_DISCONNECT $__TCP_Sockets[$idx][5] = $sFunction Case $TCP_EVENT_NEWCLIENT $__TCP_Sockets[$idx][6] = $sFunction Case Else Return SetError(-4, 0, 0) EndSwitch Return 1 EndFunc ;==>_TCP_RegisterEvent ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_ClientList ; Description ...: Get list of client sockets ; Syntax ........: _TCP_Server_ClientList() ; Return values .: Array of client sockets, [0] = count ; =============================================================================================================================== Func _TCP_Server_ClientList() Local $aClients[1] = [0] For $i = 0 To UBound($__TCP_Sockets) - 1 If $__TCP_Sockets[$i][0] And Not $__TCP_Sockets[$i][9] Then ; Not a server socket ReDim $aClients[UBound($aClients) + 1] $aClients[UBound($aClients) - 1] = $__TCP_Sockets[$i][0] $aClients[0] += 1 EndIf Next Return $aClients EndFunc ;==>_TCP_Server_ClientList ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_ClientIP ; Description ...: Get IP address of client ; Syntax ........: _TCP_Server_ClientIP($hSocket) ; Parameters ....: $hSocket - Client socket handle ; Return values .: Success - IP address string ; Failure - "" and sets @error ; =============================================================================================================================== Func _TCP_Server_ClientIP($hSocket) Local $tSockAddr = DllStructCreate("short;ushort;uint;char[8]") Local $aRet = DllCall($__TCP_hWs2_32, "int", "getpeername", "int", $hSocket, "ptr", DllStructGetPtr($tSockAddr), "int*", DllStructGetSize($tSockAddr)) If @error Or $aRet[0] <> 0 Then Return SetError(-1, 0, "") $aRet = DllCall($__TCP_hWs2_32, "str", "inet_ntoa", "int", DllStructGetData($tSockAddr, 3)) If @error Then Return SetError(-1, 0, "") Return $aRet[0] EndFunc ;==>_TCP_Server_ClientIP ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_Broadcast ; Description ...: Send data to all clients ; Syntax ........: _TCP_Server_Broadcast($vData) ; Parameters ....: $vData - Data to broadcast ; Return values .: Number of clients sent to ; =============================================================================================================================== Func _TCP_Server_Broadcast($vData) Local $iCount = 0 For $i = 0 To UBound($__TCP_Sockets) - 1 If $__TCP_Sockets[$i][0] And Not $__TCP_Sockets[$i][9] Then TCPSend($__TCP_Sockets[$i][0], $vData) $iCount += 1 EndIf Next Return $iCount EndFunc ;==>_TCP_Server_Broadcast ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Server_DisconnectClient ; Description ...: Disconnect a client ; Syntax ........: _TCP_Server_DisconnectClient($hSocket) ; Parameters ....: $hSocket - Client socket handle ; Return values .: Success - 1 ; Failure - 0 and sets @error ; =============================================================================================================================== Func _TCP_Server_DisconnectClient($hSocket) Return _TCP_Client_Stop($hSocket) EndFunc ;==>_TCP_Server_DisconnectClient ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_NameToIP ; Description ...: Convert hostname to IP address ; Syntax ........: _TCP_NameToIP($sName) ; Parameters ....: $sName - Hostname ; Return values .: Success - IP address ; Failure - "" and sets @error ; =============================================================================================================================== Func _TCP_NameToIP($sName) Local $sIP = TCPNameToIP($sName) Return SetError(@error, 0, $sIP) EndFunc ;==>_TCP_NameToIP ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_GetIPs ; Description ...: Get local and public IP addresses ; Syntax ........: _TCP_GetIPs([$sServerName = ""]) ; Parameters ....: $sServerName - [optional] Server to check public IP ; Return values .: Success - Array [localIP, publicIP] ; Failure - -1 and sets @error ; =============================================================================================================================== Func _TCP_GetIPs($sServerName = "") If Not $__TCP_Initialized Then If Not _TCP_Startup() Then Return SetError(@error, 0, -1) EndIf Local $aServers[][2] = [["www.myexternalip.com/raw"], ["checkip.dyndns.org/"], ["bot.whatismyipaddress.com/"]] If $sServerName <> "" Then ReDim $aServers[UBound($aServers) + 1][2] $aServers[UBound($aServers) - 1][0] = $sServerName EndIf Local $sLocalIP = "", $sPublicIP = "" Local $hSocket = ___TCP_Socket() If @error Then Return SetError(@error, 0, -1) For $i = 0 To UBound($aServers) - 1 Local $sHost = StringRegExp($aServers[$i][0], "^([^/]+)", 1) If @error Then ContinueLoop $sHost = $sHost[0] Local $sServerIP = TCPNameToIP($sHost) If $sServerIP = "" Then ContinueLoop ; Connect Local $tSockAddr = ___TCP_SockAddr($sServerIP, 80) If @error Then ContinueLoop ___TCP_SetNonBlocking($hSocket) DllCall($__TCP_hWs2_32, "int", "connect", "uint", $hSocket, "ptr", DllStructGetPtr($tSockAddr), "int", DllStructGetSize($tSockAddr)) ; Wait for connection If Not ___TCP_WaitForConnect($hSocket, 2000) Then ___TCP_CloseSocket($hSocket) $hSocket = ___TCP_Socket() ContinueLoop EndIf ; Get local IP If $sLocalIP = "" Then Local $tLocalAddr = DllStructCreate("short;ushort;uint;char[8]") Local $aRet = DllCall($__TCP_hWs2_32, "int", "getsockname", "uint", $hSocket, "ptr", DllStructGetPtr($tLocalAddr), "int*", DllStructGetSize($tLocalAddr)) If Not @error And $aRet[0] = 0 Then $aRet = DllCall($__TCP_hWs2_32, "ptr", "inet_ntoa", "ulong", DllStructGetData($tLocalAddr, 3)) If Not @error And $aRet[0] <> Null Then $sLocalIP = DllStructGetData(DllStructCreate("char[15]", $aRet[0]), 1) EndIf EndIf EndIf ; Get public IP Local $sRequest = "GET /" & StringRegExpReplace($aServers[$i][0], "^[^/]+/?", "") & " HTTP/1.1" & @CRLF & _ "Host: " & $sHost & @CRLF & _ "Connection: close" & @CRLF & @CRLF TCPSend($hSocket, $sRequest) Sleep(500) Local $sRecv = "" Local $hTimer = TimerInit() While TimerDiff($hTimer) < 3000 Local $sChunk = _TCP_Recv($hSocket, 2048) If @extended = 1 Then ExitLoop ; Connection closed $sRecv &= $sChunk If $sChunk = "" Then Sleep(10) WEnd Local $aIP = StringRegExp($sRecv, "((?:\d{1,3}\.){3}\d{1,3})", 3) If Not @error And UBound($aIP) > 0 Then $sPublicIP = $aIP[0] ExitLoop EndIf ___TCP_CloseSocket($hSocket) $hSocket = ___TCP_Socket() Next ___TCP_CloseSocket($hSocket) If $sLocalIP = "" Or $sPublicIP = "" Then Return SetError(-6, 0, -1) Local $aResult[2] = [$sLocalIP, $sPublicIP] Return $aResult EndFunc ;==>_TCP_GetIPs ; #UDP FUNCTIONS# =============================================================================================================== ; #FUNCTION# ==================================================================================================================== ; Name ..........: _UDP_Startup ; Description ...: Initialize UDP system ; Syntax ........: _UDP_Startup() ; Return values .: Success - 1 ; Failure - 0 and sets @error ; =============================================================================================================================== Func _UDP_Startup() Local $iResult = UDPStartup() Return SetError(@error, 0, $iResult) EndFunc ;==>_UDP_Startup ; #FUNCTION# ==================================================================================================================== ; Name ..........: _UDP_Shutdown ; Description ...: Shutdown UDP system ; Syntax ........: _UDP_Shutdown() ; Return values .: Success - 1 ; Failure - 0 and sets @error ; =============================================================================================================================== Func _UDP_Shutdown() Local $iResult = UDPShutdown() Return SetError(@error, 0, $iResult) EndFunc ;==>_UDP_Shutdown ; #FUNCTION# ==================================================================================================================== ; Name ..........: _UDP_Bind ; Description ...: Create and bind UDP socket ; Syntax ........: _UDP_Bind([$sSourceIP = ""[, $iSourcePort = 0]]) ; Parameters ....: $sSourceIP - [optional] Local IP to bind (default = "") ; $iSourcePort - [optional] Local port to bind (default = 0) ; Return values .: Success - Socket handle ; Failure - -1 and sets @error ; =============================================================================================================================== Func _UDP_Bind($sSourceIP = "", $iSourcePort = 0) If Not $__TCP_Initialized Then If Not _TCP_Startup() Then Return SetError(@error, 0, -1) EndIf If Not ($iSourcePort >= 0 And $iSourcePort < 65535) Then Return SetError(-4, 0, -1) Local $aRet = DllCall($__TCP_hWs2_32, "uint", "socket", "int", 2, "int", 2, "int", 17) ; AF_INET, SOCK_DGRAM, IPPROTO_UDP If @error Then Return SetError(-1, 0, -1) If $aRet[0] = 4294967295 Or $aRet[0] = -1 Then Return SetError(-1, ___TCP_WSAGetLastError(), -1) Local $hSocket = $aRet[0] ; Bind if IP or port specified If $sSourceIP <> "" Or $iSourcePort > 0 Then Local $tSockAddr = ___TCP_SockAddr($sSourceIP <> "" ? $sSourceIP : "0.0.0.0", $iSourcePort) If @error Then ___TCP_CloseSocket($hSocket) Return SetError(@error, 0, -1) EndIf $aRet = DllCall($__TCP_hWs2_32, "int", "bind", "uint", $hSocket, "ptr", DllStructGetPtr($tSockAddr), "int", DllStructGetSize($tSockAddr)) If @error Or $aRet[0] <> 0 Then ___TCP_CloseSocket($hSocket) Return SetError(-1, ___TCP_WSAGetLastError(), -1) EndIf EndIf Return $hSocket EndFunc ;==>_UDP_Bind ; #FUNCTION# ==================================================================================================================== ; Name ..........: _UDP_SendTo ; Description ...: Send UDP packet to specified address ; Syntax ........: _UDP_SendTo($sIP, $iPort, $vData[, $hSocket = 0]) ; Parameters ....: $sIP - Destination IP address ; $iPort - Destination port ; $vData - Data to send (string or binary) ; $hSocket - [optional] Socket handle (0 = create temporary socket) ; Return values .: Success - Array [bytes_sent, socket_handle] ; Failure - -1 and sets @error ; =============================================================================================================================== Func _UDP_SendTo($sIP, $iPort, $vData, $hSocket = 0) If Not $__TCP_Initialized Then If Not _TCP_Startup() Then Return SetError(@error, 0, -1) EndIf If Not ($iPort > 0 And $iPort < 65535) Then Return SetError(-4, 0, -1) Local $bCloseAfter = False If $hSocket = 0 Then $hSocket = _UDP_Bind() If @error Then Return SetError(@error, 0, -1) $bCloseAfter = True EndIf Local $tSockAddr = ___TCP_SockAddr($sIP, $iPort) If @error Then If $bCloseAfter Then ___TCP_CloseSocket($hSocket) Return SetError(@error, 0, -1) EndIf Local $tBuf, $iLen If IsBinary($vData) Then $iLen = BinaryLen($vData) $tBuf = DllStructCreate("byte[" & $iLen & "]") DllStructSetData($tBuf, 1, $vData) Else $vData = String($vData) $iLen = StringLen($vData) $tBuf = DllStructCreate("char[" & $iLen & "]") DllStructSetData($tBuf, 1, $vData) EndIf ___TCP_SetNonBlocking($hSocket) Local $aRet = DllCall($__TCP_hWs2_32, "int", "sendto", _ "uint", $hSocket, "ptr", DllStructGetPtr($tBuf), "int", $iLen, "int", 0, _ "ptr", DllStructGetPtr($tSockAddr), "int", DllStructGetSize($tSockAddr)) If @error Or $aRet[0] = -1 Or $aRet[0] = 4294967295 Then Local $iError = ___TCP_WSAGetLastError() If $bCloseAfter Then ___TCP_CloseSocket($hSocket) Return SetError($iError, 0, -1) EndIf Local $aResult[2] = [$aRet[0], $hSocket] If $bCloseAfter Then ___TCP_CloseSocket($hSocket) Return $aResult EndFunc ;==>_UDP_SendTo ; #FUNCTION# ==================================================================================================================== ; Name ..........: _UDP_RecvFrom ; Description ...: Receive UDP packet ; Syntax ........: _UDP_RecvFrom($hSocket, $iMaxLen[, $iFlag = 0]) ; Parameters ....: $hSocket - Socket handle ; $iMaxLen - Max bytes to receive ; $iFlag - [optional] 0 = string, 1 = binary ; Return values .: Success - Array [data, source_ip, source_port] ; Failure - -1 and sets @error ; =============================================================================================================================== Func _UDP_RecvFrom($hSocket, $iMaxLen, $iFlag = 0) If Not $__TCP_Initialized Then Return SetError(-1, 0, -1) If $iMaxLen < 1 Then Return SetError(-4, 0, -1) If $iFlag <> 0 And $iFlag <> 1 Then Return SetError(-4, 0, -1) ___TCP_SetNonBlocking($hSocket) Local $tSockAddr = DllStructCreate("short;ushort;uint;char[8]") Local $tBuf If $iFlag = 1 Then $tBuf = DllStructCreate("byte[" & $iMaxLen & "]") Else $tBuf = DllStructCreate("char[" & $iMaxLen & "]") EndIf Local $aRet = DllCall($__TCP_hWs2_32, "int", "recvfrom", _ "uint", $hSocket, "ptr", DllStructGetPtr($tBuf), "int", $iMaxLen, "int", 0, _ "ptr", DllStructGetPtr($tSockAddr), "int*", DllStructGetSize($tSockAddr)) If @error Then Return SetError(-1, 0, -1) If $aRet[0] = -1 Or $aRet[0] = 4294967295 Then Local $iError = ___TCP_WSAGetLastError() If $iError = 0 Or $iError = 10035 Then Return SetError(0, 0, -1) ; WSAEWOULDBLOCK Return SetError($iError, 0, -1) EndIf Local $aResult[3] $aResult[0] = DllStructGetData($tBuf, 1) $aRet = DllCall($__TCP_hWs2_32, "ptr", "inet_ntoa", "ulong", DllStructGetData($tSockAddr, 3)) If @error Or $aRet[0] = Null Then Return SetError(-1, 0, -1) $aResult[1] = DllStructGetData(DllStructCreate("char[15]", $aRet[0]), 1) $aRet = DllCall($__TCP_hWs2_32, "ushort", "ntohs", "ushort", DllStructGetData($tSockAddr, 2)) If @error Then Return SetError(-1, 0, -1) $aResult[2] = $aRet[0] Return $aResult EndFunc ;==>_UDP_RecvFrom ; #FUNCTION# ==================================================================================================================== ; Name ..........: _UDP_CloseSocket ; Description ...: Close UDP socket ; Syntax ........: _UDP_CloseSocket($vSocket) ; Parameters ....: $vSocket - Socket handle or array from _UDP_SendTo ; Return values .: Success - 1 ; Failure - 0 and sets @error ; =============================================================================================================================== Func _UDP_CloseSocket($vSocket) Local $hSocket If IsArray($vSocket) And UBound($vSocket) = 2 Then $hSocket = $vSocket[1] Else $hSocket = $vSocket EndIf If $hSocket < 1 Then Return SetError(-4, 0, 0) Local $aRet = DllCall($__TCP_hWs2_32, "int", "closesocket", "uint", $hSocket) If @error Or $aRet[0] <> 0 Then Return SetError(___TCP_WSAGetLastError(), 0, 0) EndIf Return 1 EndFunc ;==>_UDP_CloseSocket ; #INTERNAL FUNCTIONS# ========================================================================================================== Func ___TCP_Socket() Local $aRet = DllCall($__TCP_hWs2_32, "uint", "socket", "int", 2, "int", 1, "int", 6) ; AF_INET, SOCK_STREAM, IPPROTO_TCP If @error Then Return SetError(-1, 0, -1) If $aRet[0] = 4294967295 Or $aRet[0] = -1 Then Return SetError(-1, ___TCP_WSAGetLastError(), -1) Return $aRet[0] EndFunc ;==>___TCP_Socket Func ___TCP_CloseSocket($hSocket) DllCall($__TCP_hWs2_32, "int", "closesocket", "uint", $hSocket) Return TCPCloseSocket($hSocket) EndFunc ;==>___TCP_CloseSocket Func ___TCP_Shutdown($hSocket) DllCall($__TCP_hWs2_32, "int", "shutdown", "uint", $hSocket, "int", 2) ; SD_BOTH EndFunc ;==>___TCP_Shutdown Func ___TCP_SockAddr($sIP, $iPort) Local $tAddr = DllStructCreate("short sin_family;ushort sin_port;uint S_addr;char sin_zero[8]") If @error Then Return SetError(-1, 0, False) DllStructSetData($tAddr, "sin_family", 2) ; AF_INET Local $aRet = DllCall($__TCP_hWs2_32, "ushort", "htons", "ushort", $iPort) If @error Then Return SetError(-1, 0, False) DllStructSetData($tAddr, "sin_port", $aRet[0]) If $sIP = "" Or $sIP = "0.0.0.0" Then DllStructSetData($tAddr, "S_addr", 0x00000000) Else $aRet = DllCall($__TCP_hWs2_32, "ulong", "inet_addr", "str", $sIP) If @error Or $aRet[0] = -1 Or $aRet[0] = 4294967295 Then Return SetError(-4, 0, False) DllStructSetData($tAddr, "S_addr", $aRet[0]) EndIf Return $tAddr EndFunc ;==>___TCP_SockAddr Func ___TCP_SetNonBlocking($hSocket) Local $aRet = DllCall($__TCP_hWs2_32, "int", "ioctlsocket", "uint", $hSocket, "long", 0x8004667e, "ulong*", 1) ; FIONBIO If @error Or $aRet[0] <> 0 Then Return SetError(-1, ___TCP_WSAGetLastError(), False) Return True EndFunc ;==>___TCP_SetNonBlocking Func ___TCP_AsyncSelect($hSocket, $hWnd, $iMsg, $iEvents) ; WSAAsyncSelect automatically sets socket to non-blocking mode Local $aRet = DllCall($__TCP_hWs2_32, "int", "WSAAsyncSelect", _ "uint", $hSocket, "hwnd", $hWnd, "uint", $iMsg, "int", $iEvents) If @error Or $aRet[0] <> 0 Then Return SetError(-1, ___TCP_WSAGetLastError(), False) Return True EndFunc ;==>___TCP_AsyncSelect Func ___TCP_WaitForConnect($hSocket, $iTimeout) Local $tFdWrite = DllStructCreate("uint fd_count;uint fd_array[64]") Local $tFdExcept = DllStructCreate("uint fd_count;uint fd_array[64]") Local $tTimeval = DllStructCreate("long tv_sec;long tv_usec") DllStructSetData($tFdWrite, "fd_count", 1) DllStructSetData($tFdWrite, "fd_array", $hSocket, 1) DllStructSetData($tFdExcept, "fd_count", 1) DllStructSetData($tFdExcept, "fd_array", $hSocket, 1) DllStructSetData($tTimeval, "tv_sec", Floor($iTimeout / 1000)) DllStructSetData($tTimeval, "tv_usec", Mod($iTimeout, 1000) * 1000) Local $aRet = DllCall($__TCP_hWs2_32, "int", "select", _ "int", 0, "ptr", 0, "ptr", DllStructGetPtr($tFdWrite), _ "ptr", DllStructGetPtr($tFdExcept), "ptr", DllStructGetPtr($tTimeval)) If @error Then Return SetError(-1, 0, False) If $aRet[0] = 0 Then Return SetError(-6, 0, False) ; Timeout If $aRet[0] = -1 Then Return SetError(-1, ___TCP_WSAGetLastError(), False) ; Check if connected or error If DllStructGetData($tFdWrite, "fd_count") = 1 Then Return True If DllStructGetData($tFdExcept, "fd_count") = 1 Then Local $tErr = DllStructCreate("int") $aRet = DllCall($__TCP_hWs2_32, "int", "getsockopt", _ "uint", $hSocket, "int", 0xFFFF, "int", 0x1007, _ "ptr", DllStructGetPtr($tErr), "int*", DllStructGetSize($tErr)) ; SOL_SOCKET, SO_ERROR If Not @error And $aRet[0] = 0 Then Return SetError(DllStructGetData($tErr, 1), 0, False) EndIf EndIf Return SetError(-5, 0, False) ; Not connected EndFunc ;==>___TCP_WaitForConnect Func ___TCP_WSAGetLastError() Local $aRet = DllCall($__TCP_hWs2_32, "int", "WSAGetLastError") If @error Then Return 0 Return $aRet[0] EndFunc ;==>___TCP_WSAGetLastError Func ___TCP_FindSocket($hSocket) For $i = 0 To UBound($__TCP_Sockets) - 1 If $__TCP_Sockets[$i][0] = $hSocket Then Return $i Next Return -1 EndFunc ;==>___TCP_FindSocket Func ___TCP_LoWord($iValue) Return BitAND($iValue, 0xFFFF) EndFunc ;==>___TCP_LoWord Func ___TCP_HiWord($iValue) Return BitShift($iValue, 16) EndFunc ;==>___TCP_HiWord Func ___TCP_ArrayDelete(ByRef $aArray, $iElement) If Not IsArray($aArray) Then Return SetError(1, 0, 0) Local $iUBound = UBound($aArray, 1) - 1 If $iUBound < 0 Then Return 0 If $iElement < 0 Then $iElement = 0 If $iElement > $iUBound Then $iElement = $iUBound Switch UBound($aArray, 0) Case 1 For $i = $iElement To $iUBound - 1 $aArray[$i] = $aArray[$i + 1] Next ReDim $aArray[$iUBound] Case 2 Local $iSubMax = UBound($aArray, 2) - 1 For $i = $iElement To $iUBound - 1 For $j = 0 To $iSubMax $aArray[$i][$j] = $aArray[$i + 1][$j] Next Next ReDim $aArray[$iUBound][$iSubMax + 1] Case Else Return SetError(3, 0, 0) EndSwitch Return $iUBound EndFunc ;==>___TCP_ArrayDelete ; #ASYNC EVENT HANDLERS# ======================================================================================================== Func ___TCP_Server_OnAccept($hWnd, $iMsgID, $wParam, $lParam) Local $hSocket = $wParam Local $iError = ___TCP_HiWord($lParam) Local $iEvent = ___TCP_LoWord($lParam) Abs($hWnd) ; Suppress AU3Check warning ; Find server socket Local $iServerIdx = -1 For $i = 0 To UBound($__TCP_Sockets) - 1 If $__TCP_Sockets[$i][1] = $iMsgID Then $iServerIdx = $i ExitLoop EndIf Next If $iServerIdx < 0 Then Return If $iEvent = $FD_ACCEPT Then If Not $iError Then Local $hClient = TCPAccept($hSocket) If $hClient < 0 Then Return ; Setup client async Local $iClientMsgID = 0x0400 + UBound($__TCP_Sockets) ___TCP_AsyncSelect($hClient, $__TCP_AsyncWindow, $iClientMsgID, BitOR($FD_READ, $FD_WRITE, $FD_CLOSE)) GUIRegisterMsg($iClientMsgID, "___TCP_Server_OnClientEvent") ; Store client ReDim $__TCP_Sockets[UBound($__TCP_Sockets) + 1][11] Local $idx = UBound($__TCP_Sockets) - 1 $__TCP_Sockets[$idx][0] = $hClient $__TCP_Sockets[$idx][1] = $iClientMsgID $__TCP_Sockets[$idx][7] = _TCP_Server_ClientIP($hClient) $__TCP_Sockets[$idx][9] = False ; isClient $__TCP_Sockets[$idx][10] = $hSocket ; parentServer ; Call callback If $__TCP_Sockets[$iServerIdx][6] <> "" Then Call($__TCP_Sockets[$iServerIdx][6], $hClient, $iError) EndIf Else ; Error accepting If $__TCP_Sockets[$iServerIdx][6] <> "" Then Call($__TCP_Sockets[$iServerIdx][6], 0, $iError) EndIf EndIf EndIf EndFunc ;==>___TCP_Server_OnAccept Func ___TCP_Server_OnClientEvent($hWnd, $iMsgID, $wParam, $lParam) Local $hSocket = $wParam Local $iError = ___TCP_HiWord($lParam) Local $iEvent = ___TCP_LoWord($lParam) Abs($hWnd) Local $iClientIdx = -1 For $i = 0 To UBound($__TCP_Sockets) - 1 If $__TCP_Sockets[$i][1] = $iMsgID Then $iClientIdx = $i ; BUG FIX: Don't override the actual socket handle from $wParam ; $hSocket = $__TCP_Sockets[$i][0] ; This was causing socket mismatch! ExitLoop EndIf Next If $iClientIdx < 0 Then Return ; Find parent server for this client - CRITICAL FIX for multi-server support Local $iServerIdx = -1 Local $hParentServer = $__TCP_Sockets[$iClientIdx][10] If $hParentServer > 0 Then ; Find the parent server by socket handle For $i = 0 To UBound($__TCP_Sockets) - 1 If $__TCP_Sockets[$i][0] = $hParentServer And $__TCP_Sockets[$i][9] Then $iServerIdx = $i ExitLoop EndIf Next EndIf If $iServerIdx < 0 Then Return Switch $iEvent Case $FD_READ Local $sData = TCPRecv($hSocket, 4096) If $__TCP_Sockets[$iServerIdx][2] <> "" Then Call($__TCP_Sockets[$iServerIdx][2], $hSocket, $sData, $iError) EndIf Case $FD_WRITE If $__TCP_Sockets[$iServerIdx][3] <> "" Then Call($__TCP_Sockets[$iServerIdx][3], $hSocket, $iError) EndIf Case $FD_CLOSE If $__TCP_Sockets[$iServerIdx][5] <> "" Then Call($__TCP_Sockets[$iServerIdx][5], $hSocket, $iError) EndIf ___TCP_Shutdown($hSocket) ___TCP_CloseSocket($hSocket) ___TCP_ArrayDelete($__TCP_Sockets, $iClientIdx) EndSwitch EndFunc ;==>___TCP_Server_OnClientEvent Func ___TCP_Client_OnSocketEvent($hWnd, $iMsgID, $wParam, $lParam) Local $hSocket = $wParam Local $iError = ___TCP_HiWord($lParam) Local $iEvent = ___TCP_LoWord($lParam) Abs($hWnd) Local $iClientIdx = -1 For $i = 0 To UBound($__TCP_Sockets) - 1 If $__TCP_Sockets[$i][1] = $iMsgID Then $iClientIdx = $i ; BUG FIX: Don't override the actual socket handle from $wParam ; $hSocket = $__TCP_Sockets[$i][0] ; This was causing socket mismatch! ExitLoop EndIf Next If $iClientIdx < 0 Then Return Switch $iEvent Case $FD_CONNECT ; Connection completed (success or failure) If $__TCP_Sockets[$iClientIdx][4] <> "" Then Call($__TCP_Sockets[$iClientIdx][4], $hSocket, $iError) EndIf Case $FD_READ Local $sData = TCPRecv($hSocket, 4096) If $__TCP_Sockets[$iClientIdx][2] <> "" Then Call($__TCP_Sockets[$iClientIdx][2], $hSocket, $sData, $iError) EndIf Case $FD_WRITE If $__TCP_Sockets[$iClientIdx][3] <> "" Then Call($__TCP_Sockets[$iClientIdx][3], $hSocket, $iError) EndIf Case $FD_CLOSE If $__TCP_Sockets[$iClientIdx][5] <> "" Then Call($__TCP_Sockets[$iClientIdx][5], $hSocket, $iError) EndIf ___TCP_Shutdown($hSocket) ___TCP_CloseSocket($hSocket) ___TCP_ArrayDelete($__TCP_Sockets, $iClientIdx) EndSwitch EndFunc ;==>___TCP_Client_OnSocketEvent ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Send_Ex ; Description ...: Send data through socket with automatic Base64 encoding ; Syntax ........: _TCP_Send_Ex($hSocket, $vData[, $iFlag = 0]) ; Parameters ....: $hSocket - Socket handle ; $vData - Data to send (string or binary) - auto Base64 encoded ; $iFlag - [optional] $TCP_DEFAULT_DATA (0) or $TCP_EOT_DATA (2) ; Return values .: Success - Number of bytes sent ; Failure - -1 and sets @error ; =============================================================================================================================== Func _TCP_Send_Ex($hSocket, $vData, $iFlag = 0) ; Auto encode to Base64 Local $sEncoded = _Base64Encode($vData) If @error Then Return SetError(@error, 0, -1) If BitAND($iFlag, $TCP_EOT_DATA) Then $sEncoded = $sEncoded & Chr(3) Local $iResult = TCPSend($hSocket, $sEncoded) Return SetError(@error, 0, $iResult) EndFunc ;==>_TCP_Send_Ex ; #FUNCTION# ==================================================================================================================== ; Name ..........: _TCP_Recv_Ex ; Description ...: Receive data from socket with automatic Base64 decoding ; Syntax ........: _TCP_Recv_Ex($hSocket, $iMaxLen[, $iFlag = 0]) ; Parameters ....: $hSocket - Socket handle ; $iMaxLen - Max bytes to receive (after decoding) ; $iFlag - [optional] $TCP_DEFAULT_DATA (0), $TCP_BINARY_DATA (1), or $TCP_EOT_DATA (2) ; Return values .: Success - Data received (decoded from Base64) ; Failure - "" and sets @error/@extended ; Remarks .......: @extended = 1 if connection closed, = 2 if EOT reached ; Data is automatically decoded from Base64 ; =============================================================================================================================== Func _TCP_Recv_Ex($hSocket, $iMaxLen, $iFlag = 0) If Not $__TCP_Initialized Then Return SetError(-1, 0, "") ; Calculate buffer size for Base64 (encoded is ~33% larger) Local $iBase64MaxLen = Int($iMaxLen * 1.35) + 100 Local $tBuf = DllStructCreate("char[" & $iBase64MaxLen & "]") If Not ___TCP_SetNonBlocking($hSocket) Then Return SetError(@error, 0, "") Local $aRet = DllCall($__TCP_hWs2_32, "int", "recv", "uint", $hSocket, "ptr", DllStructGetPtr($tBuf), "int", $iBase64MaxLen, "int", 0) If @error Then Return SetError(-1, 0, "") If $aRet[0] = -1 Or $aRet[0] = 4294967295 Then Local $iError = ___TCP_WSAGetLastError() If $iError = 0 Or $iError = 10035 Then Return SetError(0, 0, "") ; WSAEWOULDBLOCK - no data Return SetError($iError, 0, "") EndIf If $aRet[0] = 0 Then Return SetError(0, 1, "") ; Connection closed Local $sBase64Result = DllStructGetData($tBuf, 1) ; Check for EOT marker Local $bHasEOT = False If BitAND($iFlag, $TCP_EOT_DATA) Then If StringRight($sBase64Result, 1) = Chr(3) Then $sBase64Result = StringTrimRight($sBase64Result, 1) $bHasEOT = True EndIf EndIf ; Auto decode from Base64 Local $sDecoded = _Base64Decode($sBase64Result, True) ; Convert to binary if requested If BitAND($iFlag, $TCP_BINARY_DATA) Then $sDecoded = Binary($sDecoded) EndIf If $bHasEOT Then Return SetError(0, 2, $sDecoded) ; EOT reached EndIf Return SetError(0, 0, $sDecoded) EndFunc ;==>_TCP_Recv_Ex ; #FUNCTION# ==================================================================================================================== ; Name ..........: _Base64Encode ; Description ...: Encode binary data to Base64 string ; Syntax ........: _Base64Encode($bInput[, $bNoCRLF = True]) ; Parameters ....: $bInput - Binary data to encode (can also accept ASCII string directly) ; $bNoCRLF - [optional] True: no line breaks, False: add CRLF every 76 chars (default = True) ; Return values .: Success - Base64 encoded string ; Failure - "" and sets @error ; Remarks .......: For ASCII strings, you can use this function directly. For UTF-8 strings, use _Base64EncodeStr() instead ; Author ........: Dao Van Trong - TRONG.PRO ; =============================================================================================================================== Func _Base64Encode($bInput, $bNoCRLF = True) $bInput = Binary($bInput) Local $iFlags = 1 ; CRYPT_STRING_BASE64 If $bNoCRLF Then $iFlags = 0x40000001 ; CRYPT_STRING_BASE64 | CRYPT_STRING_NOCRLF Local $tInput = DllStructCreate("byte[" & BinaryLen($bInput) & "]") DllStructSetData($tInput, 1, $bInput) ; Get required buffer size Local $aResult = DllCall("Crypt32.dll", "bool", "CryptBinaryToStringW", _ "struct*", $tInput, _ "dword", DllStructGetSize($tInput), _ "dword", $iFlags, _ "ptr", 0, _ "dword*", 0) If @error Or Not $aResult[0] Then Return SetError(1, 0, "") Local $iSize = $aResult[5] Local $tOutput = DllStructCreate("wchar[" & $iSize & "]") ; Perform encoding $aResult = DllCall("Crypt32.dll", "bool", "CryptBinaryToStringW", _ "struct*", $tInput, _ "dword", DllStructGetSize($tInput), _ "dword", $iFlags, _ "struct*", $tOutput, _ "dword*", $iSize) If @error Or Not $aResult[0] Then Return SetError(2, 0, "") Return DllStructGetData($tOutput, 1) EndFunc ;==>_Base64Encode ; #FUNCTION# ==================================================================================================================== ; Name ..........: _Base64Decode ; Description ...: Decode Base64 string to binary or string ; Syntax ........: _Base64Decode($sInput[, $bReturnBinary = False[, $iDecodeType = 1]]) ; Parameters ....: $sInput - Base64 string to decode ; $bReturnBinary - [optional] False: return string, True: return binary (default = False) ; $iDecodeType - [optional] 1: ASCII, 4: UTF-8 (default = 1, only used when $bReturnBinary = False) ; Return values .: Success - Binary data or string ; Failure - Binary("") and sets @error ; Remarks .......: For ASCII-only data, use default parameters. For UTF-8 data, use $iDecodeType = 4. For binary data, use $bReturnBinary = True ; Author ........: Dao Van Trong - TRONG.PRO ; =============================================================================================================================== Func _Base64Decode($sInput, $bReturnBinary = False, $iDecodeType = 1) If ($iDecodeType > 4) Or ($iDecodeType < 1) Then $iDecodeType = 4 ; Remove all whitespace and CRLF $sInput = StringRegExpReplace($sInput, "\s", "") If ($sInput = "") Then Return SetError(1, 0, ($bReturnBinary ? Binary("") : "")) Local $iFlags = 1 ; CRYPT_STRING_BASE64 ; Get required buffer size Local $aResult = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryW", _ "wstr", $sInput, _ "dword", StringLen($sInput), _ "dword", $iFlags, _ "ptr", 0, _ "dword*", 0, _ "ptr", 0, _ "ptr", 0) If @error Or Not $aResult[0] Then Return SetError(2, 0, ($bReturnBinary ? Binary("") : "")) Local $iSize = $aResult[5] Local $tOutput = DllStructCreate("byte[" & $iSize & "]") ; Perform decoding $aResult = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryW", _ "wstr", $sInput, _ "dword", StringLen($sInput), _ "dword", $iFlags, _ "struct*", $tOutput, _ "dword*", $iSize, _ "ptr", 0, _ "ptr", 0) If @error Or Not $aResult[0] Then Return SetError(3, 0, ($bReturnBinary ? Binary("") : "")) Local $bBinary = DllStructGetData($tOutput, 1) If $bReturnBinary Then Return $bBinary Else ; Convert binary to string with specified encoding Return BinaryToString($bBinary, $iDecodeType) EndIf EndFunc ;==>_Base64Decode ; #FUNCTION# ==================================================================================================================== ; Name ..........: _Base64EncodeStr ; Description ...: Encode string to Base64 ; Syntax ........: _Base64EncodeStr($sInput[, $iEncodeType = 4[, $bNoCRLF = True]]) ; Parameters ....: $sInput - String to encode ; $iEncodeType - [optional] 1: ASCII, 4: UTF-8 (default = 4) ; $bNoCRLF - [optional] True: no line breaks, False: add CRLF (default = True) ; Return values .: Success - Base64 encoded string ; Failure - "" and sets @error ; Author ........: Dao Van Trong - TRONG.PRO ; =============================================================================================================================== Func _Base64EncodeStr($sInput, $iEncodeType = 4, $bNoCRLF = True) If ($iEncodeType > 4) Or ($iEncodeType < 1) Then $iEncodeType = 4 Local $bBinary = StringToBinary($sInput, $iEncodeType) Return _Base64Encode($bBinary, $bNoCRLF) EndFunc ;==>_Base64EncodeStr ; #FUNCTION# ==================================================================================================================== ; Name ..........: _Base64DecodeStr ; Description ...: Decode Base64 string to text string ; Syntax ........: _Base64DecodeStr($sInput[, $iDecodeType = 4]) ; Parameters ....: $sInput - Base64 string to decode ; $iDecodeType - [optional] 1: ASCII, 4: UTF-8 (default = 4) ; Return values .: Success - Text string ; Failure - "" and sets @error ; Author ........: Dao Van Trong - TRONG.PRO ; =============================================================================================================================== Func _Base64DecodeStr($sInput, $iDecodeType = 4) Return _Base64Decode($sInput, False, $iDecodeType) EndFunc ;==>_Base64DecodeStr ; #FUNCTION# ==================================================================================================================== ; Name ..........: _PathWithSlash ; Description ...: Add single backslash to path if not present ; Syntax ........: _PathWithSlash($sPath) ; Parameters ....: $sPath - Path string ; Return values .: Path with trailing backslash ; Author ........: Dao Van Trong - TRONG.PRO ; =============================================================================================================================== Func _PathWithSlash($sPath) Return _PathRemoveTrail($sPath) & '\' EndFunc ;==>_PathWithSlash ; #FUNCTION# ==================================================================================================================== ; Name ..........: _PathRemoveTrail ; Description ...: Remove trailing backslashes from path ; Syntax ........: _PathRemoveTrail($sPath) ; Parameters ....: $sPath - Path string ; Return values .: Path without trailing backslashes ; Author ........: Dao Van Trong - TRONG.PRO ; =============================================================================================================================== Func _PathRemoveTrail($sPath) $sPath = StringStripWS($sPath, 3) While (StringRight($sPath, 1) == '\') $sPath = StringTrimRight($sPath, 1) WEnd Return $sPath EndFunc ;==>_PathRemoveTrail
    2 points
  4. It was all my fault, I fixed it! I didn't know that the dark theme of the forum didn't invert the text colors (it seems unintelligent) Thank you all for your feedback
    2 points
  5. I am just supporting the au3stripper questions in this thread. So without looking at the details it is pretty simple to me: Does the original script work?: if Yes: Does au3stripper run cleanly without any warnings? if Yes: The stripped script should work as the original if No: You are responsible and "don't come crying to me" when you override the default to continue with force! ๐Ÿ˜‰
    2 points
  6. Description WinCred is a User Defined Function (UDF) library for AutoIt that provides a complete interface to the Windows Credential Management API. This UDF allows you to create, read, update, and delete credentials stored in the Windows Credential Manager, which is the same secure storage system used by Windows itself for storing passwords and other sensitive information. Features Create and modify credentials using _WinCred_CredWrite Read credentials from the user's credential set with _WinCred_CredRead Delete credentials using _WinCred_CredDelete Support for all credential types (Generic, Domain Password, Certificates, etc.) Configurable persistence options (Session, Local Machine, Enterprise) Full Unicode support Comprehensive error handling with detailed error codes Complete example scripts for all functions Fully documented following AutoIt UDF standards Functions The UDF provides three main functions: _WinCred_CredWrite - Creates a new credential or modifies an existing credential in the user's credential set _WinCred_CredRead - Reads a credential from the user's credential set and returns an array with all credential information _WinCred_CredDelete - Deletes a credential from the user's credential set All functions follow AutoIt's standard error handling mechanism. For detailed syntax, parameters, and return values, please refer to the function documentation in the UDF file. Constants All constants are defined in WinCredConstants.au3, including credential types ($CRED_TYPE_*), persistence options ($CRED_PERSIST_*), and flags ($CRED_PRESERVE_CREDENTIAL_BLOB). See the constants file for a complete list. Quick Start Example #include "WinCred.au3" ; Create a credential Local $sTargetName = "MyApp-Credential" Local $sUserName = "MyUsername" Local $vPassword = Binary("MySecretPassword") If _WinCred_CredWrite($sTargetName, $CRED_TYPE_GENERIC, $sUserName, $vPassword) Then ConsoleWrite("Credential created successfully!" & @CRLF) Else ConsoleWrite("Error creating credential: " & @error & @CRLF) EndIf ; Read the credential Local $aCredential = _WinCred_CredRead($sTargetName, $CRED_TYPE_GENERIC) If Not @error Then ConsoleWrite("TargetName: " & $aCredential[0] & @CRLF) ConsoleWrite("UserName: " & $aCredential[2] & @CRLF) ConsoleWrite("Blob Size: " & BinaryLen($aCredential[3]) & " bytes" & @CRLF) EndIf ; Delete the credential _WinCred_CredDelete($sTargetName, $CRED_TYPE_GENERIC) Example Scripts The UDF includes complete example scripts in the Examples directory: _WinCred_CredWrite.au3 - Demonstrates creating credentials with different persistence settings _WinCred_CredRead.au3 - Shows how to read credentials and display all available information _WinCred_CredDelete.au3 - Demonstrates deleting credentials and verifying deletion All examples are fully commented and follow AutoIt best practices. Security Notes Credentials are stored securely in the Windows Credential Manager The CredentialBlob should contain binary data (use Binary() function) For sensitive data, consider encrypting the blob before storing Documentation Full function documentation is included in the UDF file following AutoIt UDF standards. The UDF is compatible with AutoIt's built-in help file system. License This UDF is released under the MIT License. See the LICENSE file for details. Changelog See CHANGELOG.md for a complete list of changes. Links GitHub Repository: https://github.com/DonChunior/WinCred-UDF Microsoft Documentation: https://learn.microsoft.com/en-us/windows/win32/api/wincred/
    2 points
  7. It seems that this is less about index collisions. The real problem is obviously that memory areas are being used across multiple map instances. Whether this occurs exclusively when using string indices in conjunction with integer indices or in other cases as well, we cannot know here and now. Without having the source code for the implementation, we can only speculate about what is happening in the background based on the behavior. And so far, it seems to me that the memory areas for the buckets of the hash table are not completely cleaned up when dereferencing the map variable, and on the other hand, these areas are used when initializing a map variable without being fully prepared for use (e.g., memory area zeros or something like that). There may well be a clever idea behind this, for example, to increase performance or something like thatโ€”we don't know. However, the current implementation is undoubtedly a bug, and worse still, a bug whose consequences cannot really be assessed at present. Therefore, we cannot simply dismiss the issue with blanket statements such as โ€œdon't use integer keysโ€ or something similar. This naturally raises the question of how to deal with it. It has been clearly stated that bug reports should not be created for maps. Nevertheless, the bug tracker is full of tickets for maps, and they are being processed as normal. That's why I would have liked to discuss the whole thing in advance in the forum, preferably with the developers involved (actually, I wanted to do just that in the German forum first, but you had already posted the thread here...). In my opinion, the โ€œAutoIt General Help and Supportโ€ forum is not the right place for this, but rather โ€œAutoIt Technical Discussion.โ€ However, it may well be that the bug has already been fixed and has been resolved in the course of the following ticket: https://www.autoitscript.com/trac/autoit/ticket/3948 The phenomenon described there is quite similar.
    2 points
  8. In order not to pollute other threads, here's one dedicated to Windows.UI controls and examples. These are for use with Xaml Islands, NOT WinUI3 - although porting them across shouldn't be too demanding. Both methods have their pros and cons - but I'd say the XAML Island approach is bit more robust at this point in time. Don't forget to update your manifests to make this work! (background/details in this thread) Download PS. More than happy for this to be a community thing if anyone else wishes to contribute
    2 points
  9. The Open Hardware Monitor is a free open source software that monitors temperature sensors, fan speeds, voltages, load and clock speeds of a computer. I found this has a WMI implementation ( http://openhardwaremonitor.org/documentation/ ) and thought it would be nice to post here. Some code to get started on Hardware ; Generated by AutoIt ScriptOMatic ; Hardware $wbemFlagReturnImmediately = 0x10 $wbemFlagForwardOnly = 0x20 $colItems = "" $strComputer = "localhost" $OutputTitle = "" $Output = "" $Output = $Output & '<html><head><title>ScriptOMatic HTML Output</title></head><body> <style>table {font-size: 10pt; font-family: arial;} th {background-color: buttonface; font-decoration: bold;} </style><table BORDER="1"><tr><th> Property </th><th> Value </th></tr>' $OutputTitle &= '<tr bgcolor="yellow"><td>' & "Computer</td><td>&nbsp;" & $strComputer & "</td></tr>" & @CRLF $objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\OpenHardwareMonitor") $colItems = $objWMIService.ExecQuery("SELECT * FROM Hardware", "WQL", _ $wbemFlagReturnImmediately + $wbemFlagForwardOnly) If IsObj($colItems) then Local $Object_Flag = 0 For $objItem In $colItems $Object_Flag = 1 $Output &= "<tr><td>HardwareType</td><td>&nbsp;" & $objItem.HardwareType & "</td></tr>" & @CRLF $Output &= "<tr><td>Identifier</td><td>&nbsp;" & $objItem.Identifier & "</td></tr>" & @CRLF $Output &= "<tr><td>InstanceId</td><td>&nbsp;" & $objItem.InstanceId & "</td></tr>" & @CRLF $Output &= "<tr><td>Name</td><td>&nbsp;" & $objItem.Name & "</td></tr>" & @CRLF $Output &= "<tr><td>Parent</td><td>&nbsp;" & $objItem.Parent & "</td></tr>" & @CRLF $Output &= "<tr><td>ProcessId</td><td>&nbsp;" & $objItem.ProcessId & "</td></tr>" & @CRLF Next If $Object_Flag = 0 Then Msgbox(1,"WMI Output",$OutputTitle) FileWrite(@TempDir & "\Hardware.HTML", $Output ) Run(@Comspec & " /c start " & @TempDir & "\Hardware.HTML" ) Else Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Hardware" ) Endif Some code to get started on Sensor ; Generated by AutoIt ScriptOMatic $wbemFlagReturnImmediately = 0x10 $wbemFlagForwardOnly = 0x20 $colItems = "" $strComputer = "localhost" $OutputTitle = "" $Output = "" $Output = $Output & '<html><head><title>ScriptOMatic HTML Output</title></head><body> <style>table {font-size: 10pt; font-family: arial;} th {background-color: buttonface; font-decoration: bold;} </style><table BORDER="1"><tr><th> Property </th><th> Value </th></tr>' $OutputTitle &= '<tr bgcolor="yellow"><td>' & "Computer</td><td>&nbsp;" & $strComputer & "</td></tr>" & @CRLF $objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\OpenHardwareMonitor") $colItems = $objWMIService.ExecQuery("SELECT * FROM Sensor", "WQL", _ $wbemFlagReturnImmediately + $wbemFlagForwardOnly) If IsObj($colItems) then Local $Object_Flag = 0 For $objItem In $colItems $Object_Flag = 1 $Output &= "<tr><td>Identifier</td><td>&nbsp;" & $objItem.Identifier & "</td></tr>" & @CRLF $Output &= "<tr><td>Index</td><td>&nbsp;" & $objItem.Index & "</td></tr>" & @CRLF $Output &= "<tr><td>InstanceId</td><td>&nbsp;" & $objItem.InstanceId & "</td></tr>" & @CRLF $Output &= "<tr><td>Max</td><td>&nbsp;" & $objItem.Max & "</td></tr>" & @CRLF $Output &= "<tr><td>Min</td><td>&nbsp;" & $objItem.Min & "</td></tr>" & @CRLF $Output &= "<tr><td>Name</td><td>&nbsp;" & $objItem.Name & "</td></tr>" & @CRLF $Output &= "<tr><td>Parent</td><td>&nbsp;" & $objItem.Parent & "</td></tr>" & @CRLF $Output &= "<tr><td>ProcessId</td><td>&nbsp;" & $objItem.ProcessId & "</td></tr>" & @CRLF $Output &= "<tr><td>SensorType</td><td>&nbsp;" & $objItem.SensorType & "</td></tr>" & @CRLF $Output &= "<tr><td>Value</td><td>&nbsp;" & $objItem.Value & "</td></tr>" & @CRLF Next If $Object_Flag = 0 Then Msgbox(1,"WMI Output",$OutputTitle) FileWrite(@TempDir & "\Sensor.HTML", $Output ) Run(@Comspec & " /c start " & @TempDir & "\Sensor.HTML" ) Else Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Sensor" ) Endif have fun.
    1 point
  10. ioa747

    SciTE_OverlayTab

    SciTE_OverlayTab Highlighting the active & unsaved tab item in SciTE Inspired from 211131-highlighting-the-active-tab-item-in-scite/ (Thanks to BugFix ๐Ÿ†) While the original was excellent, I found that I needed to change some things. Since I made these adjustments, I decided to share the revised code. ; https://www.autoitscript.com/forum/topic/213330-scite_overlaytab/ ;-------------------------------------------------------------------------------------------------------------------------------- ; Title...........: SciTE_OverlayTab.au3 ; Description.....: Highlighting the active & unsaved tab item in SciTE ; AutoIt Version..: 3.3.18.0 Author: ioa747 Script Version: 0.4 ; Note............: Testet in Windows 11 Pro 24H2 Date:17/11/2025 ; Inspired by.....: https://www.autoitscript.com/forum/topic/211131-highlighting-the-active-tab-item-in-scite ;-------------------------------------------------------------------------------------------------------------------------------- #AutoIt3Wrapper_Au3Check_Parameters=-d -w 1 -w 2 -w 3 -w 4 -w 5 -w 6 -w 7 #include <GuiTab.au3> #include <Misc.au3> #include <WinAPISysWin.au3> #include <WindowsStylesConstants.au3> Opt('TrayIconHide', 1) _Singleton(@ScriptName) OnAutoItExitRegister(_Exit) ; Colors Const Global Const $g_hActiveColor = 0x0026FF ; 0x0026FF Blue Global Const $g_hUnSavedColor = 0xFF6A00 ; 0xFF6A00 Orange Global Const $g_iOpacity = 40 ; Set Overlay transparency to 40% opacity ; Global Variables Global $g_aOverlayHwnd[0] ; Array to store Hwnd of the overlays. Index in this array corresponds to the SciTE tab index. Global $g_SciTE_Handle = WinGetHandle('[CLASS:SciTEWindow]') If @error Then Exit ;~ While True While WinExists($g_SciTE_Handle) _SciTEState() Sleep(250) WEnd ;~ Sleep(1000) ;~ $g_SciTE_Handle = WinGetHandle('[CLASS:SciTEWindow]') ;~ WEnd ;--------------------------------------------------------------------------------------- Func _Exit() _DestroyAllOverlays() ; Destroy all overlays Exit EndFunc ;==>_Exit ;--------------------------------------------------------------------------------------- Func _SciTEState() ; Retrieve the state of the SciTEWindow. Local $iState = WinGetState($g_SciTE_Handle) Switch $iState Case 15, 47 ; exists+visible+enabled+active +maximized _UpdateTabOverlays() Case Else Sleep(250) EndSwitch EndFunc ;--------------------------------------------------------------------------------------- Func _UpdateTabOverlays() Local $hTab = _GetHwnd_SciTeTabCtrl() Local $iOldCount = UBound($g_aOverlayHwnd) If @error Then ; If the Tab Control is lost, destroy all existing overlays. If $iOldCount > 0 Then _DestroyAllOverlays() Return SetError(1) EndIf Local $iActive = _GUICtrlTab_GetCurFocus($hTab) Local $iCount = _GUICtrlTab_GetItemCount($hTab) If $iCount = 0 Then ; If the Tab Control is found but contains zero tabs, we must clean up any remaining overlays. If $iOldCount > 0 Then _DestroyAllOverlays() Return SetError(2) EndIf ; Array Cleanup and Resize If $iCount < $iOldCount Then ; Tab count decreased: Destroy overlays corresponding to the missing tabs (from iCount up to iOldCount-1) For $i = $iCount To $iOldCount - 1 If IsHWnd($g_aOverlayHwnd[$i]) Then GUIDelete($g_aOverlayHwnd[$i]) Next ReDim $g_aOverlayHwnd[$iCount] ; Resize the array to the new, smaller tab count ElseIf $iCount > $iOldCount Then ReDim $g_aOverlayHwnd[$iCount] ; Tab count increased: Resize the array to accommodate new tabs EndIf ; Update/Create necessary overlays For $i = 0 To $iCount - 1 Local $sItemText = _GUICtrlTab_GetItemText($hTab, $i) Local $tRect = _GUICtrlTab_GetItemRectEx($hTab, $i) Local $iColor = 0 ; 0 means no custom coloring is needed (Saved & Inactive) Local $hOverlay = $g_aOverlayHwnd[$i] ; Get the existing handle If $i = $iActive Then $iColor = $g_hActiveColor ; Active Tab ElseIf StringRight($sItemText, 1) = '*' Then $iColor = $g_hUnSavedColor ; Unsaved Tab EndIf If $iColor <> 0 Then ; Create or Update Overlay $g_aOverlayHwnd[$i] = _CreateOrUpdateOverlay($hTab, $i, $tRect, $iColor, $hOverlay) Else ; Destroy unnecessary overlay (if it's saved and inactive) If IsHWnd($hOverlay) Then GUIDelete($hOverlay) $g_aOverlayHwnd[$i] = 0 ; Reset array element EndIf EndIf Next EndFunc ;==>_UpdateTabOverlays ;--------------------------------------------------------------------------------------- Func _CreateOrUpdateOverlay($hTab, $iIndex, $tRectItem, $iColor, $hExistingOverlay) ; Calculates coordinates and creates/updates the transparent GUI. Local $iLeft = $tRectItem.Left Local $iTop = $tRectItem.Top Local $iWidth = $tRectItem.Right - $tRectItem.Left Local $iHeight = $tRectItem.Bottom - $tRectItem.Top Local $tPoint = DllStructCreate("int X;int Y") DllStructSetData($tPoint, "X", $iLeft) DllStructSetData($tPoint, "Y", $iTop) ; Convert client coordinates (relative to hTab) to screen coordinates _WinAPI_ClientToScreen($hTab, $tPoint) Local $iScrX = $tPoint.X Local $iScrY = $tPoint.Y Local $hOverlay = $hExistingOverlay If Not IsHWnd($hOverlay) Then ; Create the overlay GUI Local $sTitle = 'OverlayTab_' & $iIndex $hOverlay = GUICreate($sTitle, $iWidth, $iHeight, $iScrX, $iScrY, $WS_POPUP, BitOR($WS_EX_TOOLWINDOW, $WS_EX_NOACTIVATE, $WS_EX_TRANSPARENT), $hTab) GUISetBkColor($iColor) WinSetTrans($hOverlay, "", $g_iOpacity) ; Set transparency to 40% opacity GUISetState(@SW_SHOWNOACTIVATE, $hOverlay) ; Show without activating Else ; Update existing overlay GUI WinMove($hOverlay, "", $iScrX, $iScrY, $iWidth, $iHeight) ; Move and resize it GUISetBkColor($iColor, $hOverlay) ; Update color EndIf Return $hOverlay EndFunc ;==>_CreateOrUpdateOverlay ;--------------------------------------------------------------------------------------- Func _DestroyAllOverlays() ; Destroys all currently tracked overlay GUIs. For $i = 0 To UBound($g_aOverlayHwnd) - 1 Local $hOverlay = $g_aOverlayHwnd[$i] If IsHWnd($hOverlay) Then GUIDelete($hOverlay) Next ReDim $g_aOverlayHwnd[0] ; Reset the array EndFunc ;==>_DestroyAllOverlays ;--------------------------------------------------------------------------------------- Func _GetHwnd_SciTeTabCtrl() ; Local $hScite = WinGetHandle('[CLASS:SciTEWindow]') ; If @error Then Return SetError(1, 0, Null) Local $aChild, $hWndTab = Null $aChild = _WinAPI_EnumChildWindows($g_SciTE_Handle) If Not @error Then For $i = 1 To $aChild[0][0] If $aChild[$i][1] = "SciTeTabCtrl" Then $hWndTab = $aChild[$i][0] ExitLoop EndIf Next EndIf Return SetError(($hWndTab = Null ? 1 : 0), 0, $hWndTab) EndFunc ;==>_GetHwnd_SciTeTabCtrl ;--------------------------------------------------------------------------------------- Please, every comment is appreciated! leave your comments and experiences here! Thank you very much
    1 point
  11. Trong

    Delayed MouseClick()

    Because you are working on another software, you are operating that software to receive events that need time to process so you need to rest (although it is not correct, it should be confirmed by checking whether a window or some text appears before performing the action instead of just stopping for a moment)
    1 point
  12. water

    Debug Messages Monitor UDF

    Added this UDF to the wiki
    1 point
  13. This is pure gold! The IsProcessElevated() function is also fantastic. Thank you so much. As you said, it works perfectly on x86 and x64. By the way, related to this, I was able to integrate your WCD_IPC UDF into my engine script which is actually a multi-process engine. Your UDF was the only one light enough and fast enough to do the job. I actually ended up creating a "broker" process for my multi-process engine and that is where I put your IPC server function. And now with the help of your RunLow() function, I can drop the privileges of the GUI and the GUI can still control the elevated "broker" process and therefore also control the various processes. Your willingness to help combined with your abilities to educate others on this forum are absolutely top-notch!
    1 point
  14. Trong

    HardwareMonitorUDF

    Version 2.0

    22 downloads

    HardwareMonitor AutoIt UDF A comprehensive hardware monitoring library for AutoIt with 65 read-only functions to monitor CPU, GPU, RAM, Storage, Battery, and Motherboard sensors. ๐ŸŽฏ Features 100% Read-Only - Safe monitoring without hardware control Cross-Platform Compatible - Works on different Windows systems Exception Handling - Crash-free operation with graceful fallbacks Multi-GPU Support - NVIDIA and AMD Radeon GPUs Extensive Sensor Coverage - Temperature, clocks, voltages, fan speeds, and more ๐Ÿ“ฆ Package Contents HardwareMonitor.dll - Native C++ monitoring library (Only x64) HardwareMonitor.au3 - AutoIt UDF wrapper with 65 functions test_udf.au3 - Comprehensive test script demonstrating all features ๐Ÿ”ง Requirements AutoIt 3.3.14.0+ (x64 version recommended) Windows 7/8/10/11 (x64) Administrator Rights - Required for low-level hardware access Optional: PawnIO driver for enhanced motherboard monitoring ๐Ÿš€ Quick Start 1. Basic Usage #RequireAdmin #include "HardwareMonitor.au3" ; Initialize library If Not _HWMon_Initialize() Then MsgBox(16, "Error", "Failed to initialize: " & _HWMon_GetLastError()) Exit EndIf ; Get hardware information Local $aModuleInfo = _HWMon_GetModuleInfo() If @error Then MsgBox(16, "Error", "Failed to get module info") _HWMon_Shutdown() Exit EndIf ; Check available modules ConsoleWrite("Intel CPU: " & ($aModuleInfo[2] ? "Yes" : "No") & @CRLF) ConsoleWrite("AMD Radeon GPU: " & ($aModuleInfo[7] ? "Yes" : "No") & @CRLF) ConsoleWrite("Storage: " & ($aModuleInfo[9] ? "Yes" : "No") & @CRLF) ; Cleanup _HWMon_Shutdown() 2. CPU Temperature Monitoring #RequireAdmin #include "HardwareMonitor.au3" _HWMon_Initialize() ; Get Intel CPU temperatures Local $coreCount = _HWMon_IntelCPU_GetCoreCount() ConsoleWrite("CPU Cores: " & $coreCount & @CRLF) For $i = 0 To $coreCount - 1 Local $temp = _HWMon_IntelCPU_GetCoreTemperature($i) ConsoleWrite("Core " & $i & ": " & $temp & "°C" & @CRLF) Next _HWMon_Shutdown() 3. GPU Monitoring #RequireAdmin #include "HardwareMonitor.au3" _HWMon_Initialize() ; AMD Radeon GPU Local $gpuCount = _HWMon_AMDRadeon_EnumerateGPUs() If $gpuCount > 0 Then _HWMon_AMDRadeon_SelectGPU(0) _HWMon_AMDRadeon_Update() ConsoleWrite("GPU: " & _HWMon_AMDRadeon_GetGPUName() & @CRLF) ConsoleWrite("Temperature: " & _HWMon_AMDRadeon_GetGPUTemperature() & "°C" & @CRLF) ConsoleWrite("Core Clock: " & _HWMon_AMDRadeon_GetCoreClock() & " MHz" & @CRLF) ConsoleWrite("Memory Clock: " & _HWMon_AMDRadeon_GetMemoryClock() & " MHz" & @CRLF) EndIf _HWMon_Shutdown() ๐Ÿ“š Available Modules Core Functions (3) _HWMon_Initialize() - Initialize library _HWMon_GetModuleInfo() - Get available hardware modules _HWMon_Shutdown() - Cleanup and shutdown Intel CPU Monitor (4) _HWMon_IntelCPU_GetCoreCount() - Number of CPU cores _HWMon_IntelCPU_GetPackageTemperature() - Package temperature _HWMon_IntelCPU_GetCoreTemperature($core) - Individual core temperature _HWMon_IntelCPU_GetTjMax() - Maximum junction temperature AMD CPU Monitor (3) _HWMon_AMDCPU_GetCoreCount() - Number of CPU cores _HWMon_AMDCPU_GetCoreTemperature($core) - Core temperature _HWMon_AMDCPU_GetCCDTemperature($ccd) - CCD temperature (Zen 2+) NVIDIA GPU Monitor (13) _HWMon_NVIDIAGPU_EnumerateGPUs() - Count NVIDIA GPUs _HWMon_NVIDIAGPU_SelectGPU($index) - Select GPU _HWMon_NVIDIAGPU_Update() - Update sensor readings _HWMon_NVIDIAGPU_GetGPUName() - GPU name _HWMon_NVIDIAGPU_GetGPUTemperature() - GPU temperature _HWMon_NVIDIAGPU_GetCoreClock() - Core clock (MHz) _HWMon_NVIDIAGPU_GetMemoryClock() - Memory clock (MHz) _HWMon_NVIDIAGPU_GetShaderClock() - Shader clock (MHz) _HWMon_NVIDIAGPU_GetFanSpeed() - Fan speed (RPM) _HWMon_NVIDIAGPU_GetFanSpeedPercent() - Fan speed (%) _HWMon_NVIDIAGPU_GetGPUUsage() - GPU usage (%) _HWMon_NVIDIAGPU_GetMemoryUsage() - Memory usage (MB) _HWMon_NVIDIAGPU_GetPowerUsage() - Power usage (W) AMD Radeon GPU Monitor (13) _HWMon_AMDRadeon_EnumerateGPUs() - Count AMD GPUs _HWMon_AMDRadeon_SelectGPU($index) - Select GPU _HWMon_AMDRadeon_Update() - Update sensor readings _HWMon_AMDRadeon_GetGPUName() - GPU name _HWMon_AMDRadeon_GetGPUTemperature() - GPU temperature _HWMon_AMDRadeon_GetHotspotTemperature() - Hotspot temperature _HWMon_AMDRadeon_GetMemoryTemperature() - Memory temperature _HWMon_AMDRadeon_GetCoreClock() - Core clock (MHz) _HWMon_AMDRadeon_GetMemoryClock() - Memory clock (MHz) _HWMon_AMDRadeon_GetFanSpeed() - Fan speed (RPM) _HWMon_AMDRadeon_GetFanSpeedPercent() - Fan speed (%) _HWMon_AMDRadeon_GetGPUUsage() - GPU usage (%) _HWMon_AMDRadeon_GetPowerUsage() - Power usage (W) Storage Monitor (4) _HWMon_Storage_EnumerateDrives() - Count storage drives _HWMon_Storage_GetDriveName($index) - Drive name _HWMon_Storage_GetDriveType($index) - Drive type (SSD/HDD) _HWMon_Storage_GetTemperature($index) - Drive temperature RAM Monitor (10) _HWMon_RAM_Initialize() - Initialize RAM monitoring _HWMon_RAM_GetTotalMemory() - Total RAM (GB) _HWMon_RAM_GetUsedMemory() - Used RAM (GB) _HWMon_RAM_GetAvailableMemory() - Available RAM (GB) _HWMon_RAM_GetMemoryLoad() - Memory load (%) _HWMon_RAM_GetMemorySpeed() - RAM speed (MHz) _HWMon_RAM_GetMemoryVoltage() - RAM voltage (V) _HWMon_RAM_GetModuleCount() - Number of RAM modules _HWMon_RAM_GetModuleSize($index) - Module size (GB) _HWMon_RAM_GetModuleSpeed($index) - Module speed (MHz) Battery Monitor (15) _HWMon_Battery_Initialize() - Initialize battery monitoring _HWMon_Battery_IsPresent() - Check if battery present _HWMon_Battery_GetStatus() - Battery status string _HWMon_Battery_GetChargeLevel() - Charge level (%) _HWMon_Battery_GetVoltage() - Voltage (V) _HWMon_Battery_GetChargeCurrent() - Charge current (mA) _HWMon_Battery_GetDischargeCurrent() - Discharge current (mA) _HWMon_Battery_GetChargeRate() - Charge rate (W) _HWMon_Battery_GetDischargeRate() - Discharge rate (W) _HWMon_Battery_GetRemainingCapacity() - Remaining capacity (mWh) _HWMon_Battery_GetFullChargeCapacity() - Full charge capacity (mWh) _HWMon_Battery_GetDesignCapacity() - Design capacity (mWh) _HWMon_Battery_GetHealth() - Battery health (%) _HWMon_Battery_GetEstimatedTime() - Estimated time (minutes) _HWMon_Battery_GetCycleCount() - Charge cycle count Motherboard Monitor (14) _HWMon_Motherboard_Initialize() - Initialize motherboard monitoring _HWMon_Motherboard_IsChipDetected() - Check if Super I/O chip detected _HWMon_Motherboard_GetChipName() - Super I/O chip name _HWMon_Motherboard_GetTemperatureCount() - Number of temperature sensors _HWMon_Motherboard_GetTemperature($index) - Temperature sensor value _HWMon_Motherboard_GetTemperatureName($index) - Temperature sensor name _HWMon_Motherboard_GetVoltageCount() - Number of voltage sensors _HWMon_Motherboard_GetVoltage($index) - Voltage sensor value _HWMon_Motherboard_GetVoltageName($index) - Voltage sensor name _HWMon_Motherboard_GetFanCount() - Number of fan sensors _HWMon_Motherboard_GetFanSpeed($index) - Fan speed (RPM) _HWMon_Motherboard_GetFanName($index) - Fan name _HWMon_Motherboard_GetFanControlPercent($index) - Fan control (%) _HWMon_Motherboard_Update() - Update all sensor readings ๐Ÿ” Hardware Detection Module Info Array Structure Local $aModuleInfo = _HWMon_GetModuleInfo() ; [0] = Library Initialized (1/0) ; [1] = PawnIO Available (1/0) ; [2] = Intel CPU (1/0) ; [3] = AMD CPU (1/0) ; [4] = AMD CPU Family ; [5] = NVIDIA GPU (1/0) ; [6] = NVIDIA GPU Count ; [7] = AMD Radeon GPU (1/0) ; [8] = AMD Radeon GPU Count ; [9] = Storage (1/0) ; [10] = Storage Count AMD GPU Detection The library uses a 3-tier fallback system for AMD GPU detection: ADL2 API (Primary) - Full monitoring support with temperature, clocks, fan, etc. ADL1 API (Fallback) - Legacy driver support WMI (Final Fallback) - Detection only, limited monitoring Note: Some AMD GPUs may be detected but not fully monitorable due to driver limitations. If ADL fails, the GPU will be detected via WMI but monitoring functions will return 0. ๐Ÿ› ๏ธ Supported Hardware CPUs Intel Core (all generations with DTS support) AMD Ryzen (Zen, Zen+, Zen 2, Zen 3, Zen 4) GPUs NVIDIA: GeForce GTX/RTX series (NVAPI support required) AMD: Radeon RX series (ADL or WMI detection) Motherboards Supports 71 Super I/O chips from: ITE: IT8705F, IT8712F, IT8716F, IT8718F, IT8720F, IT8721F, IT8728F, IT8792E Nuvoton: NCT6775F, NCT6776F, NCT6779D, NCT6791D, NCT6792D, NCT6793D, NCT6795D, NCT6796D, NCT6797D, NCT6798D Winbond: W83627HF, W83627DHG, W83627EHF, W83667HG Fintek: F71858, F71862, F71869, F71882, F71889ED, F71889AD SMSC: SCH5027 โš ๏ธ Important Notes Administrator Rights All hardware monitoring requires administrator privileges. Always use #RequireAdmin in your scripts. Error Handling Always check for errors after function calls: Local $result = _HWMon_SomeFunction() If @error Then ConsoleWrite("Error: " & _HWMon_GetLastError() & @CRLF) EndIf Update Functions Some modules require calling Update() before reading sensors: _HWMon_NVIDIAGPU_Update() _HWMon_AMDRadeon_Update() _HWMon_Motherboard_Update() Cleanup Always call _HWMon_Shutdown() before exiting to properly cleanup resources. ๐Ÿ› Troubleshooting "Library not initialized" Ensure you called _HWMon_Initialize() first Check if DLL is in the same folder as your script Verify you're running as administrator "Module not available" Check _HWMon_GetModuleInfo() to see which modules are detected Some hardware may not be supported (e.g., laptop motherboards) AMD GPU may be detected but not monitorable (driver limitation) Crashes or Unexpected Behavior Ensure you're using the x64 version of AutoIt Update your GPU drivers to the latest version Check _HWMon_GetLastError() for detailed error messages ๐Ÿ“„ License This library is provided as-is for hardware monitoring purposes only. No hardware control or modification is performed. ๐Ÿ™ Credits Built using: NVAPI - NVIDIA GPU monitoring ADL - AMD GPU monitoring WMI - Windows Management Instrumentation fallback PawnIO - Low-level I/O access for motherboard monitoring ๐Ÿ“ž Support For issues, questions, or feature requests, please check: This README for common solutions test_udf.au3 for usage examples Error messages from _HWMon_GetLastError() Status: Production Ready โœ…
    1 point
  15. Here (tested both x86 and x64) ; From Nine #RequireAdmin #AutoIt3Wrapper_UseX64=y #include <WinAPI.au3> Example() Func Example() Local $iPID = RunLow(@ComSpec, " /k Title Low") ConsoleWrite($iPID & " : " & IsProcessElevated($iPID) & @CRLF) EndFunc ;==>Example Func IsProcessElevated($iPID) Local $aRet, $iError = 0 Local $hProcess = _WinAPI_OpenProcess($PROCESS_QUERY_LIMITED_INFORMATION, False, $iPID, True) If Not $hProcess Then Return SetError(1, 0, False) Local $hToken = _WinAPI_OpenProcessToken($TOKEN_QUERY, $hProcess) If Not $hToken Then $iError = 2 Else $aRet = DllCall('advapi32.dll', 'bool', 'GetTokenInformation', 'handle', $hToken, 'uint', 20, 'uint*', 0, 'dword', 4, 'dword*', 0) ; TOKEN_ELEVATION If @error Or Not $aRet[0] Then $iError = 3 EndIf _WinAPI_CloseHandle($hToken) _WinAPI_CloseHandle($hProcess) If $iError Then Return SetError($iError, 0, False) Return $aRet[3] = 1 EndFunc ;==>IsProcessElevated Func RunLow($sPath, $sCmd = "") Local $hProcess = _WinAPI_OpenProcess($PROCESS_QUERY_INFORMATION, False, ProcessExists("explorer.exe")) Local $hToken = _WinAPI_OpenProcessToken($TOKEN_DUPLICATE, $hProcess) Local $hDupToken = _WinAPI_DuplicateTokenEx($hToken, $TOKEN_ALL_ACCESS, $SECURITYIMPERSONATION) Local $tSTARTUPINFO = DllStructCreate($tagSTARTUPINFO) $tSTARTUPINFO.Size = DllStructGetSize($tSTARTUPINFO) Local $tPROCESS = DllStructCreate($tagPROCESS_INFORMATION) _WinAPI_CreateProcessWithToken($sPath, $sCmd, 0, $tSTARTUPINFO, $tPROCESS, $hDupToken) _WinAPI_CloseHandle($hDupToken) _WinAPI_CloseHandle($hToken) _WinAPI_CloseHandle($hProcess) Return $tPROCESS.ProcessID EndFunc ;==>RunLow
    1 point
  16. I have removed the redundant - or, non-essential lines...which are implemented in "other" scripts...but of which are NOT required here. Thanks for the clarification....
    1 point
  17. It could be something like this. #include <AutoItConstants.au3> Opt("MustDeclareVars", 1) Global $iTimeOut = 100 ; **** Preset Configuration Array **** ; This is a 2D array holding all the data that changes between presets. ; Column 0: Preset Name - e.g. "Preset 002" ; Column 1: AmpSimView MouseClick Y-coordinate - e.g. 544 or 564 ; Column 2: Mouse positioning X-coordinate - e.g. 885 ; Column 3: Mouse positioning Y-coordinate - e.g. 222 Global $aPresets[2][4] = [ _ ["Preset 002", 544, 885, 222], _ ["Preset 003", 564, 885, 222] _ ] CallPresetScene($aPresets[0][0], $aPresets[0][1], $aPresets[0][2], $aPresets[0][3]) ; ๐Ÿ”” Preset 002 ;~ CallPresetScene($aPresets[1][0], $aPresets[1][1], $aPresets[1][2], $aPresets[1][3]) ; ๐Ÿ”” Preset 003 ; ... ; ------------------------------------------------------------------------------ Func CallPresetScene($sPresetName, $iAmpSimY, $iMPosX, $iMPosY) ConfigureAmpSimView($sPresetName, $iAmpSimY) ConfigureFMixerView() UpdateScenesView($sPresetName, $iMPosX, $iMPosY) UpdateSceneProperties($iMPosX, $iMPosY) EndFunc ;==>CallPresetScene ; ------------------------------------------------------------------------------ Func ConfigureAmpSimView($sPresetName, $iMPosY) Sleep($iTimeOut) MouseClick($MOUSE_CLICK_LEFT, 534, $iMPosY, 2, 0) EndFunc ;==>ConfigureAmpSimView ; ------------------------------------------------------------------------------ Func ConfigureFMixerView() Sleep($iTimeOut) MouseClick($MOUSE_CLICK_LEFT, 50, 120, 1, 0) ; Select: Channel Label [ZMixer] EndFunc ;==>ConfigureFMixerView ; ------------------------------------------------------------------------------ Func UpdateScenesView($sPresetName, $iMPosX, $iMPosY) Local $hSAC_SCENES = "[CLASS:SAC_SCENES]" WinActivate($hSAC_SCENES) Send("{End}") ; Select: [End Of List] Sleep($iTimeOut) MouseClick($MOUSE_CLICK_LEFT, 188, 118, 1, 0) ; Select: [New] Sleep($iTimeOut) ClipPut($sPresetName) ; Copy the variable Preset Name ; Paste text Send("{CTRLDOWN}") Send("v") Send("{CTRLUP}") Send("{ENTER}") ; Select: [Ok] EndFunc ;==>UpdateScenesView ; ------------------------------------------------------------------------------ Func UpdateSceneProperties($iMPosX, $iMPosY) Local $hSAC_SCENEPROPERTIES = "[CLASS:SAC_SCENEPROPERTIES]" Sleep(1500) Send("{ENTER}") ; Select: [OK] EndFunc ;==>UpdateSceneProperties ; ------------------------------------------------------------------------------ Edit: It reflects the idea more. Because it has some problems, which stem from your examples. Like Func UpdatePreset002SceneProperties($iX, $iY) Func UpdatePreset003SceneProperties($iX, $iY) there are parameters $iX, $iY, but you don't use them anywhere in the function Func UpdatePreset002ScenesView($iX, $iY) Func UpdatePreset003ScenesView($iX, $iY) there are parameters $iX, $iY, but you don't use them anywhere in the function
    1 point
  18. If this forum had better themes and more formatting options I would agree but unfortunately none of that is there and a user is somewhat limited. On the other hand this post was formatted by AI and he just pasted it. Maybe pasting without formatting would do what you ask but would loose much of it's nice looking presentation. P.S.: It suck to come from the future @WildByDesign and having to wait for the past to catch up
    1 point
  19. Workaround: Use Ctrl+a to select all text of the page and make it readable
    1 point
  20. Poor coding does Change what you need ๐Ÿคฏ
    1 point
  21. Do you run the "AutoIt (Dark)" theme? The dark mode caused the unreadable text.
    1 point
  22. How would you like to run: curl -d "Finished running my script. All good." ntfy.sh/Testing_AutoIt_script or ConsoleWrite(ntfy_send("**All good**, all the time ๐Ÿ˜ƒ") & @TAB & @error & @TAB & @extended & @CRLF) Func ntfy_send($sMsg, $sTopicName = "Testing_AutoIt_script") Local Static $iErr = 0, $oErr If IsObj($sMsg) Then If $sMsg.retcode Then $iErr = "0x" & Hex($sMsg.retcode, 8) Return EndIf If ObjEvent("AutoIt.Error") = "" Then $oErr = ObjEvent("AutoIt.Error", "ntfy_send") Local $sUrl = "https://ntfy.sh/" & $sTopicName Local $oHTTP = ObjCreate("winhttp.winhttprequest.5.1") $oHTTP.Open("POST", $sUrl, False) ; Open the connection using POST method (synchronous = False) $oHTTP.SetRequestHeader("Markdown", "yes") ; Set Markdown ON $oHTTP.SetRequestHeader("Tags", "heavy_check_mark,PC:" & "@ComputerName") ; https://docs.ntfy.sh/publish/#tags-emojis $oHTTP.Send($sMsg) ; Send the request If ObjEvent("AutoIt.Error") = "ntfy_send" Then $oErr = ObjEvent("AutoIt.Error", "") If $iErr Then Return SetError(2, $iErr, "oHTTP.Send FAILED") Return SetError(Int($oHTTP.Status <> 200), $oHTTP.Status, ($oHTTP.Status = 200 ? StringReplace($oHTTP.ResponseText, @LF, "") : $oHTTP.StatusText)) EndFunc ;==>ntfy_send and be notified in your phone, browser or ...basically any possible way ?!, meet ntfy.sh ๐Ÿคฉ Ok. How would you like to have your own AutoIt receiver for these notifications ๐Ÿคฏ For that you'll need the curl DLL, the curl UDF and something like this: #Region ;**** Directives created by AutoIt3Wrapper_GUI **** #AutoIt3Wrapper_UseX64=y #EndRegion ;**** Directives created by AutoIt3Wrapper_GUI **** Opt("TrayAutoPause", 0) ; Script pauses when click on tray icon = OFF/0 Opt("TrayOnEventMode", 0) ; Enable/disable OnEvent functions notifications for the tray = OFF/0 Opt("GUICloseOnESC", 0) ; When ESC is pressed on a GUI the $GUI_EVENT_CLOSE message is sent = ON/1 If Not FileGetSize(@ScriptDir & '\curl-ca-bundle.crt') Then MsgBox(262144 + 64, @ScriptName, "The curl stuff needs to be in the same folder for this example", 30) Exit EndIf If Not @AutoItX64 Then MsgBox(262144 + 64, @ScriptName, "It needs to run x64", 30) Exit EndIf #include "Curl.au3" ; https://www.autoitscript.com/forum/topic/207859-curl-udf-libcurl-with-x64-support #include <GuiEdit.au3> ;_GUICtrlEdit_AppendText() ; GUI stuff #include <ButtonConstants.au3> #include <EditConstants.au3> #include <GUIConstantsEx.au3> #include <StaticConstants.au3> #include <WindowsConstants.au3> #Region ### START Koda GUI section ### Form= Global $Form1 = GUICreate("Form1", 565, 425) Global $Group1 = GUICtrlCreateGroup("MyTopic", 8, 8, 305, 49) Global $Input1 = GUICtrlCreateInput("Testing_AutoIt_script", 16, 24, 281, 21) GUICtrlCreateGroup("", -99, -99, 1, 1) Global $Button1 = GUICtrlCreateButton("Gather all in cache", 320, 16, 131, 25) Global $Button2 = GUICtrlCreateButton("Listen ( start )", 464, 16, 91, 25) Global $Group2 = GUICtrlCreateGroup("Dump", 8, 96, 545, 321) Global $Edit1 = GUICtrlCreateEdit("", 16, 120, 529, 289) GUICtrlCreateGroup("", -99, -99, 1, 1) Global $Label1 = GUICtrlCreateLabel("last ""keepalive""", 8, 64, 548, 33, $SS_CENTER) GUISetState(@SW_SHOW) #EndRegion ### END Koda GUI section ### Global $g_nfty_CurlPeeked, $g_nfty_ListenStop = 1 Global $__g_nfty_RunningHandles, $__g_nfty_Curl = 0, $__g_nfty_Multi = 0 OnAutoItExitRegister(nfty_Listen_Cleanup) While 1 Switch GUIGetMsg() Case $GUI_EVENT_CLOSE If $g_nfty_ListenStop = 1 Then GUIDelete() Exit EndIf GUICtrlSetState($Button2, $GUI_DISABLE) GUICtrlSetData($Button2, "Listen ( stoping )") $g_nfty_ListenStop = 2 Case $Button1 $g_nfty_ListenStop = 0 nfty_Listen_Start(GUICtrlRead($Input1), "?poll=1&since=all") nfty_Listen_Perform() Case $Button2 If $g_nfty_ListenStop Then GUICtrlSetState($Button1, $GUI_DISABLE) GUICtrlSetState($Button2, $GUI_DISABLE) $g_nfty_ListenStop = 0 GUICtrlSetData($Button2, "Listen ( starting )") nfty_Listen_Start(GUICtrlRead($Input1)) If @error Then $g_nfty_ListenStop = 1 GUICtrlSetData($Button2, "Listen ( start )") GUICtrlSetState($Button1, $GUI_ENABLE) GUICtrlSetState($Button2, $GUI_ENABLE) Else GUICtrlSetData($Button2, "Listen ( stop )") GUICtrlSetState($Button2, $GUI_ENABLE) EndIf Else GUICtrlSetState($Button2, $GUI_DISABLE) GUICtrlSetData($Button2, "Listen ( stoping )") $g_nfty_ListenStop = 2 EndIf EndSwitch Switch $g_nfty_ListenStop Case 1 ; was never running ContinueLoop Case 0 ; not stopped - is running nfty_Listen_Perform() Case 2 ; request to stop nfty_Listen_Cleanup() $g_nfty_ListenStop = 1 GUICtrlSetData($Button2, "Listen ( start )") GUICtrlSetState($Button1, $GUI_ENABLE) GUICtrlSetState($Button2, $GUI_ENABLE) EndSwitch WEnd Func nfty_Listen_Start($sTopic, $suffix = "") $__g_nfty_Curl = Curl_Easy_Init() If Not $__g_nfty_Curl Then $g_nfty_ListenStop = 0 Return SetError(1, 0, 1) EndIf Curl_Easy_Setopt($__g_nfty_Curl, $CURLOPT_URL, "https://ntfy.sh/" & $sTopic & "/json" & $suffix) ;~ Curl_Easy_Setopt($Curl, $CURLOPT_USERAGENT, "AutoIt/Curl") Curl_Easy_Setopt($__g_nfty_Curl, $CURLOPT_FOLLOWLOCATION, 1) Curl_Easy_Setopt($__g_nfty_Curl, $CURLOPT_ACCEPT_ENCODING, "") Curl_Easy_Setopt($__g_nfty_Curl, $CURLOPT_WRITEFUNCTION, Curl_DataWriteCallback_nfty()) Curl_Easy_Setopt($__g_nfty_Curl, $CURLOPT_WRITEDATA, $__g_nfty_Curl) Curl_Easy_Setopt($__g_nfty_Curl, $CURLOPT_TCP_KEEPALIVE, 1) If $suffix Then Curl_Easy_Setopt($__g_nfty_Curl, $CURLOPT_TIMEOUT, 10) ; 10 sec timeout ;peer verification curl_easy_setopt($__g_nfty_Curl, $CURLOPT_CAINFO, @ScriptDir & '\curl-ca-bundle.crt') ; ;~ Curl_Easy_Setopt($__g_nfty_Curl, $CURLOPT_SSL_VERIFYPEER, 0) $__g_nfty_Multi = Curl_Multi_Init() If Not $__g_nfty_Multi Then $g_nfty_ListenStop = 0 nfty_Listen_Cleanup() Return SetError(2, 0, 2) EndIf Curl_Multi_Add_Handle($__g_nfty_Multi, $__g_nfty_Curl) EndFunc ;==>nfty_Listen_Start Func nfty_Listen_Perform() Local Static $MsgsInQueue, $hTimer = 0 If TimerDiff($hTimer) < 100 Then Return ; no need to ask so often $hTimer = TimerInit() ; let's restart the timer Curl_Multi_Perform($__g_nfty_Multi, $__g_nfty_RunningHandles) Local $CURLMsg = Curl_Multi_Info_Read($__g_nfty_Multi, $MsgsInQueue) If DllStructGetData($CURLMsg, "msg") = $CURLMSG_DONE Then Local $__g_nfty_Curl = DllStructGetData($CURLMsg, "easy_handle") Local $Code = DllStructGetData($CURLMsg, "data") If $Code = $CURLE_OK Then ;~ ConsoleWrite('@@(' & @ScriptLineNumber & ') : ' & @MIN & ':' & @SEC & '.' & @MSEC & @TAB & "Content Type: " & Curl_Easy_GetInfo($__g_nfty_Curl, $CURLINFO_CONTENT_TYPE) & @LF) ;~ ConsoleWrite('@@(' & @ScriptLineNumber & ') : ' & @MIN & ':' & @SEC & '.' & @MSEC & @TAB & "Download Size: " & Curl_Easy_GetInfo($__g_nfty_Curl, $CURLINFO_SIZE_DOWNLOAD) & @LF) ;~ ConsoleWrite('@@(' & @ScriptLineNumber & ') : ' & @MIN & ':' & @SEC & '.' & @MSEC & @TAB & '- Header >' & BinaryToString(Curl_Data_Get($__g_nfty_Curl + 1)) & '<' & @CRLF) ;~ ConsoleWrite('@@(' & @ScriptLineNumber & ') : ' & @MIN & ':' & @SEC & '.' & @MSEC & @TAB & '- Html >' & BinaryToString(Curl_Data_Get($__g_nfty_Curl)) & '<' & @CRLF) Else ConsoleWrite('@@(' & @ScriptLineNumber & ') : ' & @MIN & ':' & @SEC & '.' & @MSEC & @TAB & Curl_Easy_StrError($Code) & @LF) EndIf nfty_Listen_Cleanup() $g_nfty_ListenStop = 1 EndIf EndFunc ;==>nfty_Listen_Perform Func nfty_Listen_Cleanup() If $__g_nfty_Multi Then Curl_Multi_Remove_Handle($__g_nfty_Multi, $__g_nfty_Curl) Curl_Multi_Cleanup($__g_nfty_Multi) $__g_nfty_Multi = 0 EndIf Curl_Easy_Cleanup($__g_nfty_Curl) Curl_Data_Cleanup($__g_nfty_Curl) Curl_Data_Cleanup($__g_nfty_Curl + 1) $__g_nfty_Curl = 0 EndFunc ;==>nfty_Listen_Cleanup Func Curl_DataWriteCallback_nfty() Static $Ptr = DllCallbackGetPtr(DllCallbackRegister(__Curl_DataWriteCallback_nfty, (@AutoItX64 ? "uint_ptr" : "uint_ptr:cdecl"), "ptr;uint_ptr;uint_ptr;ptr")) Return $Ptr EndFunc ;==>Curl_DataWriteCallback_nfty Func __Curl_DataWriteCallback_nfty($Ptr, $Size, $Nmemb, $Handle) Local $Length = $Size * $Nmemb, $Data = __Curl_Peek("byte[" & $Length & "]", $Ptr) $g_nfty_CurlPeeked = StringReplace(BinaryToString($Data), @LF, @CRLF) If StringInStr($g_nfty_CurlPeeked, ',"event":"open","topic":"') Or StringInStr($g_nfty_CurlPeeked, ',"event":"keepalive","topic":"') Then ; not important GUICtrlSetData($Label1, @MIN & ":" & @SEC & " >" & StringStripCR($g_nfty_CurlPeeked) & "<") Else _GUICtrlEdit_AppendText($Edit1, $g_nfty_CurlPeeked & @CRLF) EndIf Return $Length EndFunc ;==>__Curl_DataWriteCallback_nfty Do place your scripts in the bin folder where libcurl-x64.dll is at, or this example will not work as is. This is just an example. FAQ: Q: Why the curl UDF ?, why not ... A: Because "the page" never finishes the download ( and is not meant to finish ). Couldn't find a way to peek into the message other than this. Q: Can you ... A: Maybe. But am busy, and not all that good at all these. If you code that you wish it had, do share it in the forum. ( Think GPLv2 ) Q: I sent a message but my receiver script wasn't running at the time / Lost internet for X hours. A: Text messages are likely to be available for up to 12 hours ( for what I read ). Just click "Gather all in cache" in this example. Q: How can I ... A: ntfy has excellent documentation. Read it. Q: Can I make my messages private ? A: Yes you can. Read the offers they have available for the service.
    1 point
  23. 1 point
  24. After seeing a number of threads talking about how to exchange efficiently messages between processes (Inter Process Communication), I decided to create a framework using Windows Messages WM_COPYDATA. What is new with this UDF you ask ? Well it will depends how familiar you are with IPC. One thing is sure, the simplicity of use and the fabulous speed are amazing. This is based on a Clients-Server approach. You can have an unlimited number of clients talking with a single server. You will have to define the protocol of communication between them, but the code you have to create is incredibly low. The UDF proposes 2 simple message properties of communication. The first (called data) is based on a number. You can decide what value 1,2,3, etc. means between your client and server. Server will react upon the value of the data field. Second, there is a string field where you can inscribe additional information on request, and where the server will respond to client request (if necessary). Version 2025-11-17 * Added support to x64 server and/or x64 clients * Added support to AutoIt version 3.3.18.0 Version 2020-06-27 * Allows processes with different levels of privilege to communicate with each other Here are the functions that I have wrapped around this : Func _WCD_CreateServer Func _WCD_CreateClient Func _WCD_GetServerHandle Func _WCD_IsServerAvailable Func _WCD_Send Func _WCD_WM_COPYDATA_CLIENT_HANDLER Func _WCD_Client_GetResponse Func _WCD_WM_COPYDATA_SERVER_HANDLER Func _WCD_Server_PeekRequest Func _WCD_Server_GetRequest Func _WCD_Server_IsRequestAvail Here an example of the server : #include <Constants.au3> #include <GUIConstants.au3> #include "WCD_IPC.au3" Opt ("MustDeclareVars", 1) $_WCD_Verbose = False ; make it True if you want to follow the convos. False is by default. Local $hServer = _WCD_CreateServer () Local $aReq, $iData While True If _WCD_Server_IsRequestAvail () Then $aReq = _WCD_Server_GetRequest () $iData = @extended Switch $iData Case 1 ; who are you _WCD_Send($hServer, $aReq[0], $iData, @ComputerName) Case 2 Switch Number($aReq[1]) Case 1 _WCD_Send($hServer, $aReq[0], $iData, @IPAddress1) Case 2 _WCD_Send($hServer, $aReq[0], $iData, @IPAddress2) Case 3 _WCD_Send($hServer, $aReq[0], $iData, @IPAddress3) Case 4 _WCD_Send($hServer, $aReq[0], $iData, @IPAddress4) Case Else _WCD_Send($hServer, $aReq[0], $iData, "Invalid parameter") EndSwitch EndSwitch EndIf Sleep (100) WEnd And the client : #include <Constants.au3> #include <GUIConstants.au3> #include "WCD_IPC.au3" Opt ("MustDeclareVars", 1) $_WCD_Verbose = True ; as for the server, you can decide to make client verbose or not Global $hWnd = _WCD_CreateClient ("Test WCD Client") Global $hWndServer = _WCD_GetServerHandle () _WCD_Send($hWnd, $hWndServer, 1) ; simple request - who are you ? Local $sString = WaitForResponse () ConsoleWrite ($sString & @CRLF) _WCD_Send($hWnd, $hWndServer, 2, "5") ; adding text to a more complex request $sString = WaitForResponse () ConsoleWrite ($sString & @CRLF) Func WaitForResponse () Local $sResp While _WCD_IsServerAvailable () $sResp = _WCD_Client_GetResponse () If $sResp <> "" Then Return $sResp Sleep (100) WEnd EndFunc As always, let me know if you got issues, comments, suggestions. I will be glad to answer. WCD_IPC.zip
    1 point
  25. As usually I love your answer my friend. As always, I really liked your answer, my friend. All is clear for me. Thanks. So. @Parsix In your opinion, does this example fully meet your needs for using Au3Stripper with the @trancexx script , I mean all the possibilities of the /SO /PE /RM parameters?
    1 point
  26. Ahhh. Thank you very much. I was able to replicate your issue. The problem is the structure alignment in 64 bits. I'll do some tests and make an update in a few...
    1 point
  27. Now it is. Thanks. So here is my solution for this script: ;~ https://www.autoitscript.com/forum/topic/154081-avoid-autoit-error-message-box-in-unknown-errors/page/4/#findComment-1547476 #Region - AutoIt3Wrapper directives section ; General section #AutoIt3Wrapper_UseX64=n #AutoIt3Wrapper_UseUpx=n #AutoIt3Wrapper_Compression=4 ; Au3Check section #AutoIt3Wrapper_Au3Check_Parameters=-d -w 1 -w 2 -w 6 -w 7 ; Au3Stripper section #AutoIt3Wrapper_Run_Au3Stripper=y ;~ #Au3Stripper_Parameters=/SO /PE #Au3Stripper_Parameters=/SO /PE /RM #AutoIt3Wrapper_Au3Stripper_OnError=f ;~ #Au3Stripper_Ignore_Funcs=Intercept_MessageBoxW ;~ #Au3Stripper_Ignore_Funcs=__AddHookApi_DllCallbackRegister_wrapper #EndRegion - AutoIt3Wrapper directives section #include <WinApi.au3> #Region - exmaple ;~ AddHookApi("user32.dll", "MessageBoxW", "Intercept_MessageBoxW", "int", "hwnd;wstr;wstr;uint") AddHookApi("user32.dll", "MessageBoxW", FuncName(Intercept_MessageBoxW), "int", "hwnd;wstr;wstr;uint") MsgBox(0, 'Test', 'Some normal MsgBox text') DllStructCreate("byte[123456789097]") ; This is a deliberate action intended to display an error, as this script demonstrates how to change error handling - interact with MsgBox's title and text. #EndRegion - exmaple #Region @trancexx - https://www.autoitscript.com/forum/topic/154081-avoid-autoit-error-message-box-in-unknown-errors/#findComment-1111917 Func Intercept_MessageBoxW($hWnd, $sText, $sTitle, $iType) If $sTitle = 'AutoIt' Then $sTitle = 'TESTING: ' & StringReplace($sTitle, "AutoIt", @ScriptName) Local $aCall = DllCall("user32.dll", "int", "MessageBoxW", _ "hwnd", $hWnd, _ "wstr", $sText, _ "wstr", $sTitle, _ "uint", $iType) If @error Or Not $aCall[0] Then Return 0 Return $aCall[0] EndFunc ;==>Intercept_MessageBoxW ; The magic is down below Func AddHookApi($sModuleName, $vFunctionName, $vNewFunction, $sRet = "", $sParams = "") Local Static $pImportDirectory, $hInstance Local Const $IMAGE_DIRECTORY_ENTRY_IMPORT = 1 If Not $pImportDirectory Then $hInstance = _WinAPI_GetModuleHandle(0) $pImportDirectory = ImageDirectoryEntryToData($hInstance, $IMAGE_DIRECTORY_ENTRY_IMPORT) If @error Then Return SetError(1, 0, 0) EndIf Local $iIsInt = IsInt($vFunctionName) Local $iRestore = Not IsString($vNewFunction) Local $tIMAGE_IMPORT_MODULE_DIRECTORY Local $pDirectoryOffset = $pImportDirectory Local $tModuleName Local $iInitialOffset, $iInitialOffset2 Local $iOffset2 Local $tBufferOffset2, $iBufferOffset2 Local $tBuffer, $tFunctionOffset, $pOld, $fMatch, $pModuleName, $pFuncName Local Const $PAGE_READWRITE = 0x04 While 1 $tIMAGE_IMPORT_MODULE_DIRECTORY = DllStructCreate("dword RVAOriginalFirstThunk;" & _ "dword TimeDateStamp;" & _ "dword ForwarderChain;" & _ "dword RVAModuleName;" & _ "dword RVAFirstThunk", _ $pDirectoryOffset) If Not DllStructGetData($tIMAGE_IMPORT_MODULE_DIRECTORY, "RVAFirstThunk") Then ExitLoop $pModuleName = $hInstance + DllStructGetData($tIMAGE_IMPORT_MODULE_DIRECTORY, "RVAModuleName") $tModuleName = DllStructCreate("char Name[" & _WinAPI_StringLenA($pModuleName) & "]", $pModuleName) If DllStructGetData($tModuleName, "Name") = $sModuleName Then ; function from this module $iInitialOffset = $hInstance + DllStructGetData($tIMAGE_IMPORT_MODULE_DIRECTORY, "RVAFirstThunk") $iInitialOffset2 = $hInstance + DllStructGetData($tIMAGE_IMPORT_MODULE_DIRECTORY, "RVAOriginalFirstThunk") If $iInitialOffset2 = $hInstance Then $iInitialOffset2 = $iInitialOffset $iOffset2 = 0 While 1 $tBufferOffset2 = DllStructCreate("dword_ptr", $iInitialOffset2 + $iOffset2) $iBufferOffset2 = DllStructGetData($tBufferOffset2, 1) If Not $iBufferOffset2 Then ExitLoop If $iIsInt Then If BitAND($iBufferOffset2, 0xFFFFFF) = $vFunctionName Then $fMatch = True ; wanted function Else $pFuncName = $hInstance + $iBufferOffset2 + 2 ; 2 is size od "word", see line below... $tBuffer = DllStructCreate("word Ordinal; char Name[" & _WinAPI_StringLenA($pFuncName) & "]", $hInstance + $iBufferOffset2) If DllStructGetData($tBuffer, "Name") == $vFunctionName Then $fMatch = True ; wanted function EndIf If $fMatch Then $tFunctionOffset = DllStructCreate("ptr", $iInitialOffset + $iOffset2) VirtualProtect(DllStructGetPtr($tFunctionOffset), DllStructGetSize($tFunctionOffset), $PAGE_READWRITE) If @error Then Return SetError(3, 0, 0) $pOld = DllStructGetData($tFunctionOffset, 1) If $iRestore Then DllStructSetData($tFunctionOffset, 1, $vNewFunction) Else #Region ; the #Au3Stripper_Off/#Au3Stripper_On directives, used in this place will lead to errors as /RM is used and all variables was changed in entire script but not within this region ;~ #Au3Stripper_Off ;~ DllStructSetData($tFunctionOffset, 1, DllCallbackGetPtr(DllCallbackRegister($vNewFunction, $sRet, $sParams))) ;~ #Au3Stripper_On #EndRegion ; the #Au3Stripper_Off/#Au3Stripper_On directives, used in this place will lead to errors as /RM is used and all variables was changed in entire script but not within this region ; for this reason __AddHookApi_DllCallbackRegister_wrapper() was added and enclosed within #Au3Stripper_Off >>> #Au3Stripper_On section __AddHookApi_DllCallbackRegister_wrapper($tFunctionOffset, $vNewFunction, $sRet, $sParams) EndIf Return $pOld EndIf $iOffset2 += DllStructGetSize($tBufferOffset2) WEnd ExitLoop EndIf $pDirectoryOffset += 20 ; size of $tIMAGE_IMPORT_MODULE_DIRECTORY WEnd Return SetError(4, 0, 0) EndFunc ;==>AddHookApi #Au3Stripper_Off Func __AddHookApi_DllCallbackRegister_wrapper($tFunctionOffset__Wrapped, $vNewFunction__Wrapped, $sRet__Wrapped, $sParams__Wrapped) DllStructSetData($tFunctionOffset__Wrapped, 1, DllCallbackGetPtr(DllCallbackRegister($vNewFunction__Wrapped, $sRet__Wrapped, $sParams__Wrapped))) EndFunc ;==>__AddHookApi_DllCallbackRegister_wrapper #Au3Stripper_On Func VirtualProtect($pAddress, $iSize, $iProtection) Local $aCall = DllCall("kernel32.dll", "bool", "VirtualProtect", "ptr", $pAddress, "dword_ptr", $iSize, "dword", $iProtection, "dword*", 0) If @error Or Not $aCall[0] Then Return SetError(1, 0, 0) Return 1 EndFunc ;==>VirtualProtect Func ImageDirectoryEntryToData($hInstance, $iDirectoryEntry) ; Get pointer to data Local $pPointer = $hInstance ; Start processing passed binary data. 'Reading' PE format follows. Local $tIMAGE_DOS_HEADER = DllStructCreate("char Magic[2];" & _ "word BytesOnLastPage;" & _ "word Pages;" & _ "word Relocations;" & _ "word SizeofHeader;" & _ "word MinimumExtra;" & _ "word MaximumExtra;" & _ "word SS;" & _ "word SP;" & _ "word Checksum;" & _ "word IP;" & _ "word CS;" & _ "word Relocation;" & _ "word Overlay;" & _ "char Reserved[8];" & _ "word OEMIdentifier;" & _ "word OEMInformation;" & _ "char Reserved2[20];" & _ "dword AddressOfNewExeHeader", _ $pPointer) Local $sMagic = DllStructGetData($tIMAGE_DOS_HEADER, "Magic") ; Check if it's valid format If Not ($sMagic == "MZ") Then Return SetError(1, 0, 0) ; MS-DOS header missing. Btw 'MZ' are the initials of Mark Zbikowski in case you didn't know. ; Move pointer $pPointer += DllStructGetData($tIMAGE_DOS_HEADER, "AddressOfNewExeHeader") ; move to PE file header ; In place of IMAGE_NT_SIGNATURE structure Local $tIMAGE_NT_SIGNATURE = DllStructCreate("dword Signature", $pPointer) ; Check signature If DllStructGetData($tIMAGE_NT_SIGNATURE, "Signature") <> 17744 Then ; IMAGE_NT_SIGNATURE Return SetError(2, 0, 0) ; wrong signature. For PE image should be "PE\0\0" or 17744 dword. EndIf ; Move pointer $pPointer += 4 ; size of $tIMAGE_NT_SIGNATURE structure ; In place of IMAGE_FILE_HEADER structure ; Move pointer $pPointer += 20 ; size of $tIMAGE_FILE_HEADER structure ; Determine the type Local $tMagic = DllStructCreate("word Magic;", $pPointer) Local $iMagic = DllStructGetData($tMagic, 1) Local $tIMAGE_OPTIONAL_HEADER If $iMagic = 267 Then ; x86 version ; Move pointer $pPointer += 96 ; size of $tIMAGE_OPTIONAL_HEADER ElseIf $iMagic = 523 Then ; x64 version ; Move pointer $pPointer += 112 ; size of $tIMAGE_OPTIONAL_HEADER Else Return SetError(3, 0, 0) ; unsupported module type EndIf ; Validate input by checking available number of structures that are in the module Local Const $IMAGE_NUMBEROF_DIRECTORY_ENTRIES = 16 ; predefined value that PE modules always use (AutoIt certainly) If $iDirectoryEntry > $IMAGE_NUMBEROF_DIRECTORY_ENTRIES - 1 Then Return SetError(4, 0, 0) ; invalid input ; Calculate the offset to wanted entry (every entry is 8 bytes) $pPointer += 8 * $iDirectoryEntry ; At place of correst directory entry Local $tIMAGE_DIRECTORY_ENTRY = DllStructCreate("dword VirtualAddress; dword Size", $pPointer) ; Collect data Local $pAddress = DllStructGetData($tIMAGE_DIRECTORY_ENTRY, "VirtualAddress") If $pAddress = 0 Then Return SetError(5, 0, 0) ; invalid input ; $pAddress is RVA, add it to base address Return $hInstance + $pAddress EndFunc ;==>ImageDirectoryEntryToData #EndRegion @trancexx - https://www.autoitscript.com/forum/topic/154081-avoid-autoit-error-message-box-in-unknown-errors/#findComment-1111917 Explanations: Using @trancexx code, in order to use: #AutoIt3Wrapper_Run_Au3Stripper=y #Au3Stripper_Parameters=/so /pe #AutoIt3Wrapper_Au3Stripper_OnError=f there is also a need to use: #Au3Stripper_Ignore_Funcs=Intercept_MessageBoxW Because in other way: #Au3Stripper_Parameters=/so /pe Will strip down the function as she is not called directly. Only the function name is used but as a string and not directly like a "pointer" To prevent using: #Au3Stripper_Ignore_Funcs=Intercept_MessageBoxW The Intercept_MessageBoxW can be called as a parameter for FuncName(Intercept_MessageBoxW) this way: ;~ AddHookApi("user32.dll", "MessageBoxW", "Intercept_MessageBoxW", "int", "hwnd;wstr;wstr;uint") AddHookApi("user32.dll", "MessageBoxW", FuncName(Intercept_MessageBoxW), "int", "hwnd;wstr;wstr;uint") In such case Au3Stripper knows that Intercept_MessageBoxW was used and should not be stripped. REMARK: You can also notice that I used: #Au3Stripper_Parameters=/SO /PE /RM I mean the the most demanding/restrictive option /RM For this reason this following mod was added: ..... #Region ; the #Au3Stripper_Off/#Au3Stripper_On directives, used in this place will lead to errors as /RM is used and all variables was changed in entire script but not within this region ;~ #Au3Stripper_Off ;~ DllStructSetData($tFunctionOffset, 1, DllCallbackGetPtr(DllCallbackRegister($vNewFunction, $sRet, $sParams))) ;~ #Au3Stripper_On #EndRegion ; the #Au3Stripper_Off/#Au3Stripper_On directives, used in this place will lead to errors as /RM is used and all variables was changed in entire script but not within this region ; for this reason __AddHookApi_DllCallbackRegister_wrapper() was added and enclosed within #Au3Stripper_Off >>> #Au3Stripper_On section __AddHookApi_DllCallbackRegister_wrapper($tFunctionOffset, $vNewFunction, $sRet, $sParams) ..... #Au3Stripper_Off Func __AddHookApi_DllCallbackRegister_wrapper($tFunctionOffset__Wrapped, $vNewFunction__Wrapped, $sRet__Wrapped, $sParams__Wrapped) DllStructSetData($tFunctionOffset__Wrapped, 1, DllCallbackGetPtr(DllCallbackRegister($vNewFunction__Wrapped, $sRet__Wrapped, $sParams__Wrapped))) EndFunc ;==>__AddHookApi_DllCallbackRegister_wrapper #Au3Stripper_On ..... The reason that I do not must to use: ;~ #Au3Stripper_Ignore_Funcs=__AddHookApi_DllCallbackRegister_wrapper is because __AddHookApi_DllCallbackRegister_wrapper() is used/called before the #Au3Stripper_Off / #Au3Stripper_Off sections occurs so Au3Stripper already dit the /RM action on the function name in entire script but at this moment do not touched $******__Wrapped variables. @Jos Does this example cover the whole topic of using Au3Stripper with this @trancexx script, I mean all releated with the /SO /PE /RM parameters? btw. I wonder whether, for the correctness of "code reading" and protection against possible changes in Au3Stripper, I should still use: #Au3Stripper_Ignore_Funcs=__AddHookApi_DllCallbackRegister_wrapper
    1 point
  28. I took me a few hours unfortunately, but I figured it out. The UDF does not support AutoIt 64-bit for some reason. The server was never receiving the strings. I was able to confirm that. None of the ConsoleWrites were working on server or client script at all. I switched to 32-bit AutoIt, strings are going as was intended and ConsoleWrites and all. So I guess that leaves the question. Is it possible to support 64-bit AutoIt? Thank you for your time with this, by the way. I thought I was completely losing my mind for a bit there.
    1 point
  29. no worries at all! what I think is happening is: $NC_CLICKED is control Id of the dummy, which fires on WM_NCLBUTTONDOWN. The dummy's data is set to the hwnd param of the WM_ message. Fair enough... But then we handle events based on $event.Form - which is the dummy's parent. I guess Form1 is the last window built with GUICreate() before we setup the dummy, so that ends up owning the control. To find the hWnd of the captured WM_NCLBUTTONDOWN message, we need to: GuiCtrlRead($NC_CLICKED).
    1 point
  30. Jos

    A Non-Strict JSON UDF (JSMN)

    Something like this ? #include "Json.au3" ConsoleWrite("- Test8() : " & Test8() & @CRLF) Func Test8() ; Your three JSON strings Local $Json1 = '{"name":"John","age":30,"locations":[]}' Local $Json2 = '{"City":"Paris","Country":"France"}' Local $Json3 = '{"City":"London","Country":"England"}' ; Decode Local $obj1 = Json_Decode($Json1) Json_ObjPut($obj1,"locations", Json_Decode("[" & $Json2 & "," & $Json3 & "]")) Local $final = Json_Encode($obj1, $JSON_PRETTY_PRINT) ConsoleWrite($final & @CRLF) EndFunc ;==>Test8
    1 point
  31. Nine

    Delayed MouseClick()

    1- you can put sleep anywhere / everywhere. It doesn't hurt except can slow down the script. You need to test and decide. 2- having a single delay ($iTimeOut) is a very bad idea. Sometimes, it requires more time, sometimes it requires less. You need to test and decide. 3- it is not because you paste something that it will be pasted instantly in the field. It may take some time. You need to test and decide.
    1 point
  32. Thank you. Yes last AutoIt version messed up with the #include. Many of my scripts are breaking because of it. I'll update this one tomorrow. Anyway, the string is located in $aReq[1], as described in example.
    1 point
  33. Thank you! Check out the latest update. I didn't do much with your code tonight, but I did use your code from today to fix the window closing issues. I also removed the garish colors from the tab items (I put it in there for debugging (took me about 16 hours to get that ironed out.)) I also came up with a hack for a weird issue. So, when a title bar is clicked a message is sent to a dummy control. Inside of the dummy control function (GUIObjectEvents) the $hwnd is correct for each form. Click form1 title bar and you get the form1 hwnd. Click on form2 title bar and you get form2 hwnd. However, inside of the GUIObjectsHandler only form1 hwnd is there regardless of which form I click. I dunno. I had a long day so I'm callling it for tonight. Thank you again MattyD ... Your code saved me from hours of banging my forehead on the desk. I could not have come up with the code that you did.
    1 point
  34. Trong

    AutoIt Resource Embedder

    AutoIt Resource Embedder A professional tool to convert binary files into self-contained AutoIt functions with advanced encoding and compression support. Author: Dao Van Trong - TRONG.PRO ๐ŸŒŸ Features Core Functionality Binary File Embedding - Convert any binary file (DLL, EXE, images, etc.) into AutoIt code Multiple Encoding Formats Hex String Encoding Base64 String Encoding (with Unicode support) LZNT Compression Level 1: Standard 4096-byte chunks Level 2: No chunking (maximum compression) Architecture Detection - Automatically detects PE file architecture (x86, x64, ARM, ARM64, IA64) Dual Operation Modes GUI Mode - User-friendly graphical interface CLI Mode - Command-line for automation/scripting Advanced Features Smart Helper Functions _DeployFile() for single file - Returns binary, hex string, or writes to file _GetBin($filename) for multiple files - Switch/Case based retrieval Automatic Decompression/Decoding - Generated code includes all necessary helper functions Error Handling - Comprehensive error checking and reporting Chunk Size Control - Configurable line length (100-4000 characters) Batch Processing - Process multiple files at once ๐Ÿš€ Quick Start GUI Mode Run the script: Double-click "AutoIt Resource Embedder.au3" Add files: Click "Add Files..." button Select one or more binary files Files appear in the list with size and architecture info Configure encoding: Hex - Standard hex string encoding Base64 - Base64 string encoding Hex + LZNT - Hex encoding with compression Base64 + LZNT - Base64 encoding with compression Select LZNT Level (1 or 2) if using compression Generate code: Click "Generate All Functions" or "Preview Single" Code appears in the output window Save output: "Save All to File" - Single .au3 file with all functions "Save Separate Files" - Individual .au3 file per input file "Copy to Clipboard" - Copy generated code CLI Mode Process files from command line: AutoIt3.exe "AutoIt Resource Embedder.au3" file1.dll file2.exe Output: All_Embedded.au3 (or individual file if only one input) ๐Ÿ“– Usage Examples Example 1: Single File with Helper Function Input: myLib.dll Generated Code: ; Function containing encoded data Func _GetBinData_myLib_dll_x86() Local $sHexData = '0x4D5A90000300000004000000FFFF...' Return $sHexData EndFunc ; Helper function to deploy the file Func _DeployFile($sDestPath = "", $bReturnHex = False) Local $sHexData = _GetBinData_myLib_dll_x86() If $sHexData = "" Then Return SetError(1, 0, "") Local $bBinary = Binary($sHexData) ; If no destination path, return binary or hex string If $sDestPath = "" Then If $bReturnHex Then Return StringTrimLeft($bBinary, 2) Else Return $bBinary EndIf EndIf ; Write binary data to file Local $hFile = FileOpen($sDestPath, 18) If $hFile = -1 Then Return SetError(4, 0, "") FileWrite($hFile, $bBinary) FileClose($hFile) If Not FileExists($sDestPath) Then Return SetError(5, 0, "") Return $sDestPath EndFunc Usage: ; Get binary data $bData = _DeployFile() ; Get hex string $sHex = _DeployFile("", True) ; Write to file $sPath = _DeployFile(@TempDir & "\myLib.dll") Example 2: Multiple Files with _GetBin() Input: Multiple DLL files Generated Code: Func _GetBin($sName) Local $sData = "" Switch $sName Case "kernel32.dll" $sData = _GetBinData_kernel32_dll_x86() Case "user32.dll" $sData = _GetBinData_user32_dll_x86() Case "advapi32.dll" $sData = _GetBinData_advapi32_dll_x86() EndSwitch If $sData = "" Then Return SetError(1, 0, Binary("")) Local $bData = Binary($sData) Return $bData EndFunc Usage: ; Get any embedded file by name $bKernel32 = _GetBin("kernel32.dll") $bUser32 = _GetBin("user32.dll") $bAdvapi32 = _GetBin("advapi32.dll") Example 3: With Compression Enable LZNT Compression: Select "Hex + LZNT" or "Base64 + LZNT" Choose compression level (1 or 2) Generated code includes decompression function: Func _WinAPI_LZNTDecompress($bCompressed) Local $tInput = DllStructCreate("byte[" & BinaryLen($bCompressed) & "]") DllStructSetData($tInput, 1, $bCompressed) Local $tOutput = DllStructCreate("byte[" & (BinaryLen($bCompressed) * 10) & "]") Local $aRet = DllCall("ntdll.dll", "uint", "RtlDecompressBuffer", "ushort", 0x0002, "struct*", $tOutput, "ulong", DllStructGetSize($tOutput), "struct*", $tInput, "ulong", BinaryLen($bCompressed), "ulong*", 0) If @error Or $aRet[0] <> 0 Then Return SetError(1, 0, "") Return BinaryMid(DllStructGetData($tOutput, 1), 1, $aRet[6]) EndFunc โš™๏ธ Configuration Options Encoding Formats Option Description Use Case Hex Standard hexadecimal encoding General purpose, human-readable Base64 Base64 string encoding Smaller output, better for text Hex + LZNT Hex with compression Large files, need compression Base64 + LZNT Base64 with compression Maximum size reduction Compression Levels Level ChunkSize Description Level 1 4096 bytes Standard LZNT compression Level 2 0 (no chunking) Maximum compression ratio Line Length Range: 100 - 4000 characters Default: 4000 characters Purpose: Controls how long each line of encoded data is in the generated code ๐ŸŽฏ Use Cases DLL Embedding - Embed runtime libraries directly in your AutoIt scripts Resource Packaging - Package images, icons, or data files Portable Applications - Create single-file executables with all dependencies Obfuscation - Hide sensitive binary data within scripts Version Control - Include small binaries in source control as text Driver Deployment - Embed device drivers for automated installation Plugin Systems - Dynamically load plugins from embedded data ๐Ÿ—๏ธ Architecture Detection Automatically identifies PE file architecture: Architecture Machine Code Description x86 0x014C 32-bit Intel x64 0x8664 64-bit AMD/Intel ARM 0x01C0, 0x01C4 ARM processors ARM64 0xAA64 64-bit ARM IA64 0x0200 Intel Itanium Not PE - Non-executable files ๐Ÿ› ๏ธ Technical Details Encoding Methods Hex Encoding: Binary($sHexData) ; Direct conversion from hex string Base64 Encoding: Uses Windows Crypto API (Crypt32.dll) Unicode support (CryptStringToBinaryW) Automatic whitespace removal Compression LZNT Algorithm: Windows native compression (ntdll.dll) RtlCompressBuffer / RtlDecompressBuffer Workspace allocation: 1MB (0x100000 bytes) Error handling with proper status codes Generated Code Structure 1. Header comments (file info, settings) 2. Data functions (_GetBinData_xxx) 3. Helper functions (decode/decompress) 4. Deployment functions (_DeployFile or _GetBin) 5. Usage examples (commented) ๐Ÿ“ Error Handling The tool provides comprehensive error handling: Error Code Description SetError 1 Cannot read file or invalid data SetError 2 Encoding/compression failed SetError 3 Decompression failed SetError 4 Cannot create output file SetError 5 File write verification failed Error Messages: Console output for debugging MessageBox alerts for critical errors Descriptive error messages in generated code ๐Ÿ”ง Advanced Features Custom Function Names Function names are automatically sanitized: Removes invalid characters Includes filename and architecture Format: _GetBinData_filename_architecture Helper Function Options For Single File: _DeployFile($sDestPath = "", $bReturnHex = False) Returns binary data (default) Returns hex string ($bReturnHex = True) Writes to file ($sDestPath provided) For Multiple Files: _GetBin($sName) Switch/Case based selection Returns binary data Includes all decode/decompress logic ๐Ÿ“Š Performance Tips Compression Trade-offs: Level 1: Faster, moderate compression Level 2: Slower, better compression Skip compression for files < 10KB Encoding Selection: Use Hex for debugging (readable) Use Base64 for smaller output size ~33% size increase with Base64 vs binary Chunk Size: Larger chunks = fewer lines but harder to edit Smaller chunks = more readable but more lines Default 4000 is optimal for most cases ๐Ÿ”„ Version History Version 3.0 (Current) โœ… Added Base64 encoding support โœ… Integrated LZNT compression (Level 1 & 2) โœ… Redesigned GUI with radio buttons โœ… Added _GetBin() for multiple files โœ… Enhanced _DeployFile() with flexible return options โœ… Fixed function naming (sanitization) โœ… Improved error handling and reporting โœ… Unicode support for Base64 (CryptStringToBinaryW) โœ… Workspace allocation for LZNT compression โœ… Integrated Base64.au3 library Version 2.x Legacy hex-only encoding Basic helper functions GUI mode only ๐Ÿ“„ License MIT License - Free to use, modify, and distribute. ๐Ÿ™ Acknowledgments AutoIt Community for feedback and testing LZNT_Base64.au3 library implementation Windows API documentation for LZNT compression โšก Quick Reference Card โ•”โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•— โ•‘ QUICK REFERENCE - AutoIt Resource Embedder v3.0 โ•‘ โ• โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•ฃ โ•‘ GUI Mode: Double-click script โ•‘ โ•‘ CLI Mode: AutoIt3.exe script.au3 file1 file2 ... โ•‘ โ•‘ โ•‘ โ•‘ Encoding Options: โ•‘ โ•‘ • Hex - Standard hex encoding โ•‘ โ•‘ • Base64 - Base64 encoding โ•‘ โ•‘ • Hex + LZNT - Hex with compression โ•‘ โ•‘ • Base64+LZNT - Base64 with compression โ•‘ โ•‘ โ•‘ โ•‘ Single File: _DeployFile($path, $bReturnHex) โ•‘ โ•‘ Multiple Files: _GetBin($filename) โ•‘ โ•‘ โ•‘ โ•‘ Line Length: 100 - 4000 characters (default: 4000) โ•‘ โ•‘ Compression: Level 1 (4096) or Level 2 (0) โ•‘ โ•šโ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ•โ• Made with โค๏ธ by Dao Van Trong - TRONG.PRO Embed anything, anywhere! App Source: #Region ;**** Directives created by AutoIt3Wrapper_GUI **** #AutoIt3Wrapper_UseX64=y #EndRegion ;**** Directives created by AutoIt3Wrapper_GUI **** ; ================================================================================================= ; Title .........: AutoIt Resource Embedder ; Author(s) .....: Dao Van Trong - TRONG.PRO ; Version .......: 3.0 (Enhanced with multiple encoding formats and compression support) ; Description ...: A professional tool to convert binary files into self-contained AutoIt functions. ; Features: Hex/Base64 encoding, LZNT compression, architecture detection, ; GUI and CLI modes, helper functions with automatic decompression/decoding. ; ================================================================================================= #Region ; *** INCLUDES *** #include <GUIConstantsEx.au3> #include <StaticConstants.au3> #include <WindowsConstants.au3> #include <ListViewConstants.au3> #include <ButtonConstants.au3> #include <ComboConstants.au3> #include <ListBoxConstants.au3> #include <EditConstants.au3> #include <StaticConstants.au3> #include <WinAPIError.au3> #include <Security.au3> #include <Memory.au3> #include <Clipboard.au3> #include <SendMessage.au3> #include <WinAPISys.au3> #include <WinAPISysWin.au3> #include <GuiStatusBar.au3> #include <Array.au3> #include <File.au3> #EndRegion ; *** INCLUDES *** #Region ; *** GLOBAL VARIABLES *** ; Global variables for GUI controls Global $g_hGUI, $g_hListView, $g_hEditOutput, $g_hInputChunkSize, $iStatusBar Global $g_hBtnAddFiles, $g_hBtnRemoveSelected, $g_hBtnClearAll, $g_hCheckAddHelpers, $g_hBtnGenerate, $g_hBtnPreview, $g_hBtnCopy, $g_hBtnSaveAll, $g_hBtnSaveSeparate, $g_hBtnExit Global $g_hRadioHex, $g_hRadioBase64, $g_hRadioHexLZNT, $g_hRadioBase64LZNT, $g_hComboCompression ; Global 2D array to store file information. ; Index [x][0]: Full Path ; Index [x][1]: File Name ; Index [x][2]: Formatted File Size ; Index [x][3]: Architecture ; Index [x][4]: Generated Function Name Global $g_aSelectedFiles[0][5] #EndRegion ; *** GLOBAL VARIABLES *** #Region ; *** SCRIPT ENTRY POINT *** ; Check if command-line arguments were provided to determine execution mode. If $CmdLine[0] > 0 Then _RunCommandLineMode() Else _RunGuiMode() EndIf #EndRegion ; *** SCRIPT ENTRY POINT *** #Region ; *** GUI MODE FUNCTIONS *** ; ------------------------------------------------------------------------------------------------- ; Function: _RunGuiMode() ; Purpose: Creates and manages the main Graphical User Interface (GUI). ; ------------------------------------------------------------------------------------------------- Func _RunGuiMode() $g_hGUI = GUICreate("AutoIt Resource Embedder by Dao Van Trong - TRONG.PRO", 795, 555) GUISetFont(9, 400, 0, "Segoe UI", $g_hGUI, 5) GUISetBkColor(0xF0F0F0) _CreateGUI_Controls() $iStatusBar = _GUICtrlStatusBar_Create($g_hGUI) _GUICtrlStatusBar_SetText($iStatusBar, "Ready | AutoIt Resource Embedder v3.0") GUISetState(@SW_SHOW, $g_hGUI) Local $nMsg While 1 $nMsg = GUIGetMsg() Switch $nMsg Case $GUI_EVENT_CLOSE, $g_hBtnExit ExitLoop Case $g_hBtnAddFiles _GUI_HandleAddFiles() Case $g_hBtnRemoveSelected _GUI_HandleRemoveSelected() Case $g_hBtnClearAll _GUI_HandleClearAll() Case $g_hBtnGenerate _GUI_HandleGenerateAll() Case $g_hBtnPreview _GUI_HandlePreviewSingle() Case $g_hBtnCopy _GUI_HandleCopyToClipboard() Case $g_hBtnSaveAll _GUI_HandleSaveAll() Case $g_hBtnSaveSeparate _GUI_HandleSaveSeparate() EndSwitch WEnd GUIDelete($g_hGUI) EndFunc ;==>_RunGuiMode ; ------------------------------------------------------------------------------------------------- ; Function: _CreateGUI_Controls() ; Purpose: Creates all controls for the main GUI window. ; ------------------------------------------------------------------------------------------------- Func _CreateGUI_Controls() GUICtrlCreateLabel("1. File Selection:", 10, 15, 150, 20, $SS_CENTERIMAGE, $GUI_WS_EX_PARENTDRAG) GUICtrlSetFont(-1, 9, 800) $g_hBtnAddFiles = GUICtrlCreateButton("Add Files...", 162, 11, 100, 25, BitOR($BS_CENTER, $BS_VCENTER)) $g_hBtnRemoveSelected = GUICtrlCreateButton("Remove Selected", 272, 11, 120, 25, BitOR($BS_CENTER, $BS_VCENTER)) $g_hBtnClearAll = GUICtrlCreateButton("Clear All", 402, 11, 80, 25, BitOR($BS_CENTER, $BS_VCENTER)) $g_hListView = GUICtrlCreateListView("File Name|Size|Architecture|Function Name", 10, 38, 780, 150) GUICtrlSendMsg($g_hListView, $LVM_SETCOLUMNWIDTH, 0, 250) GUICtrlSendMsg($g_hListView, $LVM_SETCOLUMNWIDTH, 1, 100) GUICtrlSendMsg($g_hListView, $LVM_SETCOLUMNWIDTH, 2, 100) GUICtrlSendMsg($g_hListView, $LVM_SETCOLUMNWIDTH, 3, 320) GUICtrlCreateLabel("2. Generation Options:", 10, 195, 150, 20, $SS_CENTERIMAGE, $GUI_WS_EX_PARENTDRAG) GUICtrlSetFont(-1, 9, 800) GUICtrlCreateLabel("Output Format:", 4, 220, 132, 20, BitOR($SS_RIGHT, $SS_CENTERIMAGE), $GUI_WS_EX_PARENTDRAG) GUICtrlSetFont(-1, 8, 700, 2) $g_hRadioHex = GUICtrlCreateRadio("Hex", 172, 220, 76, 22) GUICtrlSetState(-1, $GUI_CHECKED) $g_hRadioBase64 = GUICtrlCreateRadio("Base64", 252, 220, 100, 22) $g_hRadioHexLZNT = GUICtrlCreateRadio("Hex + LZNT", 358, 220, 100, 22) $g_hRadioBase64LZNT = GUICtrlCreateRadio("Base64 + LZNT", 470, 220, 100, 22) GUICtrlCreateLabel("LZNT Level:", 584, 220, 100, 20, BitOR($SS_RIGHT, $SS_CENTERIMAGE), $GUI_WS_EX_PARENTDRAG) $g_hComboCompression = GUICtrlCreateCombo("", 688, 220, 96, 25, BitOR($GUI_SS_DEFAULT_COMBO, $CBS_SIMPLE)) GUICtrlSetData($g_hComboCompression, "Level 1|Level 2", "Level 2") GUICtrlCreateLabel("Line Length (chars):", 584, 195, 100, 20, BitOR($SS_RIGHT, $SS_CENTERIMAGE), $GUI_WS_EX_PARENTDRAG) GUICtrlSetFont(-1, 8, 700, 2) $g_hInputChunkSize = GUICtrlCreateInput("4000", 688, 195, 96, 23) $g_hCheckAddHelpers = GUICtrlCreateCheckbox("Include helper functions", 172, 195, 200, 22) GUICtrlSetState(-1, $GUI_CHECKED) $g_hBtnGenerate = GUICtrlCreateButton("3. Generate All Functions", 210, 243, 304, 35, BitOR($BS_CENTER, $BS_VCENTER)) GUICtrlSetFont(-1, 10, 800) GUICtrlSetBkColor($g_hBtnGenerate, 0x90EE90) $g_hBtnPreview = GUICtrlCreateButton("Preview Single", 516, 243, 116, 35, BitOR($BS_CENTER, $BS_VCENTER)) GUICtrlCreateLabel("Generated Code:", 10, 252, 150, 20, $SS_CENTERIMAGE, $GUI_WS_EX_PARENTDRAG) GUICtrlSetFont(-1, 9, 800) $g_hEditOutput = GUICtrlCreateEdit("", 10, 280, 780, 220) GUICtrlSetData(-1, "") GUICtrlSetFont(-1, 9, 400) $g_hBtnCopy = GUICtrlCreateButton("Copy to Clipboard", 634, 243, 154, 35, BitOR($BS_CENTER, $BS_VCENTER)) GUICtrlSetFont(-1, 9, 800) $g_hBtnSaveAll = GUICtrlCreateButton("Save All to File", 14, 502, 130, 30, BitOR($BS_CENTER, $BS_VCENTER)) $g_hBtnSaveSeparate = GUICtrlCreateButton("Save Separate Files", 154, 502, 130, 30, BitOR($BS_CENTER, $BS_VCENTER)) $g_hBtnExit = GUICtrlCreateButton("Exit", 660, 502, 130, 30, BitOR($BS_CENTER, $BS_VCENTER)) GUICtrlSetBkColor($g_hBtnExit, 0xFFB6C1) EndFunc ;==>_CreateGUI_Controls ; ------------------------------------------------------------------------------------------------- ; Function: _GUI_HandleAddFiles() ; Purpose: Opens a file dialog and adds selected files to the list. ; ------------------------------------------------------------------------------------------------- Func _GUI_HandleAddFiles() Local $sFiles = FileOpenDialog("Select Files", @ScriptDir, "All Files (*.*)", 4) If @error Then _GUICtrlStatusBar_SetText($iStatusBar, "File selection cancelled") Return EndIf Local $aNewFiles = StringSplit($sFiles, "|") Local $iAdded = 0, $iSkipped = 0 If $aNewFiles[0] = 1 Then ; Single file If _AddFileToList($aNewFiles[1]) Then $iAdded = 1 Else $iSkipped = 1 EndIf Else ; Multiple files Local $sBasePath = $aNewFiles[1] For $i = 2 To $aNewFiles[0] If _AddFileToList($sBasePath & "\" & $aNewFiles[$i]) Then $iAdded += 1 Else $iSkipped += 1 EndIf Next EndIf ; Update status bar with detailed information Local $sStatus = "" If $iAdded > 0 Then $sStatus = "Added " & $iAdded & " file" & ($iAdded > 1 ? "s" : "") If $iSkipped > 0 Then $sStatus &= ($sStatus <> "" ? " | " : "") & "Skipped " & $iSkipped & " duplicate" & ($iSkipped > 1 ? "s" : "") $sStatus &= " | Total: " & UBound($g_aSelectedFiles) & " file(s)" _GUICtrlStatusBar_SetText($iStatusBar, $sStatus) EndFunc ;==>_GUI_HandleAddFiles ; ------------------------------------------------------------------------------------------------- ; Function: _GUI_HandleRemoveSelected() ; Purpose: Removes the selected file from the list. ; ------------------------------------------------------------------------------------------------- Func _GUI_HandleRemoveSelected() Local $iIndex = GUICtrlSendMsg($g_hListView, $LVM_GETNEXTITEM, -1, $LVNI_SELECTED) If $iIndex = -1 Then _GUICtrlStatusBar_SetText($iStatusBar, "No file selected") Return EndIf _ArrayDelete($g_aSelectedFiles, $iIndex) GUICtrlSendMsg($g_hListView, $LVM_DELETEITEM, $iIndex, 0) _GUICtrlStatusBar_SetText($iStatusBar, "File removed | Total: " & UBound($g_aSelectedFiles) & " file(s)") EndFunc ;==>_GUI_HandleRemoveSelected ; ------------------------------------------------------------------------------------------------- ; Function: _GUI_HandleClearAll() ; Purpose: Clears all files from the list and resets the UI. ; ------------------------------------------------------------------------------------------------- Func _GUI_HandleClearAll() ReDim $g_aSelectedFiles[0][5] GUICtrlSendMsg($g_hListView, $LVM_DELETEALLITEMS, 0, 0) GUICtrlSetData($g_hEditOutput, "") _GUICtrlStatusBar_SetText($iStatusBar, "All files cleared | Ready") EndFunc ;==>_GUI_HandleClearAll ; ------------------------------------------------------------------------------------------------- ; Function: _GUI_HandleGenerateAll() ; Purpose: Generates the complete code for all files in the list. ; ------------------------------------------------------------------------------------------------- Func _GUI_HandleGenerateAll() If UBound($g_aSelectedFiles) = 0 Then Return MsgBox(48, "Warning", "Please add at least one file first.") GUICtrlSetData($g_hEditOutput, "Generating code, please wait...") Sleep(10) Local $bAddHelpers = (GUICtrlRead($g_hCheckAddHelpers) = $GUI_CHECKED) Local $iChunkSize = _ValidateChunkSize(GUICtrlRead($g_hInputChunkSize)) ; Determine encoding/compression from radio buttons Local $bUseHex = False, $bUseBase64 = False, $bUseCompression = False, $iCompLevel = 0 If GUICtrlRead($g_hRadioHex) = $GUI_CHECKED Then $bUseHex = True ElseIf GUICtrlRead($g_hRadioBase64) = $GUI_CHECKED Then $bUseBase64 = True ElseIf GUICtrlRead($g_hRadioHexLZNT) = $GUI_CHECKED Then $bUseHex = True $bUseCompression = True $iCompLevel = (GUICtrlRead($g_hComboCompression) = "Level 2") ? 2 : 1 ElseIf GUICtrlRead($g_hRadioBase64LZNT) = $GUI_CHECKED Then $bUseBase64 = True $bUseCompression = True $iCompLevel = (GUICtrlRead($g_hComboCompression) = "Level 2") ? 2 : 1 EndIf Local $sCode = _GenerateCodeBundle($g_aSelectedFiles, $bAddHelpers, $iChunkSize, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) GUICtrlSetData($g_hEditOutput, $sCode) _GUICtrlStatusBar_SetText($iStatusBar, "Code generated successfully for " & UBound($g_aSelectedFiles) & " file(s) | " & StringLen($sCode) & " characters") EndFunc ;==>_GUI_HandleGenerateAll ; ------------------------------------------------------------------------------------------------- ; Function: _GUI_HandlePreviewSingle() ; Purpose: Generates code for only the selected file. ; ------------------------------------------------------------------------------------------------- Func _GUI_HandlePreviewSingle() Local $iIndex = GUICtrlSendMsg($g_hListView, $LVM_GETNEXTITEM, -1, $LVNI_SELECTED) If $iIndex = -1 Then Return MsgBox(48, "Warning", "Please select a file from the list first.") GUICtrlSetData($g_hEditOutput, "Generating preview...") Sleep(10) Local $iChunkSize = _ValidateChunkSize(GUICtrlRead($g_hInputChunkSize)) ; Determine encoding/compression from radio buttons Local $bUseHex = False, $bUseBase64 = False, $bUseCompression = False, $iCompLevel = 0 If GUICtrlRead($g_hRadioHex) = $GUI_CHECKED Then $bUseHex = True ElseIf GUICtrlRead($g_hRadioBase64) = $GUI_CHECKED Then $bUseBase64 = True ElseIf GUICtrlRead($g_hRadioHexLZNT) = $GUI_CHECKED Then $bUseHex = True $bUseCompression = True $iCompLevel = (GUICtrlRead($g_hComboCompression) = "Level 2") ? 2 : 1 ElseIf GUICtrlRead($g_hRadioBase64LZNT) = $GUI_CHECKED Then $bUseBase64 = True $bUseCompression = True $iCompLevel = (GUICtrlRead($g_hComboCompression) = "Level 2") ? 2 : 1 EndIf Local $sOutput = "; Preview for: " & $g_aSelectedFiles[$iIndex][1] & @CRLF $sOutput &= "; Architecture: " & $g_aSelectedFiles[$iIndex][3] & @CRLF & @CRLF Local $sCode = _GenerateEncodedFunction($g_aSelectedFiles[$iIndex][0], $g_aSelectedFiles[$iIndex][4], $g_aSelectedFiles[$iIndex][1], $g_aSelectedFiles[$iIndex][3], $iChunkSize, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) If GUICtrlRead($g_hCheckAddHelpers) = $GUI_CHECKED Then $sCode &= @CRLF & @CRLF & _GenerateHelperFunction($g_aSelectedFiles[$iIndex][4], $g_aSelectedFiles[$iIndex][1], $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) EndIf GUICtrlSetData($g_hEditOutput, $sOutput & $sCode) _GUICtrlStatusBar_SetText($iStatusBar, "Preview generated for: " & $g_aSelectedFiles[$iIndex][1]) EndFunc ;==>_GUI_HandlePreviewSingle ; ------------------------------------------------------------------------------------------------- ; Function: _GUI_HandleCopyToClipboard() ; Purpose: Copies the output text to the clipboard. ; ------------------------------------------------------------------------------------------------- Func _GUI_HandleCopyToClipboard() Local $sCode = GUICtrlRead($g_hEditOutput) If StringStripWS($sCode, 8) = "" Then _GUICtrlStatusBar_SetText($iStatusBar, "No code to copy") Return MsgBox(48, "Warning", "No code to copy. Please generate code first.") EndIf _ClipBoard_SetData($sCode) _GUICtrlStatusBar_SetText($iStatusBar, "Code copied to clipboard | " & StringLen($sCode) & " characters") MsgBox(64, "Success", "Code copied to clipboard successfully!") GUICtrlSetData($g_hEditOutput, $sCode) EndFunc ;==>_GUI_HandleCopyToClipboard ; ------------------------------------------------------------------------------------------------- ; Function: _GUI_HandleSaveAll() ; Purpose: Saves the generated code for all files into a single .au3 file. ; ------------------------------------------------------------------------------------------------- Func _GUI_HandleSaveAll() Local $sCode = GUICtrlRead($g_hEditOutput) If StringStripWS($sCode, 8) = "" Then Return MsgBox(48, "Warning", "No code to save. Please generate code first.") Local $sSaveFile = FileSaveDialog("Save Combined Code", @ScriptDir, "AutoIt Scripts (*.au3)", 16, "All_Embedded.au3") If @error Then Return If @error Or Not _SaveStringToFile($sSaveFile, $sCode) Then _GUICtrlStatusBar_SetText($iStatusBar, "Save failed: " & $sSaveFile) Return MsgBox(16, "Error", "Failed to save file: " & $sSaveFile) EndIf _GUICtrlStatusBar_SetText($iStatusBar, "File saved: " & $sSaveFile & " | " & _FormatFileSize(FileGetSize($sSaveFile))) MsgBox(64, "Success", "File saved successfully: " & $sSaveFile) EndFunc ;==>_GUI_HandleSaveAll ; ------------------------------------------------------------------------------------------------- ; Function: _GUI_HandleSaveSeparate() ; Purpose: Saves the generated code for each file into its own separate .au3 file. ; ------------------------------------------------------------------------------------------------- Func _GUI_HandleSaveSeparate() If UBound($g_aSelectedFiles) = 0 Then Return MsgBox(48, "Warning", "No files to process.") Local $sSaveDir = FileSelectFolder("Select folder to save separate files", @ScriptDir) If @error Then Return Local $iChunkSize = _ValidateChunkSize(GUICtrlRead($g_hInputChunkSize)) Local $bAddHelpers = (GUICtrlRead($g_hCheckAddHelpers) = $GUI_CHECKED) ; Determine encoding/compression from radio buttons Local $bUseHex = False, $bUseBase64 = False, $bUseCompression = False, $iCompLevel = 0 If GUICtrlRead($g_hRadioHex) = $GUI_CHECKED Then $bUseHex = True ElseIf GUICtrlRead($g_hRadioBase64) = $GUI_CHECKED Then $bUseBase64 = True ElseIf GUICtrlRead($g_hRadioHexLZNT) = $GUI_CHECKED Then $bUseHex = True $bUseCompression = True $iCompLevel = (GUICtrlRead($g_hComboCompression) = "Level 2") ? 2 : 1 ElseIf GUICtrlRead($g_hRadioBase64LZNT) = $GUI_CHECKED Then $bUseBase64 = True $bUseCompression = True $iCompLevel = (GUICtrlRead($g_hComboCompression) = "Level 2") ? 2 : 1 EndIf Local $iSaved = 0 For $i = 0 To UBound($g_aSelectedFiles) - 1 Local $sFilePath = $g_aSelectedFiles[$i][0] Local $sFileName = $g_aSelectedFiles[$i][1] Local $sArch = $g_aSelectedFiles[$i][3] Local $sFuncName = $g_aSelectedFiles[$i][4] Local $sDrive, $sDir, $sNameOnly, $sExt _PathSplit($sFilePath, $sDrive, $sDir, $sNameOnly, $sExt) Local $sSaveFile = $sSaveDir & "\" & $sNameOnly & "_Embedded.au3" Local $sCode = "; Generated from: " & $sFileName & @CRLF $sCode &= "; Architecture: " & $sArch & @CRLF & @CRLF $sCode &= _GenerateEncodedFunction($sFilePath, $sFuncName, $sFileName, $sArch, $iChunkSize, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) If $bAddHelpers Then $sCode &= _GenerateHelperFunction($sFuncName, $sFileName, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) EndIf If _SaveStringToFile($sSaveFile, $sCode) Then $iSaved += 1 Next _GUICtrlStatusBar_SetText($iStatusBar, "Saved " & $iSaved & " of " & UBound($g_aSelectedFiles) & " file(s) to: " & $sSaveDir) MsgBox(64, "Success", "Saved " & $iSaved & " of " & UBound($g_aSelectedFiles) & " files to:" & @CRLF & $sSaveDir) EndFunc ;==>_GUI_HandleSaveSeparate #EndRegion ; *** GUI MODE FUNCTIONS *** #Region ; *** COMMAND-LINE MODE FUNCTIONS *** ; ------------------------------------------------------------------------------------------------- ; Function: _RunCommandLineMode() ; Purpose: Handles the script's execution when run from the command line. ; ------------------------------------------------------------------------------------------------- Func _RunCommandLineMode() Local $aFilePaths[0] For $i = 1 To $CmdLine[0] If FileExists($CmdLine[$i]) Then _ArrayAdd($aFilePaths, $CmdLine[$i]) Else ConsoleWrite("! Warning: File not found - " & $CmdLine[$i] & @CRLF) EndIf Next If UBound($aFilePaths) = 0 Then ConsoleWrite("! Error: No valid files provided." & @CRLF & " Usage: " & @ScriptName & " <file1> [file2] ..." & @CRLF) Exit 1 EndIf Local $aFilesData[UBound($aFilePaths)][5] For $i = 0 To UBound($aFilePaths) - 1 _PopulateFileInfo($aFilesData, $i, $aFilePaths[$i]) Next ConsoleWrite("+ Generating code for " & UBound($aFilesData) & " file(s)..." & @CRLF) Local $sCode = _GenerateCodeBundle($aFilesData, True, 4000, True, False, False, 0) Local $sOutputFile If UBound($aFilesData) = 1 Then Local $sDrive, $sDir, $sFileName, $sExtension _PathSplit($aFilePaths[0], $sDrive, $sDir, $sFileName, $sExtension) $sOutputFile = $sDrive & $sDir & $sFileName & "_Embedded.au3" Else $sOutputFile = @ScriptDir & "\All_Embedded.au3" EndIf If _SaveStringToFile($sOutputFile, $sCode) Then ConsoleWrite("+ Success: Output saved to - " & $sOutputFile & @CRLF) Else ConsoleWrite("! Error: Could not create output file - " & $sOutputFile & @CRLF) Exit 1 EndIf EndFunc ;==>_RunCommandLineMode #EndRegion ; *** COMMAND-LINE MODE FUNCTIONS *** #Region ; *** FILE AND DATA HANDLING *** ; ------------------------------------------------------------------------------------------------- ; Function: _AddFileToList($sFilePath) ; Purpose: Adds a file's information to the global array and updates the GUI list. ; Prevents duplicate files from being added. ; ------------------------------------------------------------------------------------------------- Func _AddFileToList($sFilePath) ; Validate file exists If Not FileExists($sFilePath) Then _GUICtrlStatusBar_SetText($iStatusBar, "File not found: " & $sFilePath) Return False EndIf ; Check for duplicate - exact path match For $i = 0 To UBound($g_aSelectedFiles) - 1 If $g_aSelectedFiles[$i][0] = $sFilePath Then Local $sFileName = _GetFileName($sFilePath) _GUICtrlStatusBar_SetText($iStatusBar, "Duplicate skipped: " & $sFileName & " (already in list)") Return False EndIf Next ; Add new file Local $iUBound = UBound($g_aSelectedFiles) ReDim $g_aSelectedFiles[$iUBound + 1][5] _PopulateFileInfo($g_aSelectedFiles, $iUBound, $sFilePath) Local $sListViewItem = $g_aSelectedFiles[$iUBound][1] & "|" & $g_aSelectedFiles[$iUBound][2] & "|" & $g_aSelectedFiles[$iUBound][3] & "|" & $g_aSelectedFiles[$iUBound][4] GUICtrlCreateListViewItem($sListViewItem, $g_hListView) Return True EndFunc ;==>_AddFileToList ; ------------------------------------------------------------------------------------------------- ; Function: _PopulateFileInfo(ByRef $aArray, $iIndex, $sFilePath) ; Purpose: Gathers file info and populates a row in the provided 2D array. ; ------------------------------------------------------------------------------------------------- Func _PopulateFileInfo(ByRef $aArray, $iIndex, $sFilePath) Local $sFileName = _GetFileName($sFilePath) Local $sArch = _DetectArchitecture($sFilePath) $aArray[$iIndex][0] = $sFilePath $aArray[$iIndex][1] = $sFileName $aArray[$iIndex][2] = _FormatFileSize(FileGetSize($sFilePath)) $aArray[$iIndex][3] = $sArch $aArray[$iIndex][4] = "_GetBinData_" & _SanitizeName($sFileName) & "_" & _SanitizeName($sArch) EndFunc ;==>_PopulateFileInfo #EndRegion ; *** FILE AND DATA HANDLING *** #Region ; *** CORE CODE GENERATION *** ; ------------------------------------------------------------------------------------------------- ; Function: _GenerateCodeBundle(ByRef $aFiles, $bAddHelpers, $iChunkSize, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) ; Purpose: The main code generation engine. Creates the full script content. ; ------------------------------------------------------------------------------------------------- Func _GenerateCodeBundle(ByRef $aFiles, $bAddHelpers, $iChunkSize, $bUseHex = True, $bUseBase64 = False, $bUseCompression = False, $iCompLevel = 0) Local $sOutput = "; Generated by AutoIt Resource Embedder - TRONG.PRO" & @CRLF $sOutput &= "; Total files: " & UBound($aFiles) & @CRLF $sOutput &= "; Encoding: " & ($bUseHex ? "Hex " : "") & ($bUseBase64 ? "Base64 " : "") & @CRLF $sOutput &= "; Compression: " & ($bUseCompression And $iCompLevel > 0 ? "LZNT Level " & $iCompLevel : "None") & @CRLF $sOutput &= "; Generated on: " & @YEAR & "-" & @MON & "-" & @MDAY & " " & @HOUR & ":" & @MIN & ":" & @SEC & @CRLF & @CRLF For $i = 0 To UBound($aFiles) - 1 $sOutput &= _GenerateEncodedFunction($aFiles[$i][0], $aFiles[$i][4], $aFiles[$i][1], $aFiles[$i][3], $iChunkSize, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) & @CRLF & @CRLF Next If $bAddHelpers Then If UBound($aFiles) = 1 Then $sOutput &= _GenerateHelperFunction($aFiles[0][4], $aFiles[0][1], $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) Else $sOutput &= _GenerateMasterHelperFunctionFromArray($aFiles, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) EndIf EndIf Return $sOutput EndFunc ;==>_GenerateCodeBundle ; ------------------------------------------------------------------------------------------------- ; Function: _GenerateEncodedFunction($sFilePath, $sFuncName, $sFileName, $sArch, $iChunkSize, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) ; Purpose: Reads a binary file and wraps its encoded content in an AutoIt function. ; ------------------------------------------------------------------------------------------------- Func _GenerateEncodedFunction($sFilePath, $sFuncName, $sFileName, $sArch, $iChunkSize = 4000, $bUseHex = True, $bUseBase64 = False, $bUseCompression = False, $iCompLevel = 0) Local $hFile = FileOpen($sFilePath, 16) If $hFile = -1 Then ConsoleWrite("! Error: Unable to open file in binary mode: " & $sFilePath & @CRLF) Return "" EndIf Local $bData = FileRead($hFile) FileClose($hFile) If @error Or $bData = "" Then ConsoleWrite("! Error reading binary data from file: " & $sFilePath & @CRLF) Return "" EndIf ; Apply compression if requested Local $bProcessedData = $bData If $bUseCompression And $iCompLevel > 0 Then Local $iEngine = ($iCompLevel = 2) ? 258 : 2 ; 2=Standard, 258=Maximum $bProcessedData = _LZNT_Compress($bData, 16, $iEngine, False) ; Updated library signature If @error Then ConsoleWrite("! Error: LZNT compression failed for file: " & $sFilePath & @CRLF) MsgBox(16, "Compression Error", "Failed to compress file: " & $sFileName & @CRLF & @CRLF & "Please try again or disable compression.") Return "" EndIf ConsoleWrite("+ Compressed " & $sFileName & ": " & _FormatFileSize(BinaryLen($bData)) & " → " & _FormatFileSize(BinaryLen($bProcessedData)) & @CRLF) EndIf ; Generate function header Local $sOutput = "Func " & $sFuncName & "()" & @CRLF $sOutput &= @TAB & '; This function holds the encoded data for ' & $sFileName & @CRLF $sOutput &= @TAB & '; File size: ' & _FormatFileSize(FileGetSize($sFilePath)) & @CRLF $sOutput &= @TAB & '; Architecture: ' & $sArch & @CRLF $sOutput &= @TAB & '; Encoding: ' & ($bUseHex ? "Hex " : "") & ($bUseBase64 ? "Base64 " : "") & @CRLF $sOutput &= @TAB & '; Compression: ' & ($bUseCompression And $iCompLevel > 0 ? "LZNT Level " & $iCompLevel : "None") & @CRLF $sOutput &= @TAB & '; Generated by AutoIt Resource Embedder' & @CRLF ; Generate Hex data if requested If $bUseHex Then Local $sHexWithPrefix = String($bProcessedData) Local $iHexLen = StringLen($sHexWithPrefix) $sOutput &= @TAB & "Local $sHexData = '" & StringMid($sHexWithPrefix, 1, $iChunkSize) & "'" & @CRLF For $i = $iChunkSize + 1 To $iHexLen Step $iChunkSize $sOutput &= @TAB & "$sHexData &= '" & StringMid($sHexWithPrefix, $i, $iChunkSize) & "'" & @CRLF Next EndIf ; Generate Base64 data if requested If $bUseBase64 Then Local $sBase64 = _Base64Encode($bProcessedData, 0) ; 0 = no line breaks If @error Or $sBase64 = "" Then ConsoleWrite("! Error: Base64 encoding failed for file: " & $sFilePath & @CRLF) MsgBox(16, "Encoding Error", "Failed to encode file to Base64: " & $sFileName & @CRLF & @CRLF & "Please try again or use Hex encoding.") Return "" EndIf Local $iB64Len = StringLen($sBase64) $sOutput &= @TAB & "Local $sBase64Data = '" & StringMid($sBase64, 1, $iChunkSize) & "'" & @CRLF For $i = $iChunkSize + 1 To $iB64Len Step $iChunkSize $sOutput &= @TAB & "$sBase64Data &= '" & StringMid($sBase64, $i, $iChunkSize) & "'" & @CRLF Next EndIf ; Return appropriate data based on encoding options $sOutput &= @CRLF If $bUseHex And $bUseBase64 Then $sOutput &= @TAB & '; Returns array: [0] = Hex, [1] = Base64' & @CRLF $sOutput &= @TAB & 'Local $aData[2] = [$sHexData, $sBase64Data]' & @CRLF $sOutput &= @TAB & 'Return $aData' & @CRLF ElseIf $bUseHex Then $sOutput &= @TAB & 'Return $sHexData' & @CRLF Else $sOutput &= @TAB & 'Return $sBase64Data' & @CRLF EndIf $sOutput &= "EndFunc ;==>" & $sFuncName Return $sOutput EndFunc ;==>_GenerateEncodedFunction ; ------------------------------------------------------------------------------------------------- ; Function: _GenerateHelperFunction($sFuncName, $sOriginalFileName, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) ; Purpose: Generates a helper function to deploy a single embedded file with decode/decompress support. ; ------------------------------------------------------------------------------------------------- Func _GenerateHelperFunction($sFuncName, $sOriginalFileName, $bUseHex = True, $bUseBase64 = False, $bUseCompression = False, $iCompLevel = 0) Local $sHelperFunc = @CRLF & @CRLF ; Add Base64 decode function if needed If $bUseBase64 Then $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= '; Base64 Decode Function (Unicode version - matches Base64.au3 encoder)' & @CRLF $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= 'Func _Base64Decode($sB64String)' & @CRLF $sHelperFunc &= @TAB & '; Remove whitespace' & @CRLF $sHelperFunc &= @TAB & '$sB64String = StringRegExpReplace($sB64String, "\s", "")' & @CRLF $sHelperFunc &= @TAB & 'If $sB64String = "" Then Return SetError(1, 0, Binary(""))' & @CRLF $sHelperFunc &= @TAB & '; Get required buffer size' & @CRLF $sHelperFunc &= @TAB & 'Local $aResult = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryW", "wstr", $sB64String, "dword", StringLen($sB64String), "dword", 1, "ptr", 0, "dword*", 0, "ptr", 0, "ptr", 0)' & @CRLF $sHelperFunc &= @TAB & 'If @error Or Not $aResult[0] Then Return SetError(2, 0, Binary(""))' & @CRLF $sHelperFunc &= @TAB & 'Local $iSize = $aResult[5]' & @CRLF $sHelperFunc &= @TAB & 'Local $tOutput = DllStructCreate("byte[" & $iSize & "]")' & @CRLF $sHelperFunc &= @TAB & '; Perform decoding' & @CRLF $sHelperFunc &= @TAB & '$aResult = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryW", "wstr", $sB64String, "dword", StringLen($sB64String), "dword", 1, "struct*", $tOutput, "dword*", $iSize, "ptr", 0, "ptr", 0)' & @CRLF $sHelperFunc &= @TAB & 'If @error Or Not $aResult[0] Then Return SetError(3, 0, Binary(""))' & @CRLF $sHelperFunc &= @TAB & 'Return DllStructGetData($tOutput, 1)' & @CRLF $sHelperFunc &= 'EndFunc ;==>_Base64Decode' & @CRLF & @CRLF EndIf ; Add LZNT decompress function if needed If $bUseCompression And $iCompLevel > 0 Then Local $iEngine = ($iCompLevel = 2) ? 258 : 2 $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= '; LZNT Decompress Function (Engine: ' & $iEngine & ', Level: ' & $iCompLevel & ')' & @CRLF $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= 'Func _LZNT_Decompress($bCompressed)' & @CRLF $sHelperFunc &= @TAB & 'Local $tInput = DllStructCreate("byte[" & BinaryLen($bCompressed) & "]")' & @CRLF $sHelperFunc &= @TAB & 'DllStructSetData($tInput, 1, $bCompressed)' & @CRLF $sHelperFunc &= @TAB & 'Local $tOutput = DllStructCreate("byte[" & (BinaryLen($bCompressed) * 16) & "]")' & @CRLF $sHelperFunc &= @TAB & 'Local $aRet = DllCall("ntdll.dll", "int", "RtlDecompressBuffer", "ushort", ' & $iEngine & ', "ptr", DllStructGetPtr($tOutput), "dword", DllStructGetSize($tOutput), "ptr", DllStructGetPtr($tInput), "dword", DllStructGetSize($tInput), "dword*", 0)' & @CRLF $sHelperFunc &= @TAB & 'If @error Or $aRet[0] <> 0 Then Return SetError(1, 0, Binary(""))' & @CRLF $sHelperFunc &= @TAB & 'Local $tOut = DllStructCreate("byte[" & $aRet[6] & "]", DllStructGetPtr($tOutput))' & @CRLF $sHelperFunc &= @TAB & 'Return DllStructGetData($tOut, 1)' & @CRLF $sHelperFunc &= 'EndFunc ;==>_LZNT_Decompress' & @CRLF & @CRLF EndIf ; Add WriteBinaryFile helper function $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= '; Write Binary File Function' & @CRLF $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= 'Func _WriteBinaryFile($sFilePath, $bBinaryData)' & @CRLF $sHelperFunc &= @TAB & 'If Not IsBinary($bBinaryData) Then Return SetError(1, 0, False)' & @CRLF $sHelperFunc &= @TAB & 'If BinaryLen($bBinaryData) = 0 Then Return SetError(2, 0, False)' & @CRLF $sHelperFunc &= @TAB & '; Remove existing file/folder' & @CRLF $sHelperFunc &= @TAB & 'If FileExists($sFilePath) Then' & @CRLF $sHelperFunc &= @TAB & @TAB & 'FileSetAttrib($sFilePath, "-RASH", 1)' & @CRLF $sHelperFunc &= @TAB & @TAB & 'DirRemove($sFilePath, 1)' & @CRLF $sHelperFunc &= @TAB & @TAB & 'FileDelete($sFilePath)' & @CRLF $sHelperFunc &= @TAB & 'EndIf' & @CRLF $sHelperFunc &= @TAB & '; Write binary data' & @CRLF $sHelperFunc &= @TAB & 'Local $hFile = FileOpen($sFilePath, 2 + 8 + 16) ; Write + Create + Binary' & @CRLF $sHelperFunc &= @TAB & 'If $hFile = -1 Then Return SetError(3, 0, False)' & @CRLF $sHelperFunc &= @TAB & 'FileWrite($hFile, $bBinaryData)' & @CRLF $sHelperFunc &= @TAB & 'FileClose($hFile)' & @CRLF $sHelperFunc &= @TAB & 'Return FileExists($sFilePath)' & @CRLF $sHelperFunc &= 'EndFunc ;==>_WriteBinaryFile' & @CRLF & @CRLF ; Generate deployment function $sHelperFunc &= '; =================================================================' & @CRLF $sHelperFunc &= '; Helper function to deploy the file from encoded data.' & @CRLF $sHelperFunc &= '; Parameters: $sDestPath - File path to write (empty = return binary)' & @CRLF $sHelperFunc &= '; $bReturnHex - Return hex string instead of binary (Default: False)' & @CRLF $sHelperFunc &= '; Encoding: ' & ($bUseHex ? "Hex " : "") & ($bUseBase64 ? "Base64 " : "") & @CRLF $sHelperFunc &= '; Compression: ' & ($bUseCompression And $iCompLevel > 0 ? "LZNT Level " & $iCompLevel : "None") & @CRLF $sHelperFunc &= '; =================================================================' & @CRLF $sHelperFunc &= 'Func _DeployFile($sDestPath = "", $bReturnHex = False)' & @CRLF $sHelperFunc &= @TAB & '; Get encoded data from main function' & @CRLF ; Handle data retrieval based on encoding options If $bUseHex And $bUseBase64 Then $sHelperFunc &= @TAB & 'Local $aData = ' & $sFuncName & '()' & @CRLF $sHelperFunc &= @TAB & 'If Not IsArray($aData) Then Return SetError(1, 0, "")' & @CRLF $sHelperFunc &= @TAB & 'Local $bBinary = Binary($aData[0]) ; Use Hex data' & @CRLF ElseIf $bUseHex Then $sHelperFunc &= @TAB & 'Local $sHexData = ' & $sFuncName & '()' & @CRLF $sHelperFunc &= @TAB & 'If $sHexData = "" Then Return SetError(1, 0, "")' & @CRLF $sHelperFunc &= @TAB & 'Local $bBinary = Binary($sHexData)' & @CRLF Else $sHelperFunc &= @TAB & 'Local $sBase64Data = ' & $sFuncName & '()' & @CRLF $sHelperFunc &= @TAB & 'If $sBase64Data = "" Then Return SetError(1, 0, "")' & @CRLF $sHelperFunc &= @TAB & 'Local $bBinary = _Base64Decode($sBase64Data)' & @CRLF $sHelperFunc &= @TAB & 'If @error Then Return SetError(2, 0, "")' & @CRLF EndIf ; Add decompression if needed If $bUseCompression And $iCompLevel > 0 Then $sHelperFunc &= @CRLF & @TAB & '; Decompress the data' & @CRLF $sHelperFunc &= @TAB & '$bBinary = _LZNT_Decompress($bBinary)' & @CRLF $sHelperFunc &= @TAB & 'If @error Then Return SetError(3, 0, "")' & @CRLF EndIf ; Return binary/hex or write to file $sHelperFunc &= @CRLF & @TAB & '; If no destination path, return binary or hex string' & @CRLF $sHelperFunc &= @TAB & 'If $sDestPath = "" Then' & @CRLF $sHelperFunc &= @TAB & @TAB & 'If $bReturnHex Then' & @CRLF $sHelperFunc &= @TAB & @TAB & @TAB & 'Return StringTrimLeft($bBinary, 2) ; Remove "0x" prefix' & @CRLF $sHelperFunc &= @TAB & @TAB & 'Else' & @CRLF $sHelperFunc &= @TAB & @TAB & @TAB & 'Return $bBinary' & @CRLF $sHelperFunc &= @TAB & @TAB & 'EndIf' & @CRLF $sHelperFunc &= @TAB & 'EndIf' & @CRLF $sHelperFunc &= @CRLF & @TAB & '; Write binary data to file' & @CRLF $sHelperFunc &= @TAB & 'If Not _WriteBinaryFile($sDestPath, $bBinary) Then Return SetError(4, 0, "")' & @CRLF $sHelperFunc &= @TAB & 'Return $sDestPath' & @CRLF $sHelperFunc &= 'EndFunc ;==>_DeployFile' & @CRLF & @CRLF $sHelperFunc &= '; Example usage:' & @CRLF $sHelperFunc &= '; $bBinary = _DeployFile() ; Get binary data' & @CRLF $sHelperFunc &= '; $sHex = _DeployFile("", True) ; Get hex string' & @CRLF $sHelperFunc &= '; $sPath = _DeployFile(@TempDir & "\' & $sOriginalFileName & '") ; Write to file' & @CRLF Return $sHelperFunc EndFunc ;==>_GenerateHelperFunction ; ------------------------------------------------------------------------------------------------- ; Function: _GenerateMasterHelperFunctionFromArray(ByRef $aFiles, $bUseHex, $bUseBase64, $bUseCompression, $iCompLevel) ; Purpose: Generates _GetBin() function with Switch/Case for all embedded files. ; ------------------------------------------------------------------------------------------------- Func _GenerateMasterHelperFunctionFromArray(ByRef $aFiles, $bUseHex = True, $bUseBase64 = False, $bUseCompression = False, $iCompLevel = 0) Local $sHelperFunc = @CRLF & @CRLF ; Add Base64 decode function if needed If $bUseBase64 Then $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= '; Base64 Decode Function (Unicode version - matches Base64.au3 encoder)' & @CRLF $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= 'Func _Base64Decode($sB64String)' & @CRLF $sHelperFunc &= @TAB & '; Remove whitespace' & @CRLF $sHelperFunc &= @TAB & '$sB64String = StringRegExpReplace($sB64String, "\s", "")' & @CRLF $sHelperFunc &= @TAB & 'If $sB64String = "" Then Return SetError(1, 0, Binary(""))' & @CRLF $sHelperFunc &= @TAB & '; Get required buffer size' & @CRLF $sHelperFunc &= @TAB & 'Local $aResult = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryW", "wstr", $sB64String, "dword", StringLen($sB64String), "dword", 1, "ptr", 0, "dword*", 0, "ptr", 0, "ptr", 0)' & @CRLF $sHelperFunc &= @TAB & 'If @error Or Not $aResult[0] Then Return SetError(2, 0, Binary(""))' & @CRLF $sHelperFunc &= @TAB & 'Local $iSize = $aResult[5]' & @CRLF $sHelperFunc &= @TAB & 'Local $tOutput = DllStructCreate("byte[" & $iSize & "]")' & @CRLF $sHelperFunc &= @TAB & '; Perform decoding' & @CRLF $sHelperFunc &= @TAB & '$aResult = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryW", "wstr", $sB64String, "dword", StringLen($sB64String), "dword", 1, "struct*", $tOutput, "dword*", $iSize, "ptr", 0, "ptr", 0)' & @CRLF $sHelperFunc &= @TAB & 'If @error Or Not $aResult[0] Then Return SetError(3, 0, Binary(""))' & @CRLF $sHelperFunc &= @TAB & 'Return DllStructGetData($tOutput, 1)' & @CRLF $sHelperFunc &= 'EndFunc ;==>_Base64Decode' & @CRLF & @CRLF EndIf ; Add LZNT decompress function if needed If $bUseCompression And $iCompLevel > 0 Then Local $iEngine = ($iCompLevel = 2) ? 258 : 2 $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= '; LZNT Decompress Function (Engine: ' & $iEngine & ', Level: ' & $iCompLevel & ')' & @CRLF $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= 'Func _LZNT_Decompress($bCompressed)' & @CRLF $sHelperFunc &= @TAB & 'Local $tInput = DllStructCreate("byte[" & BinaryLen($bCompressed) & "]")' & @CRLF $sHelperFunc &= @TAB & 'DllStructSetData($tInput, 1, $bCompressed)' & @CRLF $sHelperFunc &= @TAB & 'Local $tOutput = DllStructCreate("byte[" & (BinaryLen($bCompressed) * 16) & "]")' & @CRLF $sHelperFunc &= @TAB & 'Local $aRet = DllCall("ntdll.dll", "int", "RtlDecompressBuffer", "ushort", ' & $iEngine & ', "ptr", DllStructGetPtr($tOutput), "dword", DllStructGetSize($tOutput), "ptr", DllStructGetPtr($tInput), "dword", DllStructGetSize($tInput), "dword*", 0)' & @CRLF $sHelperFunc &= @TAB & 'If @error Or $aRet[0] <> 0 Then Return SetError(1, 0, Binary(""))' & @CRLF $sHelperFunc &= @TAB & 'Local $tOut = DllStructCreate("byte[" & $aRet[6] & "]", DllStructGetPtr($tOutput))' & @CRLF $sHelperFunc &= @TAB & 'Return DllStructGetData($tOut, 1)' & @CRLF $sHelperFunc &= 'EndFunc ;==>_LZNT_Decompress' & @CRLF & @CRLF EndIf ; Add WriteBinaryFile helper function $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= '; Write Binary File Function' & @CRLF $sHelperFunc &= '; -------------------------------------------------------------------------------------------------' & @CRLF $sHelperFunc &= 'Func _WriteBinaryFile($sFilePath, $bBinaryData)' & @CRLF $sHelperFunc &= @TAB & 'If Not IsBinary($bBinaryData) Then Return SetError(1, 0, False)' & @CRLF $sHelperFunc &= @TAB & 'If BinaryLen($bBinaryData) = 0 Then Return SetError(2, 0, False)' & @CRLF $sHelperFunc &= @TAB & '; Remove existing file/folder' & @CRLF $sHelperFunc &= @TAB & 'If FileExists($sFilePath) Then' & @CRLF $sHelperFunc &= @TAB & @TAB & 'FileSetAttrib($sFilePath, "-RASH", 1)' & @CRLF $sHelperFunc &= @TAB & @TAB & 'DirRemove($sFilePath, 1)' & @CRLF $sHelperFunc &= @TAB & @TAB & 'FileDelete($sFilePath)' & @CRLF $sHelperFunc &= @TAB & 'EndIf' & @CRLF $sHelperFunc &= @TAB & '; Write binary data' & @CRLF $sHelperFunc &= @TAB & 'Local $hFile = FileOpen($sFilePath, 2 + 8 + 16) ; Write + Create + Binary' & @CRLF $sHelperFunc &= @TAB & 'If $hFile = -1 Then Return SetError(3, 0, False)' & @CRLF $sHelperFunc &= @TAB & 'FileWrite($hFile, $bBinaryData)' & @CRLF $sHelperFunc &= @TAB & 'FileClose($hFile)' & @CRLF $sHelperFunc &= @TAB & 'Return FileExists($sFilePath)' & @CRLF $sHelperFunc &= 'EndFunc ;==>_WriteBinaryFile' & @CRLF & @CRLF $sHelperFunc &= '; =================================================================' & @CRLF $sHelperFunc &= '; Helper function to get binary data by filename.' & @CRLF $sHelperFunc &= '; Usage: $bData = _GetBin("filename.ext")' & @CRLF $sHelperFunc &= '; Encoding: ' & ($bUseHex ? "Hex " : "") & ($bUseBase64 ? "Base64 " : "") & @CRLF $sHelperFunc &= '; Compression: ' & ($bUseCompression And $iCompLevel > 0 ? "LZNT Level " & $iCompLevel : "None") & @CRLF $sHelperFunc &= '; =================================================================' & @CRLF $sHelperFunc &= 'Func _GetBin($sName)' & @CRLF $sHelperFunc &= @TAB & 'Local $sData = ""' & @CRLF $sHelperFunc &= @TAB & 'Switch $sName' & @CRLF ; Generate Switch cases for each file For $i = 0 To UBound($aFiles) - 1 Local $sFileName = $aFiles[$i][1] Local $sFuncName = $aFiles[$i][4] $sHelperFunc &= @TAB & @TAB & 'Case "' & $sFileName & '"' & @CRLF $sHelperFunc &= @TAB & @TAB & @TAB & '$sData = ' & $sFuncName & '()' & @CRLF Next $sHelperFunc &= @TAB & 'EndSwitch' & @CRLF $sHelperFunc &= @CRLF $sHelperFunc &= @TAB & '; Decode from encoding format to binary' & @CRLF $sHelperFunc &= @TAB & 'If $sData = "" Then Return SetError(1, 0, Binary(""))' & @CRLF $sHelperFunc &= @TAB & 'Local $bData' & @CRLF If $bUseBase64 Then $sHelperFunc &= @TAB & '$bData = _Base64Decode($sData)' & @CRLF $sHelperFunc &= @TAB & 'If @error Then Return SetError(2, 0, Binary(""))' & @CRLF Else $sHelperFunc &= @TAB & '$bData = Binary($sData) ; Hex to binary' & @CRLF EndIf ; Add decompression if needed If $bUseCompression And $iCompLevel > 0 Then $sHelperFunc &= @CRLF & @TAB & '; Decompress the data' & @CRLF $sHelperFunc &= @TAB & '$bData = _LZNT_Decompress($bData)' & @CRLF $sHelperFunc &= @TAB & 'If @error Then Return SetError(3, 0, Binary(""))' & @CRLF EndIf $sHelperFunc &= @CRLF $sHelperFunc &= @TAB & 'Return $bData' & @CRLF $sHelperFunc &= 'EndFunc ;==>_GetBin' & @CRLF & @CRLF $sHelperFunc &= '; Example usage:' & @CRLF For $i = 0 To UBound($aFiles) - 1 Local $sFileName = $aFiles[$i][1] $sHelperFunc &= '; $bData = _GetBin("' & $sFileName & '")' & @CRLF $sHelperFunc &= '; _WriteBinaryFile(@TempDir & "\\' & $sFileName & '", $bData)' & @CRLF Next Return $sHelperFunc EndFunc ;==>_GenerateMasterHelperFunctionFromArray #EndRegion ; *** CORE CODE GENERATION *** #Region ; *** PE HEADER AND ARCHITECTURE DETECTION *** ; ------------------------------------------------------------------------------------------------- ; Function: _DetectArchitecture($sFilePath) ; Purpose: A wrapper that returns the architecture string for a file. ; ------------------------------------------------------------------------------------------------- Func _DetectArchitecture($sFilePath) Local $sArch = _DetectArchitecture_File($sFilePath) If @error Then Return "N/A" Return $sArch EndFunc ;==>_DetectArchitecture ; ------------------------------------------------------------------------------------------------- ; Function: _DetectArchitecture_File($sFilePath) ; Purpose: Reads a file's PE headers to identify the target CPU architecture. ; ------------------------------------------------------------------------------------------------- Func _DetectArchitecture_File($sFilePath) If Not FileExists($sFilePath) Then Return SetError(1, 0, "FILE_NOT_FOUND") Local $hFile = FileOpen($sFilePath, 16) If $hFile = -1 Then Return SetError(2, 0, "CANNOT_OPEN_FILE") Local $bDOSHeader = FileRead($hFile, 64) If @error Then FileClose($hFile) Return SetError(3, 0, "CANNOT_READ_DOS_HEADER") EndIf If BinaryMid($bDOSHeader, 1, 2) <> "0x4D5A" Then FileClose($hFile) Return "Not PE" EndIf Local $iPEOffset = _BinaryToInt(BinaryMid($bDOSHeader, 61, 4)) FileSetPos($hFile, $iPEOffset, $FILE_BEGIN) Local $bPESig = FileRead($hFile, 4) If @error Or $bPESig <> "0x50450000" Then FileClose($hFile) Return SetError(5, 0, "INVALID_PE_SIGNATURE") EndIf Local $bCOFF = FileRead($hFile, 2) FileClose($hFile) If @error Then Return SetError(6, 0, "CANNOT_READ_COFF_HEADER") Local $iMachine = _BinaryToInt($bCOFF) Switch $iMachine Case 0x014c Return "x86" Case 0x8664 Return "x64" Case 0x01c0, 0x01c4 Return "ARM" Case 0xAA64 Return "ARM64" Case 0x0200 Return "IA64" Case Else Return "UNKNOWN_0x" & Hex($iMachine, 4) EndSwitch EndFunc ;==>_DetectArchitecture_File ; ------------------------------------------------------------------------------------------------- ; Function: _BinaryToInt($bData) ; Purpose: Converts a little-endian binary string to an integer value. ; ------------------------------------------------------------------------------------------------- Func _BinaryToInt($bData) Local $iResult = 0 For $i = 1 To BinaryLen($bData) $iResult += Number(BinaryMid($bData, $i, 1)) * (256 ^ ($i - 1)) Next Return $iResult EndFunc ;==>_BinaryToInt #EndRegion ; *** PE HEADER AND ARCHITECTURE DETECTION *** #Region ; *** UTILITY FUNCTIONS *** ; ------------------------------------------------------------------------------------------------- ; Function: _SanitizeName($sInput) ; Purpose: Removes illegal characters from a string to make it a valid function name. ; ------------------------------------------------------------------------------------------------- Func _SanitizeName($sInput) Local $sCleaned = StringRegExpReplace($sInput, "[^a-zA-Z0-9_]", "") If StringLeft($sCleaned, 1) = "$" Then $sCleaned = StringTrimLeft($sCleaned, 1) Return $sCleaned EndFunc ;==>_SanitizeName ; ------------------------------------------------------------------------------------------------- ; Function: _GetFileName($sFilePath) ; Purpose: Extracts the filename and extension from a full path. ; ------------------------------------------------------------------------------------------------- Func _GetFileName($sFilePath) Return StringRegExpReplace($sFilePath, "^.*\\", "") EndFunc ;==>_GetFileName ; ------------------------------------------------------------------------------------------------- ; Function: _FormatFileSize($iBytes) ; Purpose: Converts a file size in bytes into a human-readable string (KB, MB, GB). ; ------------------------------------------------------------------------------------------------- Func _FormatFileSize($iBytes) If $iBytes < 1024 Then Return $iBytes & " B" ElseIf $iBytes < 1048576 Then Return Round($iBytes / 1024, 1) & " KB" ElseIf $iBytes < 1073741824 Then Return Round($iBytes / 1048576, 2) & " MB" Else Return Round($iBytes / 1073741824, 2) & " GB" EndIf EndFunc ;==>_FormatFileSize ; ------------------------------------------------------------------------------------------------- ; Function: _ValidateChunkSize($iChunkSize) ; Purpose: Ensures the chunk size is within a valid range. ; ------------------------------------------------------------------------------------------------- Func _ValidateChunkSize($iChunkSize) ; First, check if the input from the GUI is a string containing only digits. If Not StringIsDigit($iChunkSize) Then Return 4000 ; If not, it's invalid, return the default value. EndIf ; If it is a digit string, convert it to a real number. Local $nChunkSize = Number($iChunkSize) If ($iChunkSize < 100) Or ($iChunkSize > 4000) Then Return 4000 EndIf Return Int($iChunkSize) EndFunc ;==>_ValidateChunkSize ; ------------------------------------------------------------------------------------------------- ; Function: _SaveStringToFile($sFilePath, $sContent) ; Purpose: A robust function to save a string to a file. ; Returns: True on success, False on failure. ; ------------------------------------------------------------------------------------------------- Func _SaveStringToFile($sFilePath, $sContent) Local $hFile = FileOpen($sFilePath, 2) If $hFile = -1 Then Return False Local $bSuccess = FileWrite($hFile, $sContent) FileClose($hFile) Return $bSuccess EndFunc ;==>_SaveStringToFile Func _LZNT_Compress($bInput, $iOrigSize = 16, $iEngine = 258, $bBase64 = False, $iLineLen = 1024) $bInput = Binary($bInput) If (BinaryLen($bInput) < 1) Then Return SetError(-1, 0, "") If $iEngine <> 2 And $iEngine <> 258 Then $iEngine = 258 Local $tInput = DllStructCreate("byte[" & BinaryLen($bInput) & "]") DllStructSetData($tInput, 1, $bInput) Local $aCall = DllCall("ntdll.dll", "int", "RtlGetCompressionWorkSpaceSize", _ "ushort", $iEngine, "dword*", 0, "dword*", 0) If @error Or $aCall[0] Then Return SetError(1, 0, "") Local $tWork = DllStructCreate("byte[" & $aCall[2] & "]") If ($iOrigSize < 1) Then $iOrigSize = 16 Local $iLen = $iOrigSize * DllStructGetSize($tInput) Local $tBuffer = DllStructCreate("byte[" & $iLen & "]") $aCall = DllCall("ntdll.dll", "int", "RtlCompressBuffer", _ "ushort", $iEngine, _ "ptr", DllStructGetPtr($tInput), "dword", DllStructGetSize($tInput), _ "ptr", DllStructGetPtr($tBuffer), "dword", DllStructGetSize($tBuffer), _ "dword", 4096, "dword*", 0, "ptr", DllStructGetPtr($tWork)) If @error Or $aCall[0] Then Return SetError(2, 0, "") Local $tOut = DllStructCreate("byte[" & $aCall[7] & "]", DllStructGetPtr($tBuffer)) Local $bOut = DllStructGetData($tOut, 1) If $bBase64 Then Return SetError(0, DllStructGetSize($tInput), _Base64Encode($bOut, $iLineLen)) Return SetError(0, DllStructGetSize($tInput), $bOut) EndFunc ;==>_LZNT_Compress Func _LZNT_Decompress($vInput, $iOrigSize = 16, $iEngine = 258, $bBase64 = False) Local $bInput If $bBase64 Then $bInput = _Base64Decode($vInput) Else $bInput = $vInput EndIf $bInput = Binary($bInput) If (BinaryLen($bInput) < 1) Then Return SetError(-1, 0, "") If $iEngine <> 2 And $iEngine <> 258 Then $iEngine = 258 Local $tInput = DllStructCreate("byte[" & BinaryLen($bInput) & "]") DllStructSetData($tInput, 1, $bInput) If ($iOrigSize < 1) Then $iOrigSize = 16 Local $iLen = $iOrigSize * DllStructGetSize($tInput) Local $tBuffer = DllStructCreate("byte[" & $iLen & "]") Local $aCall = DllCall("ntdll.dll", "int", "RtlDecompressBuffer", _ "ushort", $iEngine, _ "ptr", DllStructGetPtr($tBuffer), "dword", DllStructGetSize($tBuffer), _ "ptr", DllStructGetPtr($tInput), "dword", DllStructGetSize($tInput), _ "dword*", 0) If @error Or $aCall[0] Then Return SetError(1, 0, "") Local $tOut = DllStructCreate("byte[" & $aCall[6] & "]", DllStructGetPtr($tBuffer)) Return SetError(0, $aCall[6], DllStructGetData($tOut, 1)) EndFunc ;==>_LZNT_Decompress Func _LZNT_CompressStr($sInput, $iOrigSize = 16, $iEncoding = 4, $iEngine = 2, $bBase64 = False, $iLineLen = 1024) Local $bData = StringToBinary($sInput, $iEncoding) Local $sReturn = _LZNT_Compress($bData, $iOrigSize, $iEngine, $bBase64, $iLineLen) Return SetError(@error, @extended, $sReturn) EndFunc ;==>_LZNT_CompressStr Func _LZNT_DecompressStr($vInput, $iOrigSize = 16, $iEncoding = 4, $iEngine = 2, $bBase64 = False) Local $bData = _LZNT_Decompress($vInput, $iOrigSize, $iEngine, $bBase64) If @error Then Return SetError(1, 0, "") Return BinaryToString($bData, $iEncoding) EndFunc ;==>_LZNT_DecompressStr Func _Base64Encode($bData, $iLineLen = 0) If ($iLineLen < 1) Then $iLineLen = 0 $bData = Binary($bData) Local $tInput = DllStructCreate("byte[" & BinaryLen($bData) & "]") DllStructSetData($tInput, 1, $bData) Local $iFlags = 0x40000001 ; CRYPT_STRING_BASE64 | CRYPT_STRING_NOCRLF ; Get required buffer size Local $aResult = DllCall("Crypt32.dll", "bool", "CryptBinaryToStringW", _ "struct*", $tInput, _ "dword", DllStructGetSize($tInput), _ "dword", $iFlags, _ "ptr", 0, _ "dword*", 0) If @error Or Not $aResult[0] Then Return SetError(1, 0, "") Local $iSize = $aResult[5] Local $tOutput = DllStructCreate("wchar[" & $iSize & "]") ; Perform encoding $aResult = DllCall("Crypt32.dll", "bool", "CryptBinaryToStringW", _ "struct*", $tInput, _ "dword", DllStructGetSize($tInput), _ "dword", $iFlags, _ "struct*", $tOutput, _ "dword*", $iSize) If @error Or Not $aResult[0] Then Return SetError(2, 0, "") Local $sOut = DllStructGetData($tOutput, 1) ; Manual wrap for embedding in AutoIt source If ($iLineLen > 0) And (StringLen($sOut) > $iLineLen) Then Local $sWrapped = "" For $i = 1 To StringLen($sOut) Step $iLineLen $sWrapped &= StringMid($sOut, $i, $iLineLen) & @CRLF Next $sOut = StringTrimRight($sWrapped, 2) EndIf Return $sOut EndFunc ;==>_Base64Encode Func _Base64EncodeStr($sInput, $iLineLen = 0, $iEncodeType = 4) If ($iLineLen < 1) Then $iLineLen = 0 If ($iEncodeType > 4) Or ($iEncodeType < 1) Then $iEncodeType = 4 Local $bBinary = StringToBinary($sInput, $iEncodeType) Local $sReturn = _Base64Encode($bBinary, $iLineLen) Return SetError(@error, @extended, $sReturn) EndFunc ;==>_Base64EncodeStr Func _Base64Decode($sInput, $bReturnType = 0) If ($bReturnType > 4) Or ($bReturnType < 1) Then $bReturnType = 0 ; Remove all whitespace and CRLF $sInput = StringRegExpReplace($sInput, "\s", "") If $sInput = "" Then Return SetError(1, 0, Binary("")) Local $iFlags = 0x1 ; CRYPT_STRING_BASE64 ; Get required buffer size Local $aResult = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryW", _ "wstr", $sInput, _ "dword", StringLen($sInput), _ "dword", $iFlags, _ "ptr", 0, _ "dword*", 0, _ "ptr", 0, _ "ptr", 0) If @error Or Not $aResult[0] Then Return SetError(2, 0, Binary("")) Local $iSize = $aResult[5] Local $tOutput = DllStructCreate("byte[" & $iSize & "]") ; Perform decoding $aResult = DllCall("Crypt32.dll", "bool", "CryptStringToBinaryW", _ "wstr", $sInput, _ "dword", StringLen($sInput), _ "dword", $iFlags, _ "struct*", $tOutput, _ "dword*", $iSize, _ "ptr", 0, _ "ptr", 0) If @error Or Not $aResult[0] Then Return SetError(3, 0, Binary("")) Local $bBinary = DllStructGetData($tOutput, 1) If ($bReturnType = 0) Then Return $bBinary Else ; Convert binary to string with specified encoding Return BinaryToString($bBinary, $bReturnType) EndIf EndFunc ;==>_Base64Decode Func _Base64DecodeStr($sInput, $iDecodeType = 4) Local $sReturn = _Base64Decode($sInput, $iDecodeType) Return SetError(@error, @extended, $sReturn) EndFunc ;==>_Base64DecodeStr #EndRegion ; *** UTILITY FUNCTIONS ***
    1 point
  35. @Nine I was doing some testing with your WCD IPC UDF and I was very impressed with it. It really is quite simple yet such a genius idea and very efficient as well. Testing with your scripts worked perfectly. But it didn't work when I integrated it into my script. Is it possible that it didn't work with my script because my script is already a GUI script? I checked with System Informer and there wasn't a window titled "WCDServer". It would've shown there whether it was hidden or not. EDIT: I figured out the problem. I was using _WinAPI_SetWindowText to set the title for the AutoIt window specifically but it was changing the title from "WCDServer" to the other title that I was using previously. This is something that I can work around. Your UDF is the perfect solution to my problem. Thank you.
    1 point
  36. Actually, maybe this would be better... Case $WM_DESTROY _WinAPI_RemoveWindowSubclass($hwnd, $pWndProc, $iIdSubclass) $iRet = _WinAPI_DefSubclassProc($hwnd, $iMsg, $wParam, $lParam) And we must do this before exiting. GUIDelete($Guiscape.Canvas.Hwnd)
    1 point
  37. Perhaps add this to WndProc? - it should allow you exit cleanly Case $WM_DESTROY _WinAPI_RemoveWindowSubclass($hwnd, $pWndProc, $iIdSubclass) GUIDelete($hWnd)
    1 point
  38. Check it out! https://github.com/matthewrg/Guiscape
    1 point
  39. You're probably missing the proper vc_redist dll's since you're on such old OS. https://learn.microsoft.com/en-us/cpp/windows/latest-supported-vc-redist?view=msvc-170
    1 point
  40. First, I pared down the script to the essentials: For $i = 1 To 20 ; create new(!) map, add one element to the string index "c" (which calculated position in the internal list is index 8) Global $m1[] $m1["c"] = 1 ; check if there`s a value at the index 8 (shouldn`t) If $m1[8] Then ConsoleWrite($m1[8] & @CRLF) ; create another map and add value at the same integer index as the one $m1 checked Global $m2[] $m2[8] = 1 Next I made the following observations: 1. It does not occur with all string indexes, but only with some. It is noticeable that each string index has a fixed associated integer index. If you use a different integer index, the phenomenon does not occur. So far, I have found the following combinations in which the phenomenon occurs: | String-Index | Integer-Index | | ------------ | ------------- | | "[" | 0 | | "<" | 1 | | "" | 5 | | "c" | 8 | | "D" | 9 | | "%" | 10 | | "k" | 16 | | "L" | 17 | | "-" | 18 | | "s" | 24 | | "T" | 25 | | "{" | 32 | | "\" | 33 | | "=" | 34 | These relationships can be explained well using hash index collisions. AutoIt uses the DJB2 hash function in its maps. If you use this for the letters and then scale it to the table size using modulo, you get exactly the corresponding integer indices. Only the table size is obviously not fixed, as the index sometimes fits for 32 elements and sometimes for 64. For example: โ€œcโ€ has a DJB2 hash value of 177672. If we assume that the map in AutoIt has 32 elements at that point, the index for โ€œcโ€ is calculated as 177672 % 32 = 8. This also works for the other string indexes. E.g., โ€œDโ€ --> 177641 % 32 = 9 or โ€œโ€ --> 5381 % 32 = 5. Only the size of the hash table is obviously variable, as some fit for a size of 32 elements and some for 64. However, thanks to the bug, we can learn a lot about the internal structure of AutoIt maps. They are DJB2-based hash tables that start with 32 or 64 elements. 2. This behavior only occurs when the map $m2 is created and an element is created with the same integer index as in $m1. If only this index is set, a match is reported very often. If other indexes are also set, the match does not occur as frequently. One possible explanation for this behavior is as follows: A hash table is essentially an array with a specific size. This size is fundamentally independent of the number of elements it contains (resizing makes sense but is not mandatory). In this case, a map is obviously initially populated with either 32 or 64 elements. When a value is added to the hash table, the hash value of the key is calculated and this calculated value is mapped to the array size using modulo. If the key is โ€œcโ€, for example, the DJB2 hash (the hash algorithm used in AutoIt) is 177672. To obtain an index for our array in the map, we have to reduce this hash value to the range 32 or 64. This is easy to do using the modulo operator. And with 177672 % 32, we get 8 as the result. The value for the key โ€œcโ€ is therefore stored in the internal array at index 8. However, since several keys could end up at index 8, we need to create a way to hold multiple elements there. For each index, a list is created (a โ€œbucketโ€) that contains all elements whose key matches this index. The key and value of these elements are then simply stored one after the other in the bucket itself. When a value is queried, the index is first calculated and then this bucket is traversed linearly to see if the specific key is contained in it. In AutoIt, these buckets do not necessarily seem to be used only by one map instance. At some point, two maps share a bucket, resulting in a phenomenon like the one we see here. So you would have to take a closer look at the initialization of the map to see exactly where the problem lies.
    1 point
  41. Look at my Fast and simple WCD IPC. It is working well between processes with different levels of privilege.
    1 point
  42. I'm taking the hi word, that's not the same as $hwnd? Let me test it ... :forehead smack: Durrrrr .... thank you!
    1 point
  43. looks like a malformed window handle to me... around about line 70: GUICtrlSendToDummy($dummy, _WinAPI_MakeLong($NC_CLICKED, $hwnd)) so you're sending part of a window handle (the hi word part), and a in the lo work you have $NC_CLICKED.
    1 point
  44. ...If, there are very many distributed workloads and the "master" overwhelmed itself, then you see what you just witnessed. All this is painfully stupid. More bandwidth than brains. Idea: we should offer torrents ( in a throttle ). With a bit of luck they can feed each other the files ๐Ÿคช
    1 point
  45. The wrapper I put together ( @trancexx's code ) works just fine in 32 and 64 bit. I have not seen it fail.
    1 point
  46. Nine

    Delayed MouseClick()

    If you're running this script in a loop, then you are not leaving enough time to the last click to complete.
    1 point
  47. This is a UDF to use a Listview or Treeview as a File/Folder Explorer. You can also fine the TreeListExplorer UDF on Github. It allows to create a system, where a root folder can be set and that synchronizes all attached Tree or Listviews. So it is possible to attach multiple views to one system. Additionally, it is possible to add an Input Control as a View to show the current folder. When pressing {ENTER}, the system opens the path provided by the input. The following functions are available: ; #CURRENT# ===================================================================================================================== ; __TreeListExplorer_StartUp ; __TreeListExplorer_Shutdown ; __TreeListExplorer_CreateSystem ; __TreeListExplorer_DeleteSystem ; __TreeListExplorer_AddView ; __TreeListExplorer_RemoveView ; __TreeListExplorer_OpenPath ; __TreeListExplorer_Reload ; __TreeListExplorer_GetPath ; __TreeListExplorer_GetRoot ; __TreeListExplorer_GetSelected ; __TreeListExplorer_SetRoot ; =============================================================================================================================== When creating a System, a callback function can be provided to be called, when the root folder or the current folder changes. When adding a View, callback functions for single/double click at an item as well as a loading callback can be added. Example view: The Code for the Example to get a quick overview: If you like it, please leave me a comment, also if you have any suggestions to make it better or if you found bugs. I did a complete rework of this UDF (2025/03/02). Now it is easier to use and does not need external UDFs anymore. This also removes a lot of bugs, that were in the old version. It is also possible to freely select if folders and/or files should be visible in any view. Changelog: Version 1.0.0 (Old Version) Version 2.0.0 (New Version after rework) Version 2.1.0 - Rename $sCallbackOnSelect to $sCallbackOnClick - Add an additional callback $sCallbackOnSelectionChange, that is called whenever the Tree-/ListView item selection changes Version 2.2.0 - Improve loading speed for TreeView folders when expanding Version 2.3.0 - Fix some bugs where folders did not correctly expand/collapse when clicking them (when the root folder is not "" => shows all drives) - Fix some documentation - Add a method for reloading (__TreeListExplorer_Reload) the current folder (ListView/TreeView) or all folders (TreeView) - Remove the reload parameter from the __TreeListExplorer_OpenPath method (Replaced with __TreeListExplorer_Reload). - Other small internal changes Version 2.4.0 - Add the possibility to handle file/folder selections better - Files/Folders keep selected when reloading - The currently selected File/Folder can be checked with __TreeListExplorer_GetSelected - File selection is synchronized between all Tree-/Listviews, Folder selection only between ListViews (TreeView folder selection changes the current folder and expands it) - fixed minor issues Version 2.5.0 - Disabled TreeList expand with a single click and changed it to a double click - Selection is now synchronized for all files/folders between all views (Tree-/ListView) - The Selection callback is now moved from __TreeListExplorer_AddView to __TreeListExplorer_CreateSystem and only fires ones per change for the system and not for every view (as it was before) - All callbacks were changed to pass the selected folder and some additional information is now provided (clicked index/item, the loading path,...) - Small performance improvements - Some internal restructuring Version 2.5.1 - Fixed: selection not working for drives Version 2.6.0 - Added support for icons of all file extensions for TreeViews and ListViews. Version 2.7.0 - Input controls are now possible as a view. They show the current folder and when pressing {ENTER} inside, the system tries to open the path show in the input. - Changed the behavior of the treeview when clicking items. They now change the current folder, but are not expanded. This changes the folder in the ListView, when clicking a folder in the TreeView. Version 2.7.1 - Clicking on the Bitmap of a TreeView item is now registered as a click (not just the text like before) - Fixed a missing selection update when clicking on a TreeView item Version 2.7.2 - Add parameter for setting the (file-/folder-)icon size on startup Version 2.8.0 - TreeView selection is now triggering the select event and the $sSelect corresponds to the selected folder/file. NOTE: __TreeViewExplorer_GetSelected will be empty, if the selection is a folder in a treeview - Selection handling was improved, especially the synchronization between TreeView and ListView - Add keyboard navigation to the listview - Fixed a bug, where the icon index was sent as event (GuIGetMsg), when an item was clicked (happens without the udf message handling, so it needed a workaround: suppress the default autoit handler for mouseclicks) Version 2.8.1 - Fixed a bug, where the select callback was sometimes not send correctly Version 2.9.0 - Fixed bug for TreeViews, where folders were shown as expandable, when having only files but no folders, even if showing files was turned of - rework how treeviews are filled/updated/expanded (folders that are expanded will stay expanded on reload) - add the possibility to set a depth limit for the treeview (Example: Drive selection with $sRoot="" and $iMaxDepth=0) - Fixed bug for Arrow selection in the ListView to not trigger a click event anymore - When the open folder or the selection changed, the TreeView checks, if it still exists (=> treeview updates, if a folder was deleted) Version 2.9.1 - Workaround for a Bug in the GuiTreeView UDF (until it is fixed), causing random control deletions instead of TreeView item deletions Version 2.9.3 - Fixed custom icon size when extracting icons Version 2.9.4 - Improved display quality for some icons (Thanks WildByDesign for the work on that) - Fixed an issue, where cached file icons for individual files were shown as a folder Version 2.9.5 - Improved display quality for some icons (When resource files are defined in the registry, the one with the size greater or equal to the required icon size will be choosen) Version 2.10.0 - Added the possibility to filter ListViews/TreeViews with a callback function. This callbackfunction is called for every file/folder and only if it returns True, will they be added to the view. - Added the possibility to set $bNavigate for ListViews when adding them. This enables or disables the possibility to navigate through folders with doubleclicks in a ListView (and add/removes the ".." folder at the top, which enables the user to navigate to the parent folder) Version 2.10.1 - Added the WinAPIConstants.au3 include to fix missing constants due to changes with the new AutoIt-Version (v3.3.18.0) Special thanks to @WildByDesign for a lot of testing to help improving this UDF. TreeListExplorer.au3 TreeListExplorer-Example.au3
    1 point
  48. I have already posted the script in the German forum, but I would like to make it available here as well. Highlighting the active tab item in SciTE Individual: Frame color Text color Background color Text color if not saved Marker "Inactive item unsaved" Marker position "Inactive item unsaved" optionally 'top' / 'bottom' / 'none' Active item marking can be deactivated (if only unsaved marking is desired). The active item then receives the same marking as the inactive item when "unsaved". Colors can be loaded as a scheme via INI The compiled script can be ended with CMDLine parameter "/Exit". Since Windows 10, the windows have a very "flat" look. One of the consequences of this is that it is not immediately apparent which item is active in a Tab-Ctrl. When programming in SciTE, I usually have many tabs open at the same time. To make the active tab more visible, I draw it with a colored frame. In addition, unsaved tabs are marked separately with coloring of the top or bottom edge. The colors used for this can be stored individually as a scheme in an INI file. Some schemes are predefined at the beginning of the script. Just try out what you like best. I start the script via the autostart folder when Windows starts. Here are a few pictures: Active Tab Active Tab, unsaved Active Tab, BG: blue / Text: white ... BG: green / Text: white Active Tab, left & right idle unsaved Tabs Active Tab unsaved too ;-- TIME_STAMP 2023-03-23 10:16:34 v 0.5 #cs v 0.5 [fixed] Flickering, a variable assignment was incorrect [fixed] Marking has failed by using keys ("F6", "Shift+F6") to change the buffer selection v 0.4 [added] Exit via CMDLine with parameter "/Exit" [added] Optionally adjustable via INI [appearance]: - Mark active item: rect_highlight=true/false - Position of the marker for "Inactive item unsaved": idlepos=top/bottom/none v 0.3 [added] Separate marker (colored line top) for "Inactive item unsaved". v 0.2 [added] Separate marking (text color) for unsaved files. [added] Loading of colors from an INI (color schemes) possible #ce #include <FontConstants.au3> #include <GuiTab.au3> #include <Misc.au3> #include <WinAPIGdi.au3> #include <WinAPISys.au3> #include <WinAPIMisc.au3> #include <WindowsConstants.au3> Opt('TrayIconHide', 1) If $CMDLINE[0] And $CMDLINE[1] = '/Exit' Then ; CMD-Line: "@ScriptName.exe /Exit" Local $aProcessList = ProcessList(@ScriptName) For $i = 1 To $aProcessList[0][0] Step 1 If $aProcessList[$i][1] <> @AutoItPID Then ProcessClose($aProcessList[$i][1]) Next EndIf _Singleton(@ScriptName) ;~ HotKeySet("!{F8}", _End) ; <Alt><F8> Beenden OnAutoItExitRegister(_End) Global $sINI = StringFormat("%s\%s.ini", @ScriptDir, StringTrimRight(@ScriptName, 4)) Global $gm_SciTE[] $gm_SciTE.ExistsLast = 0 $gm_SciTE.ExistsCurr = 0 #cs The colors can be defined in an INI file in the script folder. If INI is not available, default colors are loaded. INI-Name = Name_of_the_Exe.ini [appearance] ; rect_highlight=true/false "false" does NOT highlight the active item, default: "true". rect_highlight=true ; idlepos=top/bottom/none "none" does NOT mark unsaved inactive files, default: "top". idlepos=top [scheme] ; Specify which of the defined schemes should be active. current=default ; One section for each scheme. [default] rect=0xCC483F text=0x800020 bg=0xFFFFFF unsaved=0x3030FF idle=0x3030FF [blue_invers] rect=0xCC483F text=0xFFF0F0 bg=0x800020 unsaved=0xA9A5F7 idle=0xA9A5F7 [green_invers] rect=0x005F00 text=0xEDFFED bg=0x409340 unsaved=0x1DE6B5 idle=0x1DE6B5 #ce ; appearance $gm_SciTE.bHighlight = (_IniOrDefault($sINI, 'rect_highlight', 'true', 'appearance') = 'true') $gm_SciTE.IdlePos = _IniOrDefault($sINI, 'idlepos', 'top', 'appearance') ; scheme: default (blue): $gm_SciTE.RectColor = _IniOrDefault($sINI, 'rect' , 0xCC483F) ; BGR $gm_SciTE.TextColor = _IniOrDefault($sINI, 'text' , 0x800020) ; BGR $gm_SciTE.BGColor = _IniOrDefault($sINI, 'bg' , 0xFFFFFF) ; BGR $gm_SciTE.TextColorUnsaved = _IniOrDefault($sINI, 'unsaved', 0x3030FF) ; BGR $gm_SciTE.IdleUnsaved = _IniOrDefault($sINI, 'idle' , 0x3030FF) ; BGR _CheckSciTE() ; the effect takes place immediately AdlibRegister(_CheckSciTE, 750) While True Sleep(5000) WEnd Func _End() AdlibUnRegister(_CheckSciTE) ;~ MsgBox(0, 'SciTE TabItem', 'Beendet!') Exit EndFunc Func _CheckSciTE() If ProcessExists("SciTE.exe") Then $gm_SciTE.ExistsCurr = 1 If $gm_SciTE.ExistsLast = 0 Then $gm_SciTE.ExistsLast = 1 If $gm_SciTE.bHighlight Then _DrawTabItem() AdlibRegister(_MouseHoversTab, 150) EndIf _MarkUnsavedIdleTab() Else $gm_SciTE.ExistsCurr = 0 If $gm_SciTE.ExistsLast = 1 Then $gm_SciTE.ExistsLast = 0 If $gm_SciTE.bHighlight Then AdlibUnRegister(_MouseHoversTab) EndIf EndIf EndFunc Func _MouseHoversTab() Local Static $iHoverLast = 1 ; when starting the program, exit from the item must be simulated Local $mTab = _SciTE_GetActiveTabInfo() If @error Then Return Local $tPoint = _WinAPI_GetMousePos(True, $mTab.hTab) Local $tRect = $mTab.RectItem Local $isHover = _WinAPI_PtInRect($tRect, $tPoint) If $isHover = 1 And $iHoverLast = 0 Then $iHoverLast = 1 ElseIf $isHover = 0 And $iHoverLast = 1 Then $iHoverLast = 0 Return _DrawTabItem() EndIf EndFunc Func _MarkUnsavedIdleTab() If $gm_SciTE.IdlePos = 'none' Then Return Local $hTab = __GetHwnd_SciTeTabCtrl() If @error Then Return SetError(1) Local $iActive = _GUICtrlTab_GetCurFocus($hTab) For $i = 0 To _GUICtrlTab_GetItemCount($hTab) -1 If $i = $iActive And $gm_SciTE.bHighlight Then ContinueLoop If StringRight(_GUICtrlTab_GetItemText($hTab, $i), 1) = '*' Then _DrawMarkerUnsaved($hTab, $i) EndIf Next EndFunc Func _DrawMarkerUnsaved($_hTab, $_iItem) Local $tRect = _GUICtrlTab_GetItemRectEx($_hTab, $_iItem) Local $tRectDraw = DllStructCreate("struct; long Left;long Top;long Right;long Bottom; endstruct") If $gm_SciTE.IdlePos = 'top' Then $tRectDraw.Left = $tRect.Left $tRectDraw.Top = $tRect.Top -1 $tRectDraw.Right = $tRect.Right $tRectDraw.Bottom = $tRect.Top Else $tRectDraw.Left = $tRect.Left $tRectDraw.Top = $tRect.Bottom +2 $tRectDraw.Right = $tRect.Right $tRectDraw.Bottom = $tRect.Bottom +3 EndIf Local $hDC = _WinAPI_GetDC($_hTab) Local $hPen = _WinAPI_CreatePen($PS_SOLID, 2, $gm_SciTE.IdleUnsaved) Local $hOldPen = _WinAPI_SelectObject($hDC, $hPen) _WinAPI_Rectangle($hDC, $tRectDraw) _WinAPI_SelectObject($hDC, $hOldPen) _WinAPI_DeleteObject($hPen) _WinAPI_ReleaseDC(0, $hDC) EndFunc Func _DrawTabItem() Local $mTab = _SciTE_GetActiveTabInfo() If @error Then Return Local $hDC = _WinAPI_GetDC($mTab.hTab) Local $hFont = _WinAPI_CreateFont(14.5, 0, 0, 0, 400, False, False, False, $DEFAULT_CHARSET, _ $OUT_DEFAULT_PRECIS, $CLIP_DEFAULT_PRECIS, $DEFAULT_QUALITY, 0, 'Lucida Sans Unicode Standard') Local $hOldFont = _WinAPI_SelectObject($hDC, $hFont) Local $tRect = $mTab.RectItem ; extract to variable - otherwise no ByRef access possible Local $dY = (@OSVersion = "Win_7" ? 2 : 1) _WinAPI_InflateRect($tRect, 2, $dY) ; enlarge rectangle _WinAPI_OffsetRect($tRect, 0, 1) ; move rectangle down by 1px ; draw and fill rect Local $hPen = _WinAPI_CreatePen($PS_SOLID, 2, $gm_SciTE.RectColor) Local $hBrush = _WinAPI_CreateSolidBrush($gm_SciTE.BGColor) Local $hOldPen = _WinAPI_SelectObject($hDC, $hPen) Local $hOldBrush = _WinAPI_SelectObject($hDC, $hBrush) _WinAPI_Rectangle($hDC, $tRECT) ; draw text If StringRight($mTab.Item, 1) = '*' Then _WinAPI_SetTextColor($hDC, $gm_SciTE.TextColorUnsaved) Else _WinAPI_SetTextColor($hDC, $gm_SciTE.TextColor) EndIf _WinAPI_SetBkColor($hDC, $gm_SciTE.BGColor) ; move the text down a bit more _WinAPI_OffsetRect($tRect, 0, 3) _WinAPI_DrawText($hDC, $mTab.Item, $tRect, BitOR($DT_BOTTOM,$DT_CENTER)) ; clear ressources _WinAPI_SelectObject($hDC, $hOldFont) _WinAPI_DeleteObject($hFont) _WinAPI_SelectObject($hDC, $hOldPen) _WinAPI_DeleteObject($hPen) _WinAPI_SelectObject($hDC, $hOldBrush) _WinAPI_DeleteObject($hBrush) _WinAPI_ReleaseDC(0, $hDC) EndFunc Func _SciTE_GetActiveTabInfo() Local $mResult[], $hTab = __GetHwnd_SciTeTabCtrl() If @error Then Return SetError(1) $mResult.hTab = $hTab $mResult.Index = _GUICtrlTab_GetCurFocus($hTab) $mResult.Item = _GUICtrlTab_GetItemText($hTab, $mResult.Index) $mResult.RectItem = _GUICtrlTab_GetItemRectEx($hTab, $mResult.Index) Return $mResult EndFunc Func __GetHwnd_SciTE() Local $hScite = WinGetHandle('[ACTIVE]') If _WinAPI_GetClassName($hScite) = 'SciTEWindow' Then Return $hScite Else Return SetError(1, 0, Null) EndIf EndFunc Func __GetHwnd_SciTeTabCtrl() Local $hScite = __GetHwnd_SciTE() If @error Then Return SetError(1, 0, Null) Local $aChild, $hWndTab = Null $aChild = _WinAPI_EnumChildWindows($hScite) ; only visible If Not @error Then For $i = 1 To $aChild[0][0] If $aChild[$i][1] = "SciTeTabCtrl" Then $hWndTab = $aChild[$i][0] ExitLoop EndIf Next EndIf Return SetError(($hWndTab = Null ? 1 : 0), 0, $hWndTab) EndFunc ; read from INI if exists Func _IniOrDefault($_sINI, $_sKey, $_sDefault, $_sec=Null) Local $sVal = $_sDefault, $sSec = $_sec = Null ? 'scheme' : $_sec If FileExists($_sINI) Then If $sSec = 'scheme' Then $sSec = IniRead($_sINI, 'scheme', 'current', 'default') $sVal = IniRead($_sINI, $sSec, $_sKey, $_sDefault) EndIf Return $sVal EndFunc SciTE_DrawTabItem.au3
    1 point
  49. twitchyliquid64

    Proxy Checker

    Scans a textfile (@ScriptDir & "/proxylist.txt") for addresses and checks to see if the proxy at that address still works. Addresses in this file are placed in the format <ipaddress>:<port> and addresses are separated by lines. Credit to Zatorg - his Asynchronous sockets UDF is used (included) #include <GUIConstantsEx.au3> #include <file.au3> #include <array.au3> #Include <GuiListView.au3> Opt("GUIOnEventMode", 1) global $PROXY_LIST[1][5] TCPStartup() Global $hWs2_32 = -1 ;Create the GUI $win = GUICreate( "Proxy Scanner", 400, 400) GUISetOnEvent($GUI_EVENT_CLOSE, "CLOSEClicked") $list = GUICtrlCreateListView( "# | IP | Port | Status", 10, 10, 380, 330) Readin_Proxies() GUISetState() Global Const $__TCP_WINDOW = GUICreate("Async Sockets UDF") ;Set the status of each proxy. For $x = 0 to UBound($PROXY_LIST)-2 step 1 Test_Connection( $x) Sleep(100) Next While 1 Sleep(20) WEnd Func CLOSEClicked() Exit EndFunc Func Readin_Proxies() ProgressOn( "Proxy Scanner", "Loading...Please Wait.", "populating lists...") local $linecount = _FileCountLines( @ScriptDir & "/proxylist.txt") ReDim $PROXY_LIST[$linecount][5] $filehnd = FileOpen( @ScriptDir & "/proxylist.txt") For $x = 0 to $linecount step 1 ProgressSet( ($x/$linecount)*100) $Line = "" While 1 ;Collect the entire line into a variable. $character = FileRead( $filehnd, 1) if @error = -1 then ExitLoop 2 if $character = @CR Then ExitLoop if $character = @LF then ContinueLoop $Line &= $character WEnd $spl = StringSplit( $Line, ":", 1) $PROXY_LIST[$x][0] = $spl[1] if $spl[0] >= 2 Then $PROXY_LIST[$x][1] = $spl[2] Else $PROXY_LIST[$x][1] = 80 EndIf $PROXY_LIST[$x][2] = GUICtrlCreateListViewItem( $x&"|"&$spl[1]&"|"&$PROXY_LIST[$x][1]&"|Unknown", $list) GUICtrlSetBkColor( $PROXY_LIST[$x][2], 0xFFFFAA) Next FileClose( $filehnd) ProgressOff() EndFunc Func Test_Connection( $arrayslot) local $SocketID = ___ASocket() ___ASockSelect( $SocketID, $__TCP_WINDOW, 0x401 + $arrayslot, BitOR( 1, 2, 16, 32)) GUIRegisterMsg( 0x401 + $arrayslot, "Opensocket_data_" ) ___ASockConnect( $SocketID, $PROXY_LIST[$arrayslot][0], $PROXY_LIST[$arrayslot][1]) $PROXY_LIST[$arrayslot][3] = $SocketID EndFunc Func Opensocket_data_( $hWnd, $iMsgID, $WParam, $LParam ) Local $iError = ___HiWord( $LParam ) Local $iEvent = ___LoWord( $LParam ) Abs($hWnd) local $Array_Slot = $iMsgID-0x0401 ;No more loops to slow down message delievery! local $x = $Array_Slot Switch $iEvent Case 16 If $iError Then ;FAILED CONNECTION GUICtrlSetData( $PROXY_LIST[$x][2], $x&"|"&$PROXY_LIST[$x][0]&"|"&$PROXY_LIST[$x][1]&"|OFFLINE") GUICtrlSetBkColor( $PROXY_LIST[$x][2], 0xEEEEAA) Else GUICtrlSetData( $PROXY_LIST[$x][2], $x&"|"&$PROXY_LIST[$x][0]&"|"&$PROXY_LIST[$x][1]&"|ONLINE") GUICtrlSetBkColor( $PROXY_LIST[$x][2], 0x00FF00) EndIf ___ASockShutdown($PROXY_LIST[$x][3]) TCPCloseSocket($PROXY_LIST[$x][2]) EndSwitch EndFunc ;================================================================================================================== ; ; Zatorg's Asynchronous Sockets UDF Starts from here. ; ;================================================================================================================== Func ___ASocket($iAddressFamily = 2, $iType = 1, $iProtocol = 6) If $hWs2_32 = -1 Then $hWs2_32 = DllOpen( "Ws2_32.dll" ) Local $hSocket = DllCall($hWs2_32, "uint", "socket", "int", $iAddressFamily, "int", $iType, "int", $iProtocol) If @error Then SetError(1, @error) Return -1 EndIf If $hSocket[ 0 ] = -1 Then SetError(2, ___WSAGetLastError()) Return -1 EndIf Return $hSocket[ 0 ] EndFunc ;==>_ASocket Func ___ASockShutdown($hSocket) If $hWs2_32 = -1 Then $hWs2_32 = DllOpen( "Ws2_32.dll" ) Local $iRet = DllCall($hWs2_32, "int", "shutdown", "uint", $hSocket, "int", 2) If @error Then SetError(1, @error) Return False EndIf If $iRet[ 0 ] <> 0 Then SetError(2, ___WSAGetLastError()) Return False EndIf Return True EndFunc ;==>_ASockShutdown Func ___ASockClose($hSocket) If $hWs2_32 = -1 Then $hWs2_32 = DllOpen( "Ws2_32.dll" ) Local $iRet = DllCall($hWs2_32, "int", "closesocket", "uint", $hSocket) If @error Then SetError(1, @error) Return False EndIf If $iRet[ 0 ] <> 0 Then SetError(2, ___WSAGetLastError()) Return False EndIf Return True EndFunc ;==>_ASockClose Func ___ASockSelect($hSocket, $hWnd, $uiMsg, $iEvent) If $hWs2_32 = -1 Then $hWs2_32 = DllOpen( "Ws2_32.dll" ) Local $iRet = DllCall( _ $hWs2_32, _ "int", "WSAAsyncSelect", _ "uint", $hSocket, _ "hwnd", $hWnd, _ "uint", $uiMsg, _ "int", $iEvent _ ) If @error Then SetError(1, @error) Return False EndIf If $iRet[ 0 ] <> 0 Then SetError(2, ___WSAGetLastError()) Return False EndIf Return True EndFunc ;==>_ASockSelect ; Note: you can see that $iMaxPending is set to 5 by default. ; IT DOES NOT MEAN THAT DEFAULT = 5 PENDING CONNECTIONS ; 5 == SOMAXCONN, so don't worry be happy Func ___ASockListen($hSocket, $sIP, $uiPort, $iMaxPending = 5); 5 == SOMAXCONN => No need to change it. Local $iRet Local $stAddress If $hWs2_32 = -1 Then $hWs2_32 = DllOpen( "Ws2_32.dll" ) $stAddress = ___SockAddr($sIP, $uiPort) If @error Then SetError(@error, @extended) Return False EndIf $iRet = DllCall($hWs2_32, "int", "bind", "uint", $hSocket, "ptr", DllStructGetPtr($stAddress), "int", DllStructGetSize($stAddress)) If @error Then SetError(3, @error) Return False EndIf If $iRet[ 0 ] <> 0 Then $stAddress = 0; Deallocate SetError(4, ___WSAGetLastError()) Return False EndIf $iRet = DllCall($hWs2_32, "int", "listen", "uint", $hSocket, "int", $iMaxPending) If @error Then SetError(5, @error) Return False EndIf If $iRet[ 0 ] <> 0 Then $stAddress = 0; Deallocate SetError(6, ___WSAGetLastError()) Return False EndIf Return True EndFunc ;==>_ASockListen Func ___ASockConnect($hSocket, $sIP, $uiPort) Local $iRet Local $stAddress If $hWs2_32 = -1 Then $hWs2_32 = DllOpen( "Ws2_32.dll" ) $stAddress = ___SockAddr($sIP, $uiPort) If @error Then SetError(@error, @extended) Return False EndIf $iRet = DllCall($hWs2_32, "int", "connect", "uint", $hSocket, "ptr", DllStructGetPtr($stAddress), "int", DllStructGetSize($stAddress)) If @error Then SetError(3, @error) Return False EndIf $iRet = ___WSAGetLastError() If $iRet = 10035 Then; WSAEWOULDBLOCK Return True; Asynchronous connect attempt has been started. EndIf SetExtended(1); Connected immediately Return True EndFunc ;==>_ASockConnect ; A wrapper function to ease all the pain in creating and filling the sockaddr struct Func ___SockAddr($sIP, $iPort, $iAddressFamily = 2) Local $iRet Local $stAddress If $hWs2_32 = -1 Then $hWs2_32 = DllOpen( "Ws2_32.dll" ) $stAddress = DllStructCreate("short; ushort; uint; char[8]") If @error Then SetError(1, @error) Return False EndIf DllStructSetData($stAddress, 1, $iAddressFamily) $iRet = DllCall($hWs2_32, "ushort", "htons", "ushort", $iPort) DllStructSetData($stAddress, 2, $iRet[ 0 ]) $iRet = DllCall($hWs2_32, "uint", "inet_addr", "str", $sIP) If $iRet[ 0 ] = 0xffffffff Then; INADDR_NONE $stAddress = 0; Deallocate SetError(2, ___WSAGetLastError()) Return False EndIf DllStructSetData($stAddress, 3, $iRet[ 0 ]) Return $stAddress EndFunc ;==>__SockAddr Func ___WSAGetLastError() If $hWs2_32 = -1 Then $hWs2_32 = DllOpen( "Ws2_32.dll" ) Local $iRet = DllCall($hWs2_32, "int", "WSAGetLastError") If @error Then ;if $console_out = True then ConsoleWrite("+> _WSAGetLastError(): WSAGetLastError() failed. Script line number: " & @ScriptLineNumber & @CRLF) SetExtended(1) Return 0 EndIf Return $iRet[ 0 ] EndFunc ;==>_WSAGetLastError ; Got these here: ; http://www.autoitscript.com/forum/index.php?showtopic=5620&hl=MAKELONG Func ___MakeLong($LoWord, $HiWord) Return BitOR($HiWord * 0x10000, BitAND($LoWord, 0xFFFF)); Thanks Larry EndFunc ;==>_MakeLong Func ___HiWord($Long) Return BitShift($Long, 16); Thanks Valik EndFunc ;==>_HiWord Func ___LoWord($Long) Return BitAND($Long, 0xFFFF); Thanks Valik EndFunc ;==>_LoWord ;----------------------------------OTHER AUTOIT INBUILT FUNCS----## ;=============================================================================== ; ; Function Name: _GetIP() ; Description: Get public IP address of a network/computer. ; Parameter(s): None ; Requirement(s): Internet access. ; Return Value(s): On Success - Returns the public IP Address ; On Failure - -1 and sets @ERROR = 1 ; Author(s): Larry/Ezzetabi & Jarvis Stubblefield ; ;=============================================================================== Func _Get_IP() Local $ip, $t_ip If InetGet("http://checkip.dyndns.org/?rnd1=" & Random(1, 65536) & "&rnd2=" & Random(1, 65536), @TempDir & "\~ip.tmp") Then $ip = FileRead(@TempDir & "\~ip.tmp", FileGetSize(@TempDir & "\~ip.tmp")) FileDelete(@TempDir & "\~ip.tmp") $ip = StringTrimLeft($ip, StringInStr($ip, ":") + 1) $ip = StringTrimRight($ip, StringLen($ip) - StringInStr($ip, "/") + 2) $t_ip = StringSplit($ip, '.') If $t_ip[0] = 4 And StringIsDigit($t_ip[1]) And StringIsDigit($t_ip[2]) And StringIsDigit($t_ip[3]) And StringIsDigit($t_ip[4]) Then Return $ip EndIf EndIf If InetGet("http://www.whatismyip.com/?rnd1=" & Random(1, 65536) & "&rnd2=" & Random(1, 65536), @TempDir & "\~ip.tmp") Then $ip = FileRead(@TempDir & "\~ip.tmp", FileGetSize(@TempDir & "\~ip.tmp")) FileDelete(@TempDir & "\~ip.tmp") $ip = StringTrimLeft($ip, StringInStr($ip, "Your ip is") + 10) $ip = StringLeft($ip, StringInStr($ip, " ") - 1) $ip = StringStripWS($ip, 8) $t_ip = StringSplit($ip, '.') If $t_ip[0] = 4 And StringIsDigit($t_ip[1]) And StringIsDigit($t_ip[2]) And StringIsDigit($t_ip[3]) And StringIsDigit($t_ip[4]) Then Return $ip EndIf EndIf SetError(1) Return -1 EndFunc ;==>_Get_IP Some Proxies to get you started: 118.96.94.36:8080 69.125.128.138:27977 114.129.97.46:8080 124.195.18.119:80 62.75.145.245:9100 98.183.251.11:27977 173.196.50.100:27977 221.12.61.214:8080 222.186.43.82:1080 69.33.181.42:80 114.129.100.35:8080 64.76.188.126:80 114.129.97.101:8080 212.58.10.10:80 77.241.165.114:8080 159.226.234.7:80 114.59.80.243:8080 190.94.1.195:80 118.182.20.242:8080 41.234.207.197:8080 98.155.37.249:47793 79.125.28.242:8080 24.126.55.101:27977 193.188.125.173:80 124.193.109.15:80 109.203.196.121:808 80.239.243.18:80 218.6.13.35:80 69.136.47.4:27977 216.104.161.208:80 24.179.18.15:12378 189.1.162.4:8080 195.97.254.137:80 117.28.232.186:80 41.215.177.206:8080 110.138.211.56:8080 66.193.15.82:80 124.225.57.10:8080 112.169.94.143:8088 70.44.61.7:1233 204.15.147.149:8080 114.129.98.35:8080 76.18.96.186:27977 180.241.98.194:8080 72.13.94.164:80 209.237.236.110:80 41.205.110.85:8080 91.210.104.104:80 121.14.104.244:80 68.199.165.7:3697 122.70.156.157:80 174.129.133.21:8000 114.129.98.236:8080 75.73.231.37:27977 118.137.65.154:8080 200.167.162.203:8080 187.45.232.176:8080 115.69.216.98:80 70.163.50.203:27977 112.95.238.199:808 193.87.7.65:80 95.0.211.186:8080 182.48.43.12:80 114.129.98.108:8080 222.247.48.221:808 182.48.23.77:8090 69.244.133.182:1168 78.93.242.7:80 114.129.97.49:8080 114.129.98.66:8080 67.192.11.165:80 63.130.248.252:80 210.23.76.200:8080 196.202.83.129:8000 65.32.56.224:1083 68.84.169.216:27977 208.110.220.133:8080 198.12.16.170:80 69.124.240.221:37701 85.214.50.156:8118 222.188.10.1:1080 183.62.24.34:808 114.129.100.143:8080 98.183.9.251:1137 218.19.119.99:8080 203.186.62.125:8080 91.200.171.245:8080 202.4.155.234:808 212.33.237.113:80 163.152.133.22:8080 88.85.125.78:8080 64.4.98.119:27977 89.188.141.51:80 212.51.207.126:80 118.174.36.190:8080 200.82.126.87:80 212.85.146.236:80 96.240.2.237:42863 120.136.22.154:8080 111.67.80.116:80 61.4.234.216:8080 66.119.43.37:80 122.227.22.214:63000 114.129.98.231:8080 80.239.242.225:80 82.160.44.55:8080 72.3.245.248:80 222.124.25.74:80 119.235.53.131:80 98.199.27.21:27977 85.254.213.163:80 61.4.219.6:8080 93.189.5.138:8080 195.189.142.69:80 212.209.194.144:80 202.159.8.74:8080 118.97.13.60:8080 88.87.215.114:81 67.84.134.22:27977 114.129.98.37:8080 116.55.19.96:1080 203.142.72.107:80 175.111.89.16:8080 99.248.60.100:1939 63.130.248.251:80 62.129.243.242:8080 200.242.222.139:80 114.129.98.212:8080 193.160.201.95:80 202.212.166.90:8080 189.47.194.196:8080 114.129.99.161:8080 114.129.97.136:8080 59.77.17.24:8080 98.109.59.184:1797 114.129.100.77:8080 114.129.99.254:8080 98.222.69.66:27977 201.75.73.131:8080 24.90.235.196:27977 98.208.56.122:10971 201.234.133.41:1080 46.0.203.7:80 67.184.98.250:27977 92.61.188.141:8080 65.34.150.112:27977 112.216.29.245:80 114.129.98.10:8080 67.249.168.198:8085 188.40.173.106:80 83.170.116.143:80 61.4.219.10:8080 66.65.70.65:1252 159.226.251.180:83 80.239.242.242:80 76.100.17.159:27977 209.62.20.171:80 193.28.52.145:80 203.130.195.193:8080 189.200.240.68:80 68.62.73.13:1733 180.243.86.215:8080 118.96.142.61:80 92.63.52.73:8080 88.250.70.208:80 95.168.181.219:8080 118.97.83.245:8090 75.125.143.84:80 189.17.0.35:8000 178.213.33.129:443 24.234.67.140:27977 209.235.218.83:80 119.40.100.113:8080 114.129.98.142:8080 76.31.62.106:27977 202.77.107.34:80 189.3.160.42:80 114.129.97.42:8080 87.226.106.203:8080 64.34.213.148:80 190.40.28.83:8080 201.67.138.98:80 82.117.192.227:8080 193.252.48.31:8080 92.61.189.129:8080 209.62.20.196:80 118.98.216.27:8080 41.73.2.35:8080 66.92.169.250:80 194.170.16.75:8080 173.212.195.196:1337 58.246.182.60:8088 65.23.156.161:80 134.37.254.27:80 68.111.211.98:27977 77.78.3.83:9090 190.41.192.210:8080 87.250.129.151:80 62.176.18.25:80 174.134.42.74:80 220.227.100.59:8080 217.91.32.16:8080 91.194.246.49:8080 218.242.254.74:1080 200.20.0.246:80 119.235.53.130:80 67.63.92.33:27977 180.246.179.34:8080 110.137.40.102:8080 58.246.200.114:80 68.38.24.73:48397 195.189.142.132:80 69.123.91.137:27977 221.1.96.22:443 71.174.102.72:80 125.162.32.222:80 66.119.43.36:80 68.39.144.196:1385 221.215.106.82:1337 119.15.86.20:8080 68.118.109.226:27977 70.158.130.208:8080 125.40.181.247:8080 114.129.99.111:8080 117.41.228.6:2 210.48.147.36:80 67.53.116.252:80 24.109.239.138:80 114.129.99.72:8080 211.100.4.71:80 218.21.91.214:80 58.241.40.228:1080 200.88.125.4:8008 187.111.11.72:8080 118.122.88.7:8080 187.11.250.175:8080 114.129.99.144:8080 196.23.152.220:80 148.235.153.178:8080 91.194.247.234:8080 165.228.212.223:80 80.82.235.179:80 187.111.223.10:8080 202.181.164.100:80 216.40.33.31:80 195.162.130.20:8080 188.94.228.46:8080 202.147.198.69:80 202.212.166.124:8080 222.35.137.220:80 114.129.98.241:8080 41.73.15.211:8080 114.129.98.175:8080 188.40.173.101:80 98.110.80.191:1734 213.29.63.62:8080 114.129.98.146:8080 114.129.99.125:8080 60.191.232.230:80 115.124.66.30:8080 180.241.106.54:80 202.117.35.249:80 114.129.98.99:8080 190.1.137.130:8080 114.129.100.237:8080 81.217.6.239:80 196.214.141.221:8080 98.255.196.232:1590 68.49.201.216:27977 122.52.117.92:8080 202.143.148.61:80 222.70.137.238:80 222.124.136.103:8080 187.85.160.3:80 189.73.221.49:80 64.120.166.23:1080 114.129.100.55:8080 87.197.42.171:8080 180.246.114.66:8080 119.36.138.131:1080 67.223.227.21:80 221.233.134.87:8080 94.195.11.147:80 71.72.30.250:28052 209.226.31.160:80 74.197.10.24:27977 209.200.46.108:80 8.4.59.117:80 109.74.202.89:80 119.40.100.9:8080 200.63.71.225:8080 110.138.51.76:8080 203.172.167.8:8080 82.177.67.1:8080 77.67.17.17:8080 76.188.219.178:4458 221.229.119.186:80 81.0.235.172:80 216.104.161.120:80 110.138.211.56:80 212.177.17.74:80 186.24.13.125:8080 118.97.129.74:8080 80.239.242.223:80 114.129.99.83:8080 114.129.99.210:8080 202.4.155.234:1080 67.159.52.76:8080 68.192.216.10:1337 219.235.228.182:1080 118.98.215.10:8080 200.81.59.101:80 202.143.149.36:8080 195.49.188.226:80 123.125.156.92:80 92.61.191.17:8080 201.208.100.167:8080 68.169.183.117:27977 112.105.69.163:80 61.4.11.193:8080 122.72.20.218:80 200.148.135.234:8080 203.199.9.4:80 74.114.116.101:80 122.144.1.212:8080 97.65.164.214:8080 200.171.25.203:8000 41.134.81.234:80 119.235.53.130:8080 125.165.125.83:8080 160.79.35.27:80 24.0.213.12:8008 24.0.82.254:58029 91.90.120.40:1080 218.61.196.69:8080 114.129.99.243:8080 114.129.98.131:8080 70.174.29.174:27977 114.129.98.211:8080 202.51.107.34:8080 61.207.158.6:8088 122.248.213.39:80 84.22.27.4:80 110.136.207.37:80 77.66.25.53:80 98.200.72.55:1908 119.110.81.226:8080 85.214.61.55:80 202.44.53.94:80 75.69.78.108:1405 194.187.110.72:80 118.96.94.45:80 200.85.79.22:80 75.64.57.44:57907 203.142.71.149:8080 202.146.129.133:8080 67.165.33.228:27977 202.191.122.239:80 202.99.27.3:8080 61.4.253.175:8080 218.28.233.214:9000 114.129.97.51:8080 114.129.100.252:8080 63.134.178.211:27977 87.119.213.25:80 109.254.88.136:1080 66.235.245.150:80 212.118.224.151:80 80.206.48.100:80 67.182.241.56:27977 24.242.167.123:8080 210.8.224.2:80 114.129.100.86:8080 77.27.27.65:16589 210.94.189.210:8080 195.117.121.2:1080 92.63.96.135:8080 210.31.160.55:9 212.49.64.3:80 98.198.54.147:27977 220.113.15.220:8081 195.89.37.91:80 59.39.67.158:8080 218.92.252.38:8080 122.155.13.18:80 202.103.67.98:80 189.72.173.220:80 24.228.100.186:27977 76.16.165.171:1091 87.120.166.182:88 189.22.150.34:80 174.142.125.161:80 187.4.118.221:80 114.129.98.129:8080 83.36.60.252:80 112.175.251.56:8080 208.45.143.104:80 217.20.163.72:80 61.185.143.178:8080 188.142.49.254:8080 193.179.209.200:80 91.90.122.1:1080 209.62.20.239:80 64.255.180.31:80 67.205.67.45:80 222.124.5.82:8080 80.239.242.112:80 98.200.64.178:1174 75.190.141.203:27977 174.129.195.8:8123 87.106.197.98:443 195.248.250.142:80 114.129.98.73:8080 85.214.152.105:1337 68.52.107.181:27977 74.213.164.188:80 114.129.100.249:8080 200.125.243.122:8080 219.83.100.204:8080 64.211.66.142:80 62.216.165.131:8080 175.41.151.200:80 180.246.116.28:80 221.204.246.161:80 201.75.71.33:8080 24.16.196.237:1907 168.176.5.223:80 61.4.11.19:8080 61.6.245.46:80 98.212.102.97:1628 190.144.55.147:8080 120.136.21.131:80 222.69.91.144:63000 216.6.202.27:80 193.255.195.72:80 213.192.85.98:8080 189.22.105.205:8080 193.190.145.92:80 184.22.251.43:80 204.12.250.147:64616 118.96.78.2:8080 108.36.100.249:14925 119.82.239.62:8080 219.117.212.126:8080 200.206.175.108:8080 79.106.1.83:8080 173.203.102.80:8080 193.255.192.190:80 63.166.247.31:80 187.12.229.178:8080 174.108.120.102:3390 75.126.176.161:80 118.96.78.16:8080 24.215.22.136:3969 72.55.130.45:80 178.165.55.79:8008 114.129.99.131:8080 66.7.124.203:27977 117.102.83.218:80 196.28.237.43:8080 24.230.247.138:29505 202.69.33.143:8080 61.4.251.243:8080 58.20.41.168:1080 111.67.80.84:80 114.113.228.202:1080 180.249.131.31:80 112.95.238.199:1080 218.29.89.203:8080 213.41.80.7:80 200.37.204.93:8080 201.23.107.11:8080 114.129.97.73:8080 80.237.156.177:80 184.22.248.124:8080 190.145.116.22:80 120.29.157.234:8080 118.96.30.11:8080 82.99.211.50:8080 114.129.98.127:8080 72.167.202.24:8000 202.212.165.205:8080 75.102.3.18:80 97.81.175.62:1414 222.237.79.140:80 111.68.100.8:8080 210.48.147.82:80 200.97.9.234:8080 92.61.188.41:8080 75.125.242.146:80 61.191.187.23:8080 24.0.68.158:1355 58.59.31.82:1337 211.239.121.249:43565 186.136.72.41:80 118.96.94.45:8080 200.181.30.37:8080 173.22.82.104:13229 118.98.202.123:8080 85.185.105.26:8080 66.75.93.204:8088 190.147.197.35:8080 70.185.184.141:11331 111.68.28.27:8080 216.104.161.205:80 122.48.31.74:80 114.129.100.126:8080 173.217.173.248:27977 222.124.144.178:80 180.247.218.28:8080 114.129.99.129:8080 114.129.98.159:8080 72.218.74.95:27977 116.90.162.147:80 112.65.216.174:1080 221.2.144.135:1080 118.69.192.62:8088 202.74.65.69:8080 122.48.31.73:80 196.202.41.254:80 202.64.130.236:80 114.129.97.66:8080 210.166.221.61:8080 196.3.182.146:80 202.65.122.226:8080 118.122.88.44:80 58.221.129.158:1337 118.96.136.76:80 61.166.144.29:80 189.31.180.236:80 114.129.100.238:8080 202.43.74.66:8080 117.102.226.142:80 124.225.55.30:8080 115.236.98.109:80 203.251.21.105:80 69.195.207.230:7257 190.77.30.109:8080 115.124.65.94:8080 116.205.127.43:8080 216.249.85.43:27977 118.97.224.2:8080 110.139.180.151:8080 118.97.84.20:80 222.124.218.164:8080 180.244.211.224:8080 66.229.95.87:8085 110.138.207.144:8080 187.4.82.68:8080 115.124.75.36:80 200.63.71.54:8080 98.209.176.218:1565 200.181.109.20:80 115.124.73.166:80 115.124.64.241:8080 202.149.90.234:8080 24.46.89.172:1147 187.4.104.99:8080 125.164.72.200:8080 98.222.112.179:27977 24.3.70.138:27977 180.243.231.55:8080 74.109.211.64:1564 220.237.25.106:1087 8080 78.188.153.229:8080 210.48.147.52:80 208.64.176.157:80 69.125.100.96:27977 58.96.134.22:8000 24.139.43.249:8085 184.72.55.152:443 114.129.100.80:8080 119.109.115.149:8909 67.167.89.121:14073 71.82.96.242:1421 109.87.143.120:9 173.74.178.23:31779 68.144.41.195:17719 71.234.200.202:37373 24.13.125.182:2003 66.27.207.82:27977 72.240.34.23:80 182.48.167.10:8080 EDIT: All the Proxies in this list are legal, public Proxies so dont get any ideas!
    1 point
  50. I had a quick look around and couldn't find this anywhere so I'm posting up some code. This allows you to drag-and-drop the items in the listbox in order to reorder them. A nice UI touch when you want users to have the ability to do this. I'm writing something right now that will use this but thought I'd put this code here in case someone wants to use it. #include <Constants.au3> #include <GUIListBox.au3> #include <WinAPI.au3> #include <WindowsConstants.au3> Global $gnDRAGLISTMSGSTRING = _WinAPI_RegisterWindowMessage("commctrl_DragListMsg") Global $DL_BEGINDRAG = $WM_USER + 133 Global $DL_DRAGGING = $WM_USER + 134 Global $DL_DROPPED = $WM_USER + 135 Global $DL_CANCELDRAG = $WM_USER + 136 Global Enum $DL_STOPCURSOR = 1, $DL_COPYCURSOR, $DL_MOVECURSOR Global $gtDRAGLISTINFO = "long uNotification;long hWnd;long x;long y" Global $gfItemAdded = False Global $hMain = GUICreate("DragList", 200, 400) Global $cListbox = GUICtrlCreateList("", 16, 16, 168, 368, $WS_BORDER + $WS_VSCROLL) GUICtrlSetFont($cListbox, 10, Default, Default, "Tahoma") Global $hListbox = GUICtrlGetHandle($cListbox) GUICtrlSetData($cListbox, "Apples|Oranges|Bananas|Pears|Grapefruits|Limes|Lemons|Strawberries|Plums|Melons|Grapes|") GUISetState() _ComCtl32_MakeDragList($hListbox) Global $wProcNew = DllCallbackRegister("_MyWndProc", "int", "hwnd;int;wparam;lparam") Global $wProcOld = _WinAPI_SetWindowLong($hMain, $GWL_WNDPROC, DllCallbackGetPtr($wProcNew)) While GUIGetMsg() <> -3 Sleep(10) Wend Exit Func _MyWndProc($hWnd, $nMsg, $wParam, $lParam) Local $aRet, $nOldIndex, $sItemText If $nMsg = $gnDRAGLISTMSGSTRING Then Local $tDRAGLISTINFO = DllStructCreate($gtDRAGLISTINFO, $lParam) Local $uNotification = DllStructGetData($tDRAGLISTINFO, "uNotification") Local $x = DllStructGetData($tDRAGLISTINFO, "x"), $y = DllStructGetData($tDRAGLISTINFO, "y") Local $nItem = _ComCtl32_LBItemFromPt($hListbox, $x, $y) Switch $uNotification Case $DL_BEGINDRAG If $nItem < (_GUICtrlListBox_GetCount($hListbox) - 1) Then _GUICtrlListBox_AddString($hListbox, "") $gfItemAdded = True EndIf Return 1 Case $DL_DRAGGING _ComCtl32_DrawInsert($hMain, $hListbox, $nItem) If $nItem = _GUICtrlListBox_GetCurSel($hListbox) Then Return $DL_STOPCURSOR Return $DL_MOVECURSOR Case $DL_DROPPED If $nItem > -1 Then $nOldIndex = _GUICtrlListBox_GetCurSel($hListbox) If $nItem <> $nOldIndex Then $sItemText = _GUICtrlListBox_GetText($hListbox, $nOldIndex) If $nItem < $nOldIndex Then $nOldIndex += 1 _GUICtrlListBox_InsertString($hListbox, $sItemText, $nItem) _GUICtrlListBox_DeleteString($hListbox, $nOldIndex) If $nItem > $nOldIndex Then $nItem -= 1 _GUICtrlListBox_SetCurSel($hListbox, $nItem) EndIf EndIf If $gfItemAdded Then _GUICtrlListBox_DeleteString($hListbox, _GUICtrlListBox_GetCount($hListbox) - 1) $gfItemAdded = False EndIF _ComCtl32_DrawInsert($hMain, $hListbox, -1) Return 0 Case $DL_CANCELDRAG If $gfItemAdded Then _GUICtrlListBox_DeleteString($hListbox, _GUICtrlListBox_GetCount($hListbox) - 1) $gfItemAdded = False EndIF _ComCtl32_DrawInsert($hMain, $hListbox, -1) Return 0 EndSwitch EndIf Return _WinAPI_CallWindowProc($wProcOld, $hWnd, $nMsg, $wParam, $lParam) EndFunc Func _ComCtl32_MakeDragList($hWnd) Local $aRet = DllCall("comctl32.dll", "int", "MakeDragList", "hwnd", $hWnd) If @error Then Return SetError(@error, @extended, 0) Return $aRet[0] EndFunc Func _ComCtl32_LBItemFromPt($hWnd, $x, $y) Local $aRet = DllCall("comctl32.dll", "long", "LBItemFromPt", "hwnd", $hWnd, "long", $x, "long", $y, "long", 1) If @error Then Return SetError(@error, @extended, 0) Return $aRet[0] EndFunc Func _ComCtl32_DrawInsert($hWndParent, $hWnd, $nItem) DllCall("comctl32.dll", "none", "DrawInsert", "hwnd", $hWndParent, "hwnd", $hWnd, "long", $nItem) If @error Then Return SetError(@error, @extended, 0) Return EndFunc Enjoy. WBD
    1 point
×
×
  • Create New...