Sign in to follow this  
Followers 0
nullschritt

Process stops responding

2 posts in this topic

#1 ·  Posted (edited)

Hello all, I am developing a P2P instant messenger, it all works great, until the child-process stops responding, and I can see no reason why, perhaps I have coded in an error that I'm not seeing, I was wondering if someone with more experience could look at it and try to point out any possible errors, thanks.

Global $net1, $net2, $loggedin = 1, $usernfo = "test|137982", $buffer

  $UDF_Version = "1.32 STABLE"
$console_out = False
$STANDARD_MESSAGE_LIFE = 200
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
Global $hWs2_32 = -1 ;Kip, What is this? (I left it in case it was something important)

Global Const $TCP_SEND = 1
Global Const $TCP_RECEIVE = 2
Global Const $TCP_CONNECT = 4
Global Const $TCP_DISCONNECT = 8
Global Const $TCP_NEWCLIENT = 16

Global Const $IPLOC_LOCAL = 64
Global Const $IPLOC_GLOBAL = 128

Global Const $P2P_MESSAGE = 256
Global Const $P2P_RECEIVE = 512
Global Const $P2P_CONNECT = 1024
Global Const $P2P_DISCONNECT = 2048
Global Const $P2P_NEWCONNECTION = 4096
Global Const $P2P_AUX_DATA = 8192

Global $total_connected = 0
Global $max_connections
Global $Listening_Socket
Global $node_IP
Global $node_Port
Global $node_Identifier
Global $node_ext_IP
Global $Bootstrap_mode
Global $Bootstrap_max
Global $peer_timer

Global $total_ID_known = 0
Global $Known_ID[200]

Global $connectfunc = ""
Global $recievefunc = ""
Global $disconnectfunc = ""
Global $newconnectionfunc = ""
Global $messagefunc = ""
global $auxfunc = ""

Global $Main_Socket_Address = ""
TCPStartup()
Global Const $__TCP_WINDOW = GUICreate("Async Sockets UDF") ;I know, Copy paste.

#include <crypt.au3>
#include <SQLite.au3>
#include <SQLite.dll.au3>
#include <inet.au3>

_P2P_Start_Node("test", 7337, 400, 1, 100, 1)
        _P2P_Register_Event($P2P_MESSAGE, "_incoming_p2p")
_P2P_Register_Event($P2P_MESSAGE, "_message")

  If WinExists("8934562893452394856-23945629-348-29-2-3968452-834-29-4") Then
        $pid = RegRead("HKEY_CURRENT_USER\Software\SIM", "PID")
        While ProcessExists($pid)
            ProcessClose($pid)
        WEnd
    EndIf
    GUICreate("8934562893452394856-23945629-348-29-2-3968452-834-29-4")
    RegWrite("HKEY_CURRENT_USER\Software\SIM", "PID", "REG_SZ", @AutoItPID)
    HotKeySet("^+p", "connect") ;connect to someone!
    HotKeySet( "^e", "_send") ;Send some data!
    $timah = TimerInit()
    $timah2 = TimerInit()
    $timah3 = TimerInit()
         While 1
        Sleep(100)
        _checkstdin()
        If TimerDiff($timah2) > 1000 Then
              FileWrite(@ScriptDir&"\log.txt", "Process is not hung at "&round(TimerDiff($timah3)/1000)&" seconds."&@CRLF)
            If InetGetInfo($net1, 2) Then
                FileDelete(@ScriptDir & "\PEERUPDT")
            EndIf
            If InetGetInfo($net2, 2) Then
                FileDelete(@ScriptDir & "\CRON")
            EndIf
            $timah2 = TimerInit()
        EndIf

        If TimerDiff($timah) > 30000 Then
            _getcontacts()
             If $loggedin = 1 Then
            If _CheckPort() Then
                    $logindata = StringSplit($usernfo, "|")
                    $passxy = StringLower(StringTrimLeft(_Crypt_HashData($logindata[2], $CALG_MD5), 2))
                    $peers = _P2P_Peerlist()

                    If IsArray($peers) Then
                        If $peers[0][0] < 2 Then
                            $peersx = _INetGetSource("http://prodynamicsinc.com/link.php?CMD=page&ID=SIM&TYPE=PEERS&UID=" & $logindata[1] & "&PASS=" & $passxy)
                            If $peersx <> "" Then
                                $peersx = StringSplit($peersx, "|")
                                If $peersx[0] > 0 Then
                                    For $i = 1 To $peersx[0]
                                        _P2P_Connect($peersx[$i])
                                    Next
                                EndIf
                            EndIf
                        EndIf
                    EndIf
                    $net1 = InetGet("http://prodynamicsinc.com/link.php?CMD=page&ID=SIM&TYPE=PEERUPDT&IP=" & _GetIP() & "&UID=" & $logindata[1] & "&PASS=" & $passxy, @ScriptDir & "\PEERUPDT", 1, 1)
                    $net2 = InetGet("http://prodynamicsinc.com/link.php?CMD=page&ID=SIM&TYPE=CRON&UID=" & $logindata[1] & "&PASS=" & $passxy, @ScriptDir & "\CRON", 1, 1)
                EndIf
            EndIf
            $timah = TimerInit()
        EndIf

    WEnd

    Func connect()
    _P2P_Connect(InputBox("Connect to", "Enter IP address to connct to.",@IPAddress1))
EndFunc

func _checkstdin()
;subprocess gets commands and sends to main
$buffer &= ConsoleRead()
If StringRegExp($buffer, "--SIM:([PRODY](.*?)[0-9]){5}") Then
$strings = StringRegExp($buffer, "--SIM:([PRODY](.*?)[0-9]){5}", 2)
$strings = StringSplit($buffer, $strings[0], 1)
if UBound($strings) < 1 then Return
$buffer = $strings[2]
$cmds = StringSplit($strings[1], "~", 3)
if UBound($cmds) < 1 then Return

Switch $cmds[0]

    Case "LOGIN"
        $passx = StringLower(stringtrimleft(_Crypt_HashData($cmds[2], $CALG_MD5), 2))
        $login = _INetGetSource("http://prodynamicsinc.com/link.php?CMD=page&ID=LOGIN&user="&$cmds[1]&"&pass="&$passx)
        $retstring = "LOGIN~"&$login&"~"&$cmds[1]&"|"&$cmds[2]&"~"&_generateheader(2)
        ConsoleWrite($retstring)
        if $login = 0 then
        global $usernfo = $cmds[1]&"|"&$cmds[2]
;~      _P2P_Stop_Node()
        _P2P_Start_Node($cmds[1], 7337, 400, 1, 100, 1)
        _P2P_Register_Event($P2P_MESSAGE, "_incoming_p2p")
        $peers = _INetGetSource("http://prodynamicsinc.com/link.php?CMD=page&ID=SIM&TYPE=PEERS&UID="&$cmds[1]&"&PASS="&$passx)
        if $peers <> "" Then
        $peers = StringSplit($peers, "|")
        if $peers[0] > 0 Then
        for $i=1 to $peers[0]
        _P2P_Connect($peers[$i])
        Next
        EndIf
        EndIf
        _SQLite_Startup ()
        Global $stype
        Global $hQuery, $sMsg, $aRow
        $sdb = _SQLite_Open (@ScriptFullPath&":"&$cmds[1]) ; open :memory: Database
        $loggedin = 1
        Global $activeuser = $cmds[1]
        Else
        $loggedin = 0
        endif

;~      $offline = _INetGetSource("http://prodynamicsinc.com/link.php?CMD=PAGE&ID=SIM&TYPE=OFFLINE&user="&$cmds[1]&"&pass="&$cmds[2])
;~      if $offline <> "" Then
;~      if StringInStr($offline, "~") Then
;~      $offline = StringSplit($offline, "~")
;~      for $i=1 to $offline[0]
;~      ConsoleWrite("MSG~"&$offline[$i]&"~"&_generateheader())
;~      Next
;~      Else
;~      ConsoleWrite("MSG~"&$offline&"~"&_generateheader())
;~      EndIf
;~      EndIf

    Case "MSG"
    if $loggedin = 1 and IsDeclared("activeuser") Then
         _P2P_Send_Message($cmds[1], $cmds[2], $activeuser)
    EndIf

    Case "INFO"
        $peers = _P2P_Peerlist()
        $externalip = _GetIP()
        $portcheck = _CheckPort()
        $retstring = "INFO~"&$peers[0][0]&"~"&$externalip&"~"&String($portcheck)&"~"&@IPAddress1&"~"&_generateheader(2)
        ConsoleWrite($retstring)

EndSwitch

EndIf

EndFunc

Func _CheckPort($vPort = 7337)

TCPStartup()

    $MainSocket = TCPListen('0.0.0.0', $vPort)
    FileDelete(@ScriptDir & "\port.dat")
    Local $hDownload, $go = 1

    Do
        Local $ConnectedSocket = TCPAccept($MainSocket)
        If $ConnectedSocket >= 0 Then
            TCPSend($connectedsocket, "Cool Story Bro")
        EndIf

        Sleep(5)

        if $go = 1 then
            $hDownload = InetGet("http://prodynamicsinc.com/link.php?CMD=page&ID=portcheck&buffer=0&port=" & $vPort&"&IP="&_GetIP(), @ScriptDir & "\port.dat", 1, 1)
            $go = 0
        EndIf

    Until InetGetInfo($hDownload, 2)

    local $portcheck = FileRead(@ScriptDir & "\port.dat")
    FileDelete(@ScriptDir & "\port.dat")
    InetClose($hDownload)
    TCPShutdown()

        If $portcheck = "Port Open" Then
            Return True
        Else
            Return False
        EndIf
EndFunc

func _getcontacts()
;we don't need this for testing
endfunc

#cs ----------------------------------------------------------------------------

 AutoIt Version: 3.3.0.0
 Author:         Hyperzap.
                 Design concepts were first coined by Kip in his "Event driven TCP UDF"
                 Zatorg's Asynchronous Sockets UDF is also used.
 Script Function:

    This UDF is a re-write of Kip's 'Event driven TCP UDF'. Thx Kip.
    It aims to generate simple TCP, event driven functionality for P2P programs, As
    opposed to client-server oriented communication as in Kip's UDF.
    Evidently, this functionality is not possible in Kips original releases.

    Apart from the obvious conponents of such a code, like Recv, Send, Connect,
    Listen, other important P2P routines have been coded. These include things
    like; Universal identifiers, bootstrapping mechanisms, peers
    discovery, and message routing.

    MINOR DRAWBACKS:
    You can never use the string `8i8` or `8i8TERMINATE` in your communicatons.
    You cannot use the ` (hash) symbol in either your Node ID or any part of a
    long range message.
#ce ----------------------------------------------------------------------------

; `FUNCTION` ;===============================================================================================================
;
; Name...........: _P2P_Start_Node
; Description ...: Initializes the P2P Node. Starts listening for connections.
; Syntax.........: _P2P_Start_Node( $node_id, $Port, $Max_peers, $Bootstrapmode, $bootstrapmax, $location,  $IP="0.0.0.0")
; Parameters ....:  $node_id        - The Unique Identifier assigned to you, as a user of the program. Should not change
;                                     between excutions for a specific user. This ID is used as an address for long range messages.
;                   $Port           - The port to listen for incoming connections on.
;                   $Max_peers      - The maximum number of peers that can be connected to your node at any one time.
;                   $bootstrapmode  - Either 0 or 1. If 0, this UDF will not automatically connect you to other nodes.
;                   $bootstrapmax   - The number of peers connected before the UDF will stop bootstrapping. (autoconnecting)
;                   $location       - Either 0 or 1. Put 0 if working on a LAN or WLAN. Put 1 if your node works over the
;                                     Internet.
;                   $IP             - (Optional) The IP address to host the node on. Really, the default value will work 99%
;                                       of the time. You shouldn't change it unless you know exactly what your doing.
; Return values .: Err...Nothing.
; Author ........: Hyperzap and Kip.
; Modified.......:
; Remarks .......: Only 1 P2P node can be created per script. By why on earth would you need another?
; Related .......:
; Link ..........;
; Example .......; See my 'example scripts' post. (If applicable)
;
; ;==========================================================================================================================


Func _P2P_Start_Node( $node_id, $Port, $Max_peers, $Bootstrapmode, $bootstrapmax, $location,  $IP="0.0.0.0")
        local $startuptimer = TimerInit()
        $Listening_Socket = ___ASocket()
        $Main_Socket_Address = $Listening_Socket
        ___ASockSelect( $Listening_Socket, $__TCP_WINDOW, 0x0400, $FD_ACCEPT)
        GUIRegisterMsg( 0x0400, "Listensocket_data_" )
        ___ASockListen( $Listening_Socket, $IP, $Port )

        if $Bootstrapmode = 0 then $Bootstrap_mode = $IPLOC_LOCAL
        if $Bootstrapmode = 1 then $Bootstrap_mode = $IPLOC_GLOBAL
        $bootstrap_max = $bootstrapmax
        $max_connections = $Max_peers
        $node_IP = $IP
        $node_Port = $Port
        $node_Identifier = $node_id
        $peer_timer = TimerInit()
        if $location = 1 then $node_ext_IP = _Get_IP() ;GetIP command.
        if $location = 0 then $node_ext_IP = @IPAddress1

        Global $Socket_Handle_array[$Max_peers + 1]
        Global $Node_Identifier_array[$Max_peers + 1]
        Global $Node_IP_array[$Max_peers + 1]
        Global $Node_Peer_Reachable_list[$Max_peers + 1]
        For $x = 0 to $Max_peers step 1
            $Socket_Handle_array[$x] = -1
            $Node_Identifier_array[$x] = -1
            $Node_IP_array[$x] = -1
            $Node_Peer_Reachable_list[$x] = -1
        Next
        if $console_out = True then ConsoleWrite( @CRLF & @CRLF & "P2P_: Node started")
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Port: " & $node_Port)
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Ext IP: " & $node_ext_IP)
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Max peers: " & $max_connections)
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Identifier: " & $node_Identifier)
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Engine Version: " & $UDF_version)
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Startup time: " & TimerDiff( $startuptimer) & "ms" & @CRLF)
EndFunc


; `FUNCTION` ;===============================================================================
;
; Name...........: _P2P_Stop_Node
; Description ...: Stops the node, and closes all connections.
; Syntax.........: _P2P_Stop_Node()
; Parameters ....:
; Return values .: None.
; Author ........: Hyperzap
; Modified.......:
; Remarks .......:
; Related .......:
; Link ..........;
; Example .......;
;
; ;==========================================================================================


Func _P2P_Stop_Node()
    ___ASockShutdown($Listening_Socket)
    TCPCloseSocket($Listening_Socket)

    For $x = 0 to $max_connections step 1
        $Socket_Handle_array[$x] = -1
        $Node_Identifier_array[$x] = -1
        $Node_IP_array[$x] = -1
        $Node_Peer_Reachable_list[$x] = -1
    Next

    $max_connections = 0
    $Listening_Socket = ""
    $node_IP = ""
    $node_Port = ""
    $node_Identifier = -1
    $node_ext_IP = ""
    $Bootstrap_mode = ""
    $Bootstrap_max = 0
    $connectfunc = ""
    $recievefunc = ""
    $disconnectfunc = ""
    $newconnectionfunc = ""
    $messagefunc = ""
    $auxfunc = ""
    if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Engine shutdown successful.")
EndFunc

Func Listensocket_data_($hWnd, $iMsgID, $WParam, $LParam)
    Local $Socketinquestion = $WParam
    Local $iError = ___HiWord( $LParam )
    Local $iEvent = ___LoWord( $LParam )
    Abs($hWnd) ; Stupid AU3Check...
    If $iMsgID = 0x400 Then
        If $iEvent = $FD_ACCEPT Then
            If Not $iError Then
                $arrayslot = Findfreearrayslot()
                if $arrayslot = "error" then ;No more spots for new peers. Connection dropped.
                    $newsocket = TCPAccept($Socketinquestion)
                    TCPSend( $newsocket, "`"&_generateheader(2)&"`NOSLOT`"& _generateheader(1))
                    TCPCloseSocket( $newsocket)
                EndIf
                $newsocket = TCPAccept($Socketinquestion)
                ___ASockSelect($newsocket, $__TCP_WINDOW, 0x0400 + $arrayslot, BitOR($FD_READ, $FD_CONNECT, $FD_CLOSE))
                GUIRegisterMsg( 0x0400 + $arrayslot, "Opensocket_data_" )
                $Socket_Handle_array[$arrayslot] = $newsocket
                $Node_Identifier_array[$arrayslot] = -1
                $Node_IP_array[$arrayslot] = -1
                TCPSend( $newsocket, "`"&_generateheader(2)&"`IP`" & $node_ext_IP & _generateheader(1))
                TCPSend( $newsocket, "`"&_generateheader(2)&"`ID`" & $node_Identifier & _generateheader(1))
                peer_broadcast_to_peer( $newsocket)
                $total_connected += 1
                Call( $newconnectionfunc, $newsocket, $iError)
            Else
                Call( $newconnectionfunc, 0, $iError)
            EndIf

        ElseIf $iEvent = $FD_CONNECT Then

            Call( $connectfunc, $newsocket, $iError)

            EndIf
        EndIf
EndFunc

func _generateheader($type=1)
$alpha = stringsplit("PRODY", "", 3)
$str = ""
if $type = 1 Then
$str = "--SIM:"
for $i=1 to 5
$str &= Random(0, 9, 1)&$alpha[Random(0, 4, 1)]
Next
Return $str
EndIf

if $type = 2 Then
$str = "--SIM:"
for $i=1 to 5
$str &= $alpha[Random(0, 4, 1)]&Random(0, 9, 1)
Next
Return $str
EndIf
EndFunc


Func Findfreearrayslot()
    $newConnNum = -1
    For $x = 1 To $max_connections
        If $Socket_Handle_array[$x] = -1 Then
            $newConnNum = $x
            ExitLoop
        EndIf
    Next
If $newConnNum = -1 Then Return "error";Didn't want it to be a number.
 Return $newConnNum
EndFunc

Func Opensocket_data_( $hWnd, $iMsgID, $WParam, $LParam )
    Local $iError = ___HiWord( $LParam )
    Local $iEvent = ___LoWord( $LParam )
    Abs($hWnd)
    local $Array_Slot = $iMsgID-0x400 ;No more loops to slow down message delievery!
    local $SocketID = $Socket_Handle_array[$Array_Slot]
    if $SocketID = -1 then return 0
    Switch $iEvent
        Case $FD_READ
                $rawrecv = TCPRecv($SocketID, 1024)
                $regex = StringRegExp($rawrecv, "--SIM:([0-9](.*?)[PRODY]){5}", 2)
                if IsArray($regex) Then
                    recvprocess( $rawrecv, $SocketID, $Array_Slot, $iError)
                Else
                 Do
                    $recvtmp = TCPRecv($SocketID, 1024)
                    $rawrecv &= $recvtmp
                    $regex = StringRegExp($rawrecv, "--SIM:([0-9](.*?)[PRODY]){5}", 2)
                 until IsArray($regex)
                    recvprocess( $rawrecv, $SocketID, $Array_Slot, $iError)
                EndIf

        Case $FD_CLOSE
                ___ASockShutdown($SocketID)
                TCPCloseSocket($SocketID)
                Call( $disconnectfunc, $SocketID, $iError)
                $Socket_Handle_array[$Array_Slot] = -1
                $Node_Identifier_array[$Array_Slot] = -1
                $Node_IP_array[$Array_Slot] = -1
                $Node_Peer_Reachable_list[$Array_Slot] = -1
                $total_connected -= 1
                if TimerDiff( $peer_timer) > 40000 Then
                    peer_broadcast()
                EndIf
            Case $FD_CONNECT
            If $iError Then
                if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Connection failed: " & $SocketID)
                $Socket_Handle_array[$Array_Slot] = -1
                $Node_Identifier_array[$Array_Slot] = -1
                $Node_IP_array[$Array_Slot] = -1
                $Node_Peer_Reachable_list[$Array_Slot] = -1
                $total_connected -= 1
                Call( $connectfunc, $SocketID, $iError)
            Else
                Call( $connectfunc, $SocketID, $iError)
                if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Connection established: " & $SocketID)
                TCPSend( $Socket_Handle_array[$Array_Slot], "`"&_generateheader(2)&"`IP`" & $node_ext_IP &_generateheader(1))
                TCPSend( $Socket_Handle_array[$Array_Slot], "`"&_generateheader(2)&"`ID`" & $node_Identifier &_generateheader(1))
                peer_broadcast_to_peer( $Socket_Handle_array[$Array_Slot])
            EndIf
                if TimerDiff( $peer_timer) > 40000 Then
                    peer_broadcast()
                EndIf
        EndSwitch
EndFunc

Func recvprocess( $rawrecv, $SocketID, $Array_Slot, $iError)
    if stringlen($rawrecv) < 1 then return 0
    $regex = StringRegExp($rawrecv, "--SIM:([0-9](.*?)[PRODY]){5}", 2)
    if IsArray($regex) Then
    local $Single_Data = StringSplit( $rawrecv, $regex[0], 1)
    Else
    local $Single_Data = $rawrecv
    EndIf
    if UBound($Single_Data) < 1 then Return
    for $k = 1 to $Single_Data[0] step 1
        if $Single_Data[$k] = "" then ContinueLoop ;Probably isn't nessesary.
        if $Single_Data[$k] = " " then ContinueLoop ;Disregard noise and crappy coders.

        if StringRegExp($Single_Data[$k], "--SIM:([PRODY](.*?)[0-9]){5}") Then
            node_data_process( $SocketID, $Single_Data[$k], $Array_Slot, $iError);must be node info to process.
        Else
        Call($recievefunc, $SocketID, $Single_Data[$k], $iError) ;Sends to user script
        EndIf
    Next
    if TimerDiff( $peer_timer) > 40000 Then
        peer_broadcast()
    EndIf
EndFunc

Func node_data_process( $SocketID, $Data, $Array_Slot, $iError)
    local $split = StringSplit( $Data, "`")
    if $split[3] = "IP" then
        $Node_IP_array[$Array_Slot] = $split[4]
        Call( $auxfunc, $SocketID, "IP", $split[4])
    EndIf
    if $split[3] = "ID" then
        $Node_Identifier_array[$Array_Slot] = $split[4]
        Call( $auxfunc, $SocketID, "ID", $split[4])
    EndIf
    if $split[3] = "PEER" then bootstrap( $SocketID, $split[4], $Array_Slot, $iError)
    if $split[3] = "IDLIST" then
        $Node_Peer_Reachable_list[$Array_Slot] = $split[4]
        Call( $auxfunc, $SocketID, "NODE-REACHABLE", $split[4])
    EndIf
    if $split[3] = "MESSAGE" then ;`8i8`MESSAGE
        Route_Message( $SocketID, $Data, $Array_Slot)
    EndIf
EndFunc

Func bootstrap( $SocketID, $split, $Array_Slot, $iError)
    if $Bootstrap_mode = $IPLOC_LOCAL then return 9;Bootstrapping disabled.
    if $total_connected >= $Bootstrap_max then return 8;Already connected to enough peers.
    local $connectpeers = Round( ($Bootstrap_max/$total_connected/2), 0) ;calculate how many peers we should attempt to connect to.
    if $connectpeers < $Bootstrap_max and $connectpeers = 0 then $connectpeers = 1
    if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Bootstrap stats: " & $connectpeers & ":" & $total_connected & "/" & $Bootstrap_max)
    $peers = StringSplit( $split, ";")

    For $d = 1 to $connectpeers step 1
        $error = False
        $rndarray = Random( 1, $peers[0], 1)
        if $peers[$rndarray] = "" or $peers[$rndarray] = " " then ContinueLoop
        For $u = 0 to $max_connections step 1 ;checks to see if already connected
            if $peers[$rndarray] = $Node_IP_array[$u] then
                if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Bootstrap: connectee already connected! reselecting...")
                $error = True
                ExitLoop
            EndIf
        Next
        if $error = True then ContinueLoop
        _P2P_Connect( $peers[$rndarray])
    Next
EndFunc

Func peer_broadcast()
    $peer_timer = TimerInit()
    local $peers = ""
    local $IDLIST = ""
    For $a = 0 to $max_connections step 1
        if $Node_IP_array[$a] <> -1 then $peers &= $Node_IP_array[$a] & ";"
        if $Node_Identifier_array[$a] <> -1 then $IDLIST &= $Node_Identifier_array[$a] & ";"
    Next
        _P2P_Broadcast( "`"&_generateheader(2)&"`PEER`" & $peers)
        _P2P_Broadcast( "`"&_generateheader(2)&"`IDLIST`" & $IDLIST)
EndFunc

Func peer_broadcast_to_peer( $socket)
    local $peers = ""
    local $IDLIST = ""
    For $a = 0 to $max_connections step 1
        if $Node_IP_array[$a] <> -1 then $peers &= $Node_IP_array[$a] & ";"
        if $Node_Identifier_array[$a] <> -1 then $IDLIST &= $Node_Identifier_array[$a] & ";"
    Next
    TCPSend( $socket, "`"&_generateheader(2)&"`PEER`" & $peers & _generateheader(1))
    TCPSend( $socket, "`"&_generateheader(2)&"`IDLIST`" & $IDLIST & _generateheader(1))
EndFunc

Func Route_Message( $Socket, $Message, $array_slot) ;process long distance messages
    if $console_out = True then ConsoleWrite( @CRLF & "P2P_: MessageRouting started")
    local $timer = TimerInit()
    local $split = StringSplit( $Message, "`")
    if $split[0] < 6 then return 1
    Local $ttl = $split[4]
    Local $from = $split[5]
    Local $address = $split[6]
    Local $identifier = $split[7]
    Local $begin = "`"&_generateheader(2)&"`MESSAGE`" & $ttl &"`"& $from & "`"& $address & "`" & $identifier & "`"
    Local $cutlen = StringLen( $Message) - StringLen( $begin)

    if idknown( $split[7]) = True then ;Have we seen it before? if yes-Terminate.
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message-ID known.")
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message Routing Finished: " & Round( TimerDiff( $timer), 1))
        return 1
    EndIf

    if $address = $node_Identifier then ;Is it for us? if yes-deliever.
        local $messagetrim = StringRight( $Message, $cutlen)
        local $messagetrim = StringRight( $Message, $cutlen)
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message-Inbound")
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message Routing Finished: " & Round( TimerDiff( $timer), 1))
        call( $messagefunc, $Socket, $messagetrim, $from, 0)
        return 1
    EndIf

    if $ttl = 0 then ;Is it too old? if yes-Terminate.
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message-TTL Exceeded.")
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message Routing Finished: " & Round( TimerDiff( $timer), 1))
        return 1
    EndIf
    ;Time to route the message.
    $messagefull = "`"&_generateheader(2)&"`MESSAGE`" & ($ttl-1) &"`"& $from & "`"& $address & "`" & $identifier & "`" & StringRight( $Message, $cutlen)
    if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Starting First level Routing: " & $total_connected)
    For $qwe = 0 to $max_connections step 1 ;Send if we are directly connected to the destination.
        if $address = $Node_Identifier_array[$qwe] then
            _P2P_Send( $Socket_Handle_array[$qwe], $messagefull)
            if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message-Destination located.")
            if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message Routing Finished: " & Round( TimerDiff( $timer), 1))
            return 1
        EndIf
    Next

    if $Socket = -1 Then ;If we created the message: Flood to all peers
        _P2P_Broadcast($messagefull)
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message Routing Finished: " & Round( TimerDiff( $timer), 1))
        return 1
    Else ;Or check every peer to see if it is connected to destination.
    For $qwe = 0 to $max_connections step 1 ;See if our peers are connected to the destination.
            if $Socket_Handle_array[$qwe] = -1 then ContinueLoop
            if StringInStr( $Node_Peer_Reachable_List[$qwe], $address) > 0 Then
                _P2P_Send( $Socket_Handle_array[$qwe], $messagefull)
                if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message-2nd Level destination located. ")
                if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message Routing Finished: " & Round( TimerDiff( $timer), 1))
                return 1
            EndIf
        Next
    EndIf
    For $qwe = 0 to $max_connections step 1 ;So the destination is not reachable within two levels. Time to pass it on. Don't pass it on to sender or sender's peers.
            if $Socket_Handle_array[$qwe] = -1 then ContinueLoop
            if $node_Identifier_array[$qwe] = $node_Identifier_array[$array_slot] then ContinueLoop
            if StringInStr( $Node_Peer_Reachable_List[$array_slot], $node_Identifier_array[$qwe]) > 0 Then ContinueLoop
            _P2P_Send( $Socket_Handle_array[$qwe], $messagefull)
    Next
    if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message Routing Finished: " & Round( TimerDiff( $timer), 1))
EndFunc

    ; `FUNCTION` ;===============================================================================
;
; Name...........: _P2P_Send_Message
; Description ...: Sends a long range message to a peer somewhere in the network.
; Syntax.........: _P2P_Send_Message( $Identifier, $data)
; Parameters ....:  $Identifier - The node Identifier/ID/Address of the destination.
;                   $Data       - Data/Message to send.
; Return values .:
; Author ........: Hyperzap
; Modified.......:
; Remarks .......: This, as opposed to the _P2P_Send function, will send a message to the
;                   destination regardless of whether they are connected or not, That is, you need
;                   not be directly TCP connected to someone for the message to reach them. This
;                   System works making your message 'hop' from node to node until one knows where
;                   your destination is. At that point, it is sent directly to the destination To
;                   be unpacked and processed.Please note that there is no way to know if the message
;                   reached it's destination, but if it is in range and online it will reach it
;                   99.5% of the time.
; Related .......:
; Link ..........;
; Example .......;
;
; ;==========================================================================================

Func _P2P_Send_Message( $IDaddress, $INdata, $from = 'Null')
    local $messageID = Round( ((Random( 0, 99999999999, 1)*@YDAY)/@MIN)*(Random(5, 1376, 1)/(@SEC*100)), 0) ;As random as it'l ever get.
    local $ttl = $STANDARD_MESSAGE_LIFE
    local $fullmessage = "`"&_generateheader(2)&"`MESSAGE`" & $ttl & "`"& $from & "`" & $IDaddress & "`" & $messageID & "`" & $INdata & _generateheader(1)
    if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Message generated: " & $messageID)
    Route_Message( -1, $fullmessage, -1)
EndFunc



Func idknown ($ID)
    for $IDcount = 0 to $total_ID_known step 1
        if $Known_ID[$IDcount] = $ID then Return True
    Next
    $total_ID_known += 1
    if $total_ID_known > 198 then $total_ID_known = 0
    $Known_ID[$total_ID_known] = $ID
        return False

EndFunc

; `FUNCTION` ;===============================================================================
;
; Name...........: _P2P_Send
; Description ...: Sends data to a peer.
; Syntax.........: _P2P_Send( $Socket, $Data)
; Parameters ....:  $Socket - peer socket handle.
;                   $Data   - Data to send.
; Return values .:
; Author ........: Hyperzap
; Modified.......:
; Remarks .......: This UDF will automatically keep your individual messages separate, So
;                   Don't worry about adding delays or message-split-buffer systems.
; Related .......:
; Link ..........;
; Example .......;
;
; ;==========================================================================================
Func _P2P_Send( $Socket, $Data)
    TCPSend( $Socket, $Data & _generateheader(1))
EndFunc

; `FUNCTION` ;===============================================================================
;
; Name...........: _P2P_Disconnect_Peer
; Description ...: Disconnects a peer (someone your connected to) from the system.
; Syntax.........: _P2P_Disconnect_Peer($Socket)
; Parameters ....: $Socket  - Socket of peer.
; Return values .: Success  - True
;                  Failure  - False
; Author ........: Hyperzap
; Modified.......:
; Remarks .......: The peer socket ($Socket) is the socket handler of ANY peer connected.
; Related .......:
; Link ..........;
; Example .......;
;
; ;==========================================================================================

Func _P2P_Disconnect_Peer( $socket)

    local $it_socket = ""
    local $array_slot = ""
    For $count = 0 to $max_connections step 1
        if $Socket_Handle_array[$count] = $socket then
            $it_socket = $socket
            $array_slot = $count
            ExitLoop
        EndIf
    Next
    if $it_socket = "" then return False
    ___ASockShutdown($it_socket)
    TCPCloseSocket($it_socket)
    $Socket_Handle_array[$Array_Slot] = -1
    $Node_Identifier_array[$Array_Slot] = -1
    $Node_IP_array[$Array_Slot] = -1
    $Node_Peer_Reachable_list[$Array_Slot] = -1
    if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Peer " & $it_socket & " closed.")
    return true
EndFunc

; `FUNCTION` ;===============================================================================
;
; Name...........: _P2P_Connect
; Description ...: Initiates a new connection to another node.
; Syntax.........: __P2P_Connect( $Conn_IP)
; Parameters ....:  $Conn_IP    - The IP address to connect to.
; Return values .: 0, 1, 2, 3 indicate failure due to criteria. Listen to the
;                   _P2P_Register_Event( $P2P_CONNECT etc to determine if it connected or not.
; Author ........: Hyperzap
; Modified.......:
; Remarks .......:
; Related .......:
; Link ..........;
; Example .......;
;
; ;==========================================================================================

Func _P2P_Connect( $Conn_IP)
    For $u = 0 to $max_connections step 1 ;checks to see if already connected
        if $Conn_IP = $Node_IP_array[$u] then
            if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Unable to connect-IP is already connected!")
            return 1
        EndIf
    Next

    if $Conn_IP = "" then Return 0
    if $Conn_IP = " " then Return 0
    if $Conn_IP = "0" then Return 0
    if $Conn_IP = ";" then Return 0
    if $Conn_IP = @CRLF then Return 0

    $arrayslot = Findfreearrayslot()
    if $arrayslot = "error" then
        if $Listening_Socket = "" Then
            if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Unable to connect-node services offline!")
            Return 3
        EndIf
        if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Unable to connect-peer limit reached!")
        return 2 ;no free slots to put your new connection!
    EndIf
    if $console_out = True then ConsoleWrite( @CRLF & "P2P_: Attempting Connection: " & $Conn_IP)
    local $SocketID = ___ASocket()
    ___ASockSelect( $SocketID, $__TCP_WINDOW, 0x400 + $arrayslot, BitOR( $FD_CONNECT, $FD_READ, $FD_CLOSE))
    GUIRegisterMsg( 0x400 + $arrayslot, "Opensocket_data_" )
    $Socket_Handle_array[$arrayslot] = $SocketID
    $Node_Identifier_array[$arrayslot] = -1
    $Node_IP_array[$arrayslot] = $Conn_IP
    $return = ___ASockConnect( $SocketID, $Conn_IP, $node_Port )
    $total_connected += 1
    If @extended Then
        if $console_out = True then ConsoleWrite( @CRLF & "_P2P: Connection Established.")
        Call( $connectfunc, $SocketID, 0);connected immediately!
    EndIf
EndFunc

; `FUNCTION` ;===============================================================================
;
; Name...........: _P2P_Broadcast
; Description ...: Sends data to all connected peers.
; Syntax.........: _P2P_Broadcast($Data)
; Parameters ....:  $Data   - The data to send.
; Return values .: True
; Author ........: Hyperzap
; Modified.......:
; Remarks .......:
; Related .......:
; Link ..........;
; Example .......;
;
; ;==========================================================================================

Func _P2P_Broadcast($Data)
    Local $i
    For $i = 0 to $max_connections step 1
        If $Socket_Handle_array[$i] <> -1 Then TCPSend($Socket_Handle_array[$i], $Data & _generateheader(1))
    Next
    Return True
EndFunc


; `FUNCTION` ;===============================================================================
;
; Name...........: _P2P_Peerlist
; Description ...: Returns the sockets, IDs, and IPs of all connected peers.
; Syntax.........: _P2P_Peerlist()
; Parameters ....:
; Return values .: A 3 dimensional array of all connected peers. The first spot in the array,
;                   AKA [0][0] defines the number of connected peers. The remaining spots
;                   In the array are the actual peers in the format of dimension [0] socket
;                   handle, [1] ID, and [2] IP. So the first peer will be [1][0], [1][1]. [1][2]
;                   and the second [2][0], [2][1], [2][2] etc.
; Author ........: Hyperzap
; Modified.......:
; Remarks .......:
; Related .......:
; Link ..........;
; Example .......;
;
; ;==========================================================================================
Func _P2P_Peerlist()

    Local $aList[$max_connections+1][3], $alist_count = 1
    For $i = 1 to $max_connections
        If $Socket_Handle_array[$i] <> -1 Then
            $aList[$alist_count][0] = $Socket_Handle_array[$i]
            $aList[$alist_count][1] = $Node_Identifier_array[$i]
            $aList[$alist_count][2] = $Node_IP_array[$i]
            $alist_count += 1
        EndIf
    Next

    $aList[0][0] = $alist_count

    Return $alist

EndFunc

; `FUNCTION` ;===============================================================================
;
; Name...........: _P2P_Register_Event
; Description ...: Registers an event.So, if I register my function "ant" with the event
;                   $P2P_RECEIVE, it will look like: _P2P_Register_Event($P2P_RECEIVE, "ant").
;                   It will mean my function 'ant' will get called with the specified parameters
;                   (see below) when data is recieved.
; Syntax.........: _P2P_Register_Event($iEvent, $sFunction)
; Parameters ....:  $iEvent     - Event number. It can be any these values:

;                           Event number            This is the required syntax of YOUR called function

;                           $P2P_AUX_DATA           ; Function ($hSocket, $DataType, $Data)
                                ;When things like IP and Node identifier are discovered.
;                           $P2P_MESSAGE            ; Function ($hSocket, $message, $from, $iError)
                                ;When long distance messages are recieved.
;                           $P2P_RECEIVE            ; Function ($hSocket, $sReceived, $iError)
                                ;When data is recieved directly from a connected peer.
;                           $P2P_CONNECT            ; Function ($hSocket, $iError)
                                ;This is called when an attempted connection is successful or unsuccessful.
;                           $P2P_DISCONNECT         ; Function ($hSocket, $iError)
                                ;This is called whenever a peer disconnects from you.
;                           $P2P_NEWCONNECTION      ; Function ($hSocket, $iError)
                                ;This is called whenever a peer connects to you.
; Return values .: Success  - True
;                  Failure  - False
; Author ........: Kip
; Modified.......: Hyperzap
; Remarks .......:
; Related .......:
; Link ..........;
; Example .......;
;
; ;==========================================================================================


Func _P2P_Register_Event($iEvent, $sFunction)
    if $iEvent = $P2P_AUX_DATA then $auxfunc = $sFunction
    if $iEvent = $P2P_RECEIVE then $recievefunc = $sFunction
    if $iEvent = $P2P_CONNECT then $connectfunc = $sFunction
    if $iEvent = $P2P_DISCONNECT then $disconnectfunc = $sFunction
    if $iEvent = $P2P_NEWCONNECTION then $newconnectionfunc = $sFunction
    if $iEvent = $P2P_MESSAGE then $messagefunc = $sFunction
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

Func _Base64Decode($Data)
    Local $Opcode = "0xC81000005356578365F800E8500000003EFFFFFF3F3435363738393A3B3C3DFFFFFF00FFFFFF000102030405060708090A0B0C0D0E0F10111213141516171819FFFFFFFFFFFF1A1B1C1D1E1F202122232425262728292A2B2C2D2E2F303132338F45F08B7D0C8B5D0831D2E9910000008365FC00837DFC047D548A034384C0750383EA033C3D75094A803B3D75014AB00084C0751A837DFC047D0D8B75FCC64435F400FF45FCEBED6A018F45F8EB1F3C2B72193C7A77150FB6F083EE2B0375F08A068B75FC884435F4FF45FCEBA68D75F4668B06C0E002C0EC0408E08807668B4601C0E004C0EC0208E08847018A4602C0E00624C00A46038847028D7F038D5203837DF8000F8465FFFFFF89D05F5E5BC9C21000"

    Local $CodeBuffer = DllStructCreate("byte[" & BinaryLen($Opcode) & "]")
    DllStructSetData($CodeBuffer, 1, $Opcode)

    Local $Ouput = DllStructCreate("byte[" & BinaryLen($Data) & "]")
    Local $Ret = DllCall("user32.dll", "int", "CallWindowProc", "ptr", DllStructGetPtr($CodeBuffer), _
                                                    "str", $Data, _
                                                    "ptr", DllStructGetPtr($Ouput), _
                                                    "int", 0, _
                                                    "int", 0)

    Return BinaryMid(DllStructGetData($Ouput, 1), 1, $Ret[0])
EndFunc

Func _Base64Encode($Data, $LineBreak = 76)
    Local $Opcode = "0x5589E5FF7514535657E8410000004142434445464748494A4B4C4D4E4F505152535455565758595A6162636465666768696A6B6C6D6E6F707172737475767778797A303132333435363738392B2F005A8B5D088B7D108B4D0CE98F0000000FB633C1EE0201D68A06880731C083F901760C0FB6430125F0000000C1E8040FB63383E603C1E60409C601D68A0688470183F90176210FB6430225C0000000C1E8060FB6730183E60FC1E60209C601D68A06884702EB04C647023D83F90276100FB6730283E63F01D68A06884703EB04C647033D8D5B038D7F0483E903836DFC04750C8B45148945FC66B80D0A66AB85C90F8F69FFFFFFC607005F5E5BC9C21000"

    Local $CodeBuffer = DllStructCreate("byte[" & BinaryLen($Opcode) & "]")
    DllStructSetData($CodeBuffer, 1, $Opcode)

    $Data = Binary($Data)
    Local $Input = DllStructCreate("byte[" & BinaryLen($Data) & "]")
    DllStructSetData($Input, 1, $Data)

    $LineBreak = Floor($LineBreak / 4) * 4
    Local $OputputSize = Ceiling(BinaryLen($Data) * 4 / 3)
    $OputputSize = $OputputSize + Ceiling($OputputSize / $LineBreak) * 2 + 4

    Local $Ouput = DllStructCreate("char[" & $OputputSize & "]")
    DllCall("user32.dll", "none", "CallWindowProc", "ptr", DllStructGetPtr($CodeBuffer), _
                                                    "ptr", DllStructGetPtr($Input), _
                                                    "int", BinaryLen($Data), _
                                                    "ptr", DllStructGetPtr($Ouput), _
                                                    "uint", $LineBreak)
    Return DllStructGetData($Ouput, 1)
EndFunc

Func _message($HSocket, $message, $from, $iError)
    ConsoleWrite(@CRLF & "FROM: " & $from)
    ConsoleWrite(@CRLF & "DATA: " & $message)
    ConsoleWrite(@CRLF & "Length: " & StringLen($message))
EndFunc
Func _send()
    _P2P_send_message(InputBox("Destination", "Send to?"),InputBox("text", "text"),"test")
EndFunc
As always thanks for the help! you should be able to run the code as is by removing the if commandline condition, after about 5 minutes you will notice it no longer responds by pressing ctrl+shift+p (new peer window)

 

Edit: realized I left out 2 required functions. Also added a line to log how long the process runs before it freezes.

Edit: Added required global variables, includes, and consolidated the script to one code box.

Edited by nullschritt

Share this post


Link to post
Share on other sites



The problem actually send to be somewhere in the sending process, if too large a message is sent, then for some reason goes into an infinite loop doing nothing.

Just some speculation, I believe the problem may be with the way the p2p UDF handles outgoing data

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0