jvanegmond Posted January 7, 2010 Share Posted January 7, 2010 (edited) I couldn't figure out how to do this at first, and spent some sweat. "Never again!" I said to myself, and posted it on the forum. This is how you should do it (simple method): expandcollapse popup#include <Array.au3> $routerList = _GetIpAddressList("192.168.0-2.0-1") _ArrayDisplay($routerList) $clientList = _GetIpAddressList("192.168.0-2.100-110") _ArrayDisplay($clientList) $randomTest = _GetIpAddressList("0-2.2-4.4-6.6-8") _ArrayDisplay($randomTest) Func _GetIpAddressList($ipFormat) $ipFormat = StringReplace($ipFormat, "*", "1-255") $ipSplit = StringSplit($ipFormat, ".") Local $ipRange[4][2], $totalPermu = 1 For $i = 0 To 3 If StringInStr($ipSplit[$i+1], "-") Then $m = StringSplit($ipSplit[$i+1],"-") $ipRange[$i][0] = $m[1] $ipRange[$i][1] = $m[2] Else $n = Number($ipSplit[$i+1]) $ipRange[$i][0] = $n $ipRange[$i][1] = $n EndIf $totalPermu *= $ipRange[$i][1] - $ipRange[$i][0] + 1 Next Local $result[$totalPermu], $i = 0 For $a = $ipRange[0][0] To $ipRange[0][1] For $b = $ipRange[1][0] To $ipRange[1][1] For $c = $ipRange[2][0] To $ipRange[2][1] For $d = $ipRange[3][0] To $ipRange[3][1] $result[$i] = $a & "." & $b & "." & $c & "." & $d $i += 1 Next Next Next Next Return $result EndFunc ;==>_GetIpAddressList This is what I wasted my time on the first time: expandcollapse popup#include <Array.au3> $routerList = _GetIpAddressList("192.168.0-2.0-1") _ArrayDisplay($routerList) $clientList = _GetIpAddressList("192.168.0-2.100-110") _ArrayDisplay($clientList) $randomTest = _GetIpAddressList("0-2.2-4.4-6.6-8") _ArrayDisplay($randomTest) Func _GetIpAddressList($ipFormat) $ipFormat = StringReplace($ipFormat, "*", "1-255") $ipSplit = StringSplit($ipFormat, ".") Local $ipDef[4], $totalPermu = 1, $curPart[4] For $i = 0 To 3 $range = _GetIpAddressArray($ipSplit[$i + 1]) $curPart[$i] = $range[0] $totalPermu *= $range[1] - $range[0] + 1 $ipDef[$i] = $range Next Local $result[$totalPermu] $m = 0 While 1 $result[$m] = $curPart[0] & "." & $curPart[1] & "." & $curPart[2] & "." & $curPart[3] $m += 1 $add = 1 For $i = 3 To 0 Step -1 If $add Then $n = _GetIpAddressAdder($ipDef[$i]) $curPart[$i] = $n[0] $add = $n[1] EndIf Next If $add Then ExitLoop EndIf WEnd Return $result EndFunc ;==>_GetIpAddressList Func _GetIpAddressAdder(ByRef $range) Local $ret[2] = [0, 0] $range[2] += 1 If $range[2] > $range[1] Then $ret[1] = 1 $range[2] = $range[0] EndIf $ret[0] = $range[2] Return $ret EndFunc ;==>_GetIpAddressAdder Func _GetIpAddressArray($range) Local $ret[3] If StringInStr($range, "-") Then $lSplit = StringSplit($range, "-") $lStart = $lSplit[1] $lStop = $lSplit[2] $lCount = $lStop - $lStart + 1 $ret[0] = $lStart $ret[1] = $lStop $ret[2] = $ret[0] Else $n = Number($range) $ret[0] = $n $ret[1] = $n $ret[2] = $n EndIf Return $ret EndFunc ;==>_GetIpAddressArray Edited January 8, 2010 by Manadar github.com/jvanegmond Link to comment Share on other sites More sharing options...
spudw2k Posted January 7, 2010 Share Posted January 7, 2010 Just out of curiosity, what drove you to need such a func? I'd add some error checking as well (my two cents). Spoiler Things I've Made: Always On Top Tool ◊ AU History ◊ Deck of Cards ◊ HideIt ◊ ICU ◊ Icon Freezer ◊ Ipod Ejector ◊ Junos Configuration Explorer ◊ Link Downloader ◊ MD5 Folder Enumerator ◊ PassGen ◊ Ping Tool ◊ Quick NIC ◊ Read OCR ◊ RemoteIT ◊ SchTasksGui ◊ SpyCam ◊ System Scan Report Tool ◊ System UpTime ◊ Transparency Machine ◊ VMWare ESX BuilderMisc Code Snippets: ADODB Example ◊ CheckHover ◊ Detect SafeMode ◊ DynEnumArray ◊ GetNetStatData ◊ HashArray ◊ IsBetweenDates ◊ Local Admins ◊ Make Choice ◊ Recursive File List ◊ Remove Sizebox Style ◊ Retrieve PNPDeviceID ◊ Retreive SysListView32 Contents ◊ Set IE Homepage ◊ Tickle Expired Password ◊ Transpose ArrayProjects: Drive Space Usage GUI ◊ LEDkIT ◊ Plasma_kIt ◊ Scan Engine Builder ◊ SpeeDBurner ◊ SubnetCalcCool Stuff: AutoItObject UDF ◊ Extract Icon From Proc ◊ GuiCtrlFontRotate ◊ Hex Edit Funcs ◊ Run binary ◊ Service_UDF Link to comment Share on other sites More sharing options...
James Posted January 7, 2010 Share Posted January 7, 2010 I still hate your Manadar... This function drove me crazy Blog - Seriously epic web hosting - Twitter - GitHub - Cachet HQ Link to comment Share on other sites More sharing options...
SoulA Posted January 8, 2010 Share Posted January 8, 2010 Very nice. Link to comment Share on other sites More sharing options...
jvanegmond Posted January 8, 2010 Author Share Posted January 8, 2010 Just out of curiosity, what drove you to need such a func? I'd add some error checking as well (my two cents).This thread did. I can combine these scripts to make a pretty awesome network prober. github.com/jvanegmond Link to comment Share on other sites More sharing options...
jvanegmond Posted January 8, 2010 Author Share Posted January 8, 2010 I come into work today, and talk with my coworkers about this problem that I solved last night. I tell them I wanted to do it recursively, but failed that and did it sequentially which was much harder. I talk a bit about the problem and how complicated it was until someone says; That's just 4 For-Next loops. I could punch myself in the face at that point. Last night I posed the restriction on myself of using a recursive method, meaning I couldn't use the 4 for-loops method, after losing interest in the recursive method I never reconsidered I could use the 4 for-loops method. I've now redone it, which took about 5 minutes. Although, I guess the old code was nice too, because it's probably more ip v6 compatible. (ergo; Needs less changes.) github.com/jvanegmond Link to comment Share on other sites More sharing options...
James Posted January 8, 2010 Share Posted January 8, 2010 (edited) I come into work today, and talk with my coworkers about this problem that I solved last night. I tell them I wanted to do it recursively, but failed that and did it sequentially which was much harder. I talk a bit about the problem and how complicated it was until someone says; That's just 4 For-Next loops.I could punch myself in the face at that point.That's the approach I was taking, but I couldn't think it through.I'll punch you in the face though. Since it's your birthday, I'll let you off Edited January 8, 2010 by JamesBrooks Blog - Seriously epic web hosting - Twitter - GitHub - Cachet HQ Link to comment Share on other sites More sharing options...
Skrip Posted January 9, 2010 Share Posted January 9, 2010 Very nice function. I definitely will use this. [left][sub]We're trapped in the belly of this horrible machine.[/sub][sup]And the machine is bleeding to death...[/sup][sup][/sup][/left] Link to comment Share on other sites More sharing options...
SoulA Posted January 9, 2010 Share Posted January 9, 2010 This function should be an official UDF once it gets error checking. Anyway you can throw that in there? You have come this far. Link to comment Share on other sites More sharing options...
SoulA Posted January 9, 2010 Share Posted January 9, 2010 So I got some time to mess around with this and I have to admit it was pretty fun. Here are some tweaks on the function to add some minimal error checking. Also, below that is a combination of the script you had in the other thread and the script you posted here. End result was a small network prober as you mentioned. expandcollapse popupFunc _GetIpAddressList($ipFormat) Local $aResult[1] $aResult[0] = 0 If StringInStr(StringStripWS($ipFormat, 3), " ") Or StringInStr($ipFormat, ".", "", 4) Then Return $aResult $ipFormat = StringReplace($ipFormat, "*", "1-255") $ipSplit = StringSplit($ipFormat, ".") Local $ipRange[4][2], $totalPermu = 1 For $i = 0 To 3 If StringInStr($ipSplit[$i + 1], "-") Then If StringInStr($ipSplit[$i + 1], "-", "", 2) Then Return $aResult $m = StringSplit($ipSplit[$i +1 ],"-") For $i2 = 1 to $m[0] If Number($m[$i2]) > 255 Then Return $aResult $ipRange[$i][$i2 - 1] = Number($m[$i2]) Next Else $n = Number($ipSplit[$i + 1]) If $n > 255 Then Return $aResult $ipRange[$i][0] = $n $ipRange[$i][1] = $n EndIf $totalPermu *= $ipRange[$i][1] - $ipRange[$i][0] + 1 Next Local $aResult[$totalPermu + 1], $i = 1 For $a = $ipRange[0][0] To $ipRange[0][1] For $b = $ipRange[1][0] To $ipRange[1][1] For $c = $ipRange[2][0] To $ipRange[2][1] For $d = $ipRange[3][0] To $ipRange[3][1] $aResult[$i] = $a & "." & $b & "." & $c & "." & $d $i += 1 Next Next Next Next $aResult[0] = $i - 1 Return $aResult EndFunc ;==>_GetIpAddressList expandcollapse popup#include <ButtonConstants.au3> #include <GUIConstantsEx.au3> #include <WindowsConstants.au3> #include <Constants.au3> AutoItSetOption("GUIOnEventMode", 1) $hGUI = GUICreate("Alive", 348, 303, 190, 130) $hGo = GUICtrlCreateButton("Go", 250, 8, 57, 25, 0) $hInput = GUICtrlCreateInput("", 15, 10, 200) $hList = GUICtrlCreateList("", 15, 64, 313, 193) $hClear = GUICtrlCreateButton("Clear", 120, 272, 89, 25, 0) GUICtrlSetOnEvent($hGo, "alive") GUICtrlSetOnEvent($hClear, "clear") GUISetOnEvent($GUI_EVENT_CLOSE, "_Exit") GUICtrlSetState($hInput, $GUI_FOCUS) GUISetState(@SW_SHOW) While 1 Sleep(50) If _IsPressed("0D") Then alive() WEnd Func alive() $sAddress = GUICtrlRead($hInput) If $sAddress = "" Then MsgBox(0, "Error", "Input was null", 0, $hGUI) Return EndIf GUICtrlSetState($hGo, $GUI_DISABLE) GUICtrlSetState($hClear, $GUI_DISABLE) $aArray = _GetIpAddressList($sAddress) If $aArray[0] = 0 Then MsgBox(0, "Error", "Input was incorrect. Check syntax.", 0, $hGUI) enableButtons() Return EndIf Local Const $MAX_PROCESS = 10 ; We spawn a maximum of 10 processes at once Local $aProcess[$MAX_PROCESS] ; An array to keep a reference to spawned processes, in the next loop we fill it with value 0 For $i = 0 to UBound($aProcess) - 1 $aProcess[$i] = 0 Next Local $i = 1 Local $iFinished = 1 While True For $n = 0 to UBound($aProcess) - 1 If ($i <> UBound($aArray) AND $aProcess[$n] == 0) Then ; Check if we need a spot, and there is an existing spot $aProcess[$n] = _MSPing($aArray[$i]) $i += 1 Else If ($aProcess[$n] <> 0 And _MSPingIsReady($aProcess[$n])) Then $sHostname = _MSPingGetHostname($aProcess[$n]) $sResult = _MSPingGetResult($aProcess[$n]) If ($sResult <> -1) Then GUICtrlSetData($hList, $sHostname & " is alive " & $sResult & " milliseconds" & @CRLF) Else GUICtrlSetData($hList, $sHostname & " is dead" & @CRLF) EndIf ; Free up an empty space for the next address to Ping $aProcess[$n] = 0 $iFinished += 1 ; <=== New line If ($iFinished == UBound($aArray)) Then ExitLoop 2 ; Return EndIf EndIf Next Sleep(50) ; Give existing ping commands some time to process the request WEnd enableButtons() EndFunc Func enableButtons() GUICtrlSetState($hGo, @SW_ENABLE) GUICtrlSetState($hClear, @SW_ENABLE) EndFunc Func clear() GUICtrlSetData($hList, "") EndFunc Func _GetIpAddressList($ipFormat) Local $aResult[1] $aResult[0] = 0 If StringInStr(StringStripWS($ipFormat, 3), " ") Or StringInStr($ipFormat, ".", "", 4) Then Return $aResult $ipFormat = StringReplace($ipFormat, "*", "1-255") $ipSplit = StringSplit($ipFormat, ".") Local $ipRange[4][2], $totalPermu = 1 For $i = 0 To 3 If StringInStr($ipSplit[$i + 1], "-") Then If StringInStr($ipSplit[$i + 1], "-", "", 2) Then Return $aResult $m = StringSplit($ipSplit[$i +1 ],"-") For $i2 = 1 to $m[0] If Number($m[$i2]) > 255 Then Return $aResult $ipRange[$i][$i2 - 1] = Number($m[$i2]) Next Else $n = Number($ipSplit[$i + 1]) If $n > 255 Then Return $aResult $ipRange[$i][0] = $n $ipRange[$i][1] = $n EndIf $totalPermu *= $ipRange[$i][1] - $ipRange[$i][0] + 1 Next Local $aResult[$totalPermu + 1], $i = 1 For $a = $ipRange[0][0] To $ipRange[0][1] For $b = $ipRange[1][0] To $ipRange[1][1] For $c = $ipRange[2][0] To $ipRange[2][1] For $d = $ipRange[3][0] To $ipRange[3][1] $aResult[$i] = $a & "." & $b & "." & $c & "." & $d $i += 1 Next Next Next Next $aResult[0] = $i - 1 Return $aResult EndFunc ;==>_GetIpAddressList Func _Exit() Exit EndFunc Func _MSPing($sHostname, $timeout = 50) Local $return_struc[4] ; [0] = Result (in ms) ; [1] = The hostname originally used ; [2] = Process handle (for internal use only) ; [3] = Buffer (for internal use only) $return_struc[1] = $sHostname $return_struc[2] = Run("ping " & $sHostname & " -n 1 -w " & $timeout, "", @SW_HIDE, $STDOUT_CHILD) Return $return_struc EndFunc Func _MSPingIsReady(ByRef $return_struc) Return ___MSPingReadOutput($return_struc) EndFunc Func _MSPingGetResult($return_struc) Return $return_struc[0] EndFunc Func _MSPingGetHostname($return_struc) Return $return_struc[1] EndFunc ; Internal use only Func ___MSPingReadOutput(ByRef $return_struc) $data = StdoutRead($return_struc[2]) If (@error) Then ___MSPingParseResult($return_struc) Return 1 Else $return_struc[3] &= $data Return 0 EndIf EndFunc ; Internal use only Func ___MSPingParseResult(ByRef $return_struc) $result = StringRegExp($return_struc[3], "([0-9]*)ms", 3) If @error Then $return_struc[0] = -1 Else $return_struc[0] = $result[0] EndIf EndFunc Func _IsPressed($sHexKey, $vDLL = 'user32.dll') ; $hexKey must be the value of one of the keys. ; _Is_Key_Pressed will return 0 if the key is not pressed, 1 if it is. Local $a_R = DllCall($vDLL, "int", "GetAsyncKeyState", "int", '0x' & $sHexKey) If Not @error And BitAND($a_R[0], 0x8000) = 0x8000 Then Return 1 Return 0 EndFunc ;==>_IsPressed Link to comment Share on other sites More sharing options...
SoulA Posted January 10, 2010 Share Posted January 10, 2010 Here is a better GUI based off of llewxam's GUI posted in the thread previously. expandcollapse popup#include <ButtonConstants.au3> #include <GUIConstantsEx.au3> #include <WindowsConstants.au3> #include <Constants.au3> AutoItSetOption("GUIOnEventMode", 1) Global $MAX_PROCESS = 10 ; We spawn a maximum of 10 processes at once $hDefault = GUICreate("") $hGUI = GUICreate("Alive", 375, 300) $hGo = GUICtrlCreateButton("Go", 230, 10, 57, 25) $hInput = GUICtrlCreateInput("", 15, 10, 200) $hAlive = GUICtrlCreateList("", 15, 64, 165, 200) $hDead = GUICtrlCreateList("", 200, 64, 165, 200) $hClear = GUICtrlCreateButton("Clear", 150, 275, 89, 25) $hExample = GUICtrlCreateLabel("Ex. 192.168.1.* or 192.168.1-2.1-10", 15, 40) $hAliveLabel = GUICtrlCreateLabel("Alive", 85, 255) $hDeadLabel = GUICtrlCreateLabel("Dead", 275, 255) $hProg = GUICtrlCreateProgress(200, 40, 165) $hMaxProc = GUICtrlCreateInput($MAX_PROCESS, 335, 10, 30) $hMaxProcLabel = GUICtrlCreateLabel("Max" & @CRLF & "Proc's", 295, 5, 30, 30) GUICtrlSetOnEvent($hGo, "alive") GUICtrlSetOnEvent($hClear, "clear") GUISetOnEvent($GUI_EVENT_CLOSE, "_Exit") GUICtrlSetState($hInput, $GUI_FOCUS) GUISetState(@SW_SHOW) While 1 Sleep(50) If _IsPressed("0D") And WinActive($hGUI) Then alive() WEnd Func alive() GUICtrlSetState($hGo, $GUI_DISABLE) GUICtrlSetState($hClear, $GUI_DISABLE) $sAddress = GUICtrlRead($hInput) If $sAddress = "" Then error1("Input was null") Return EndIf $aArray = _GetIpAddressList($sAddress) If $aArray[0] = 0 Then error1("Input was incorrect. Check syntax.") Return EndIf $MAX_PROCESS = GUICtrlRead($hMaxProc) If $MAX_PROCESS = 0 Then $MAX_PROCESS = 1 Local $aProcess[$MAX_PROCESS] ; An array to keep a reference to spawned processes, in the next loop we fill it with value 0 For $i = 0 to UBound($aProcess) - 1 $aProcess[$i] = 0 Next Local $i = 1 Local $iFinished = 1 While True For $n = 0 to UBound($aProcess) - 1 If ($i <> UBound($aArray) AND $aProcess[$n] == 0) Then ; Check if we need a spot, and there is an existing spot $aProcess[$n] = _MSPing($aArray[$i]) $i += 1 Else If ($aProcess[$n] <> 0 And _MSPingIsReady($aProcess[$n])) Then GUICtrlSetData($hProg, ($iFinished / 255) * 100) $sHostname = _MSPingGetHostname($aProcess[$n]) $sResult = _MSPingGetResult($aProcess[$n]) If ($sResult <> -1) Then GUICtrlSetData($hAlive, $sHostname & " is alive " & $sResult & " ms" & @CRLF) Else GUICtrlSetData($hDead, $sHostname & " is dead" & @CRLF) EndIf ; Free up an empty space for the next address to Ping $aProcess[$n] = 0 $iFinished += 1 ; <=== New line If ($iFinished == UBound($aArray)) Then ExitLoop 2 ; Return EndIf EndIf Next Sleep(50) ; Give existing ping commands some time to process the request WEnd GUICtrlSetData($hProg, 0) enableButtons() EndFunc Func error1($sMessage) MsgBox(0, "Error", $sMessage, 0, $hDefault) Sleep(50) enableButtons() GUICtrlSetState($hInput, $GUI_FOCUS) EndFunc Func enableButtons() GUICtrlSetState($hGo, @SW_ENABLE) GUICtrlSetState($hClear, @SW_ENABLE) EndFunc Func clear() GUICtrlSetData($hAlive, "") GUICtrlSetData($hDead, "") EndFunc Func _GetIpAddressList($ipFormat) Local $aResult[1] $aResult[0] = 0 If StringInStr(StringStripWS($ipFormat, 3), " ") Or StringInStr($ipFormat, ".", "", 4) Then Return $aResult $ipFormat = StringReplace($ipFormat, "*", "1-255") $ipSplit = StringSplit($ipFormat, ".") Local $ipRange[4][2], $totalPermu = 1 For $i = 0 To 3 If StringInStr($ipSplit[$i + 1], "-") Then If StringInStr($ipSplit[$i + 1], "-", "", 2) Then Return $aResult $m = StringSplit($ipSplit[$i +1 ],"-") For $i2 = 1 to $m[0] If Number($m[$i2]) > 255 Or Number($m[$i2]) < 0 Then Return $aResult $ipRange[$i][$i2 - 1] = Number($m[$i2]) Next Else $n = Number($ipSplit[$i + 1]) If $n > 255 Or $n < 0 Then Return $aResult $ipRange[$i][0] = $n $ipRange[$i][1] = $n EndIf $totalPermu *= $ipRange[$i][1] - $ipRange[$i][0] + 1 Next Local $aResult[$totalPermu + 1], $i = 1 For $a = $ipRange[0][0] To $ipRange[0][1] For $b = $ipRange[1][0] To $ipRange[1][1] For $c = $ipRange[2][0] To $ipRange[2][1] For $d = $ipRange[3][0] To $ipRange[3][1] $aResult[$i] = $a & "." & $b & "." & $c & "." & $d $i += 1 Next Next Next Next $aResult[0] = $i - 1 Return $aResult EndFunc ;==>_GetIpAddressList Func _Exit() Exit EndFunc Func _MSPing($sHostname, $timeout = 50) Local $return_struc[4] ; [0] = Result (in ms) ; [1] = The hostname originally used ; [2] = Process handle (for internal use only) ; [3] = Buffer (for internal use only) $return_struc[1] = $sHostname $return_struc[2] = Run("ping " & $sHostname & " -n 1 -w " & $timeout, "", @SW_HIDE, $STDOUT_CHILD) Return $return_struc EndFunc Func _MSPingIsReady(ByRef $return_struc) Return ___MSPingReadOutput($return_struc) EndFunc Func _MSPingGetResult($return_struc) Return $return_struc[0] EndFunc Func _MSPingGetHostname($return_struc) Return $return_struc[1] EndFunc ; Internal use only Func ___MSPingReadOutput(ByRef $return_struc) $data = StdoutRead($return_struc[2]) If (@error) Then ___MSPingParseResult($return_struc) Return 1 Else $return_struc[3] &= $data Return 0 EndIf EndFunc ; Internal use only Func ___MSPingParseResult(ByRef $return_struc) $result = StringRegExp($return_struc[3], "([0-9]*)ms", 3) If @error Then $return_struc[0] = -1 Else $return_struc[0] = $result[0] EndIf EndFunc Func _IsPressed($sHexKey, $vDLL = 'user32.dll') ; $hexKey must be the value of one of the keys. ; _Is_Key_Pressed will return 0 if the key is not pressed, 1 if it is. Local $a_R = DllCall($vDLL, "int", "GetAsyncKeyState", "int", '0x' & $sHexKey) If Not @error And BitAND($a_R[0], 0x8000) = 0x8000 Then Return 1 Return 0 EndFunc ;==>_IsPressed Link to comment Share on other sites More sharing options...
jvanegmond Posted January 11, 2010 Author Share Posted January 11, 2010 (edited) Here is a better GUI based off of llewxam's GUI posted in the thread previously. expandcollapse popup#include <ButtonConstants.au3> #include <GUIConstantsEx.au3> #include <WindowsConstants.au3> #include <Constants.au3> AutoItSetOption("GUIOnEventMode", 1) Global $MAX_PROCESS = 10 ; We spawn a maximum of 10 processes at once $hDefault = GUICreate("") $hGUI = GUICreate("Alive", 375, 300) $hGo = GUICtrlCreateButton("Go", 230, 10, 57, 25) $hInput = GUICtrlCreateInput("", 15, 10, 200) $hAlive = GUICtrlCreateList("", 15, 64, 165, 200) $hDead = GUICtrlCreateList("", 200, 64, 165, 200) $hClear = GUICtrlCreateButton("Clear", 150, 275, 89, 25) $hExample = GUICtrlCreateLabel("Ex. 192.168.1.* or 192.168.1-2.1-10", 15, 40) $hAliveLabel = GUICtrlCreateLabel("Alive", 85, 255) $hDeadLabel = GUICtrlCreateLabel("Dead", 275, 255) $hProg = GUICtrlCreateProgress(200, 40, 165) $hMaxProc = GUICtrlCreateInput($MAX_PROCESS, 335, 10, 30) $hMaxProcLabel = GUICtrlCreateLabel("Max" & @CRLF & "Proc's", 295, 5, 30, 30) GUICtrlSetOnEvent($hGo, "alive") GUICtrlSetOnEvent($hClear, "clear") GUISetOnEvent($GUI_EVENT_CLOSE, "_Exit") GUICtrlSetState($hInput, $GUI_FOCUS) GUISetState(@SW_SHOW) While 1 Sleep(50) If _IsPressed("0D") And WinActive($hGUI) Then alive() WEnd Func alive() GUICtrlSetState($hGo, $GUI_DISABLE) GUICtrlSetState($hClear, $GUI_DISABLE) $sAddress = GUICtrlRead($hInput) If $sAddress = "" Then error1("Input was null") Return EndIf $aArray = _GetIpAddressList($sAddress) If $aArray[0] = 0 Then error1("Input was incorrect. Check syntax.") Return EndIf $MAX_PROCESS = GUICtrlRead($hMaxProc) If $MAX_PROCESS = 0 Then $MAX_PROCESS = 1 Local $aProcess[$MAX_PROCESS] ; An array to keep a reference to spawned processes, in the next loop we fill it with value 0 For $i = 0 to UBound($aProcess) - 1 $aProcess[$i] = 0 Next Local $i = 1 Local $iFinished = 1 While True For $n = 0 to UBound($aProcess) - 1 If ($i <> UBound($aArray) AND $aProcess[$n] == 0) Then ; Check if we need a spot, and there is an existing spot $aProcess[$n] = _MSPing($aArray[$i]) $i += 1 Else If ($aProcess[$n] <> 0 And _MSPingIsReady($aProcess[$n])) Then GUICtrlSetData($hProg, ($iFinished / 255) * 100) $sHostname = _MSPingGetHostname($aProcess[$n]) $sResult = _MSPingGetResult($aProcess[$n]) If ($sResult <> -1) Then GUICtrlSetData($hAlive, $sHostname & " is alive " & $sResult & " ms" & @CRLF) Else GUICtrlSetData($hDead, $sHostname & " is dead" & @CRLF) EndIf ; Free up an empty space for the next address to Ping $aProcess[$n] = 0 $iFinished += 1 ; <=== New line If ($iFinished == UBound($aArray)) Then ExitLoop 2 ; Return EndIf EndIf Next Sleep(50) ; Give existing ping commands some time to process the request WEnd GUICtrlSetData($hProg, 0) enableButtons() EndFunc Func error1($sMessage) MsgBox(0, "Error", $sMessage, 0, $hDefault) Sleep(50) enableButtons() GUICtrlSetState($hInput, $GUI_FOCUS) EndFunc Func enableButtons() GUICtrlSetState($hGo, @SW_ENABLE) GUICtrlSetState($hClear, @SW_ENABLE) EndFunc Func clear() GUICtrlSetData($hAlive, "") GUICtrlSetData($hDead, "") EndFunc Func _GetIpAddressList($ipFormat) Local $aResult[1] $aResult[0] = 0 If StringInStr(StringStripWS($ipFormat, 3), " ") Or StringInStr($ipFormat, ".", "", 4) Then Return $aResult $ipFormat = StringReplace($ipFormat, "*", "1-255") $ipSplit = StringSplit($ipFormat, ".") Local $ipRange[4][2], $totalPermu = 1 For $i = 0 To 3 If StringInStr($ipSplit[$i + 1], "-") Then If StringInStr($ipSplit[$i + 1], "-", "", 2) Then Return $aResult $m = StringSplit($ipSplit[$i +1 ],"-") For $i2 = 1 to $m[0] If Number($m[$i2]) > 255 Or Number($m[$i2]) < 0 Then Return $aResult $ipRange[$i][$i2 - 1] = Number($m[$i2]) Next Else $n = Number($ipSplit[$i + 1]) If $n > 255 Or $n < 0 Then Return $aResult $ipRange[$i][0] = $n $ipRange[$i][1] = $n EndIf $totalPermu *= $ipRange[$i][1] - $ipRange[$i][0] + 1 Next Local $aResult[$totalPermu + 1], $i = 1 For $a = $ipRange[0][0] To $ipRange[0][1] For $b = $ipRange[1][0] To $ipRange[1][1] For $c = $ipRange[2][0] To $ipRange[2][1] For $d = $ipRange[3][0] To $ipRange[3][1] $aResult[$i] = $a & "." & $b & "." & $c & "." & $d $i += 1 Next Next Next Next $aResult[0] = $i - 1 Return $aResult EndFunc ;==>_GetIpAddressList Func _Exit() Exit EndFunc Func _MSPing($sHostname, $timeout = 50) Local $return_struc[4] ; [0] = Result (in ms) ; [1] = The hostname originally used ; [2] = Process handle (for internal use only) ; [3] = Buffer (for internal use only) $return_struc[1] = $sHostname $return_struc[2] = Run("ping " & $sHostname & " -n 1 -w " & $timeout, "", @SW_HIDE, $STDOUT_CHILD) Return $return_struc EndFunc Func _MSPingIsReady(ByRef $return_struc) Return ___MSPingReadOutput($return_struc) EndFunc Func _MSPingGetResult($return_struc) Return $return_struc[0] EndFunc Func _MSPingGetHostname($return_struc) Return $return_struc[1] EndFunc ; Internal use only Func ___MSPingReadOutput(ByRef $return_struc) $data = StdoutRead($return_struc[2]) If (@error) Then ___MSPingParseResult($return_struc) Return 1 Else $return_struc[3] &= $data Return 0 EndIf EndFunc ; Internal use only Func ___MSPingParseResult(ByRef $return_struc) $result = StringRegExp($return_struc[3], "([0-9]*)ms", 3) If @error Then $return_struc[0] = -1 Else $return_struc[0] = $result[0] EndIf EndFunc Func _IsPressed($sHexKey, $vDLL = 'user32.dll') ; $hexKey must be the value of one of the keys. ; _Is_Key_Pressed will return 0 if the key is not pressed, 1 if it is. Local $a_R = DllCall($vDLL, "int", "GetAsyncKeyState", "int", '0x' & $sHexKey) If Not @error And BitAND($a_R[0], 0x8000) = 0x8000 Then Return 1 Return 0 EndFunc ;==>_IsPressed Exemplary work! Well done. This is a great collaboration. I'm definitely using this GUI as a stand alone application in the future. Edit: I see you changed the behavior of the code to return a [0] element indicating how large the array is. That is not a wise choice and I don't like it at all. Edited January 11, 2010 by Manadar github.com/jvanegmond Link to comment Share on other sites More sharing options...
SoulA Posted January 11, 2010 Share Posted January 11, 2010 (edited) Edit: I see you changed the behavior of the code to return a [0] element indicating how large the array is. That is not a wise choice and I don't like it at all. Explain! What makes this so terrible? Edited January 11, 2010 by SoulA Link to comment Share on other sites More sharing options...
jvanegmond Posted January 11, 2010 Author Share Posted January 11, 2010 Explain! What makes this so terrible?http://www.autoitscript.com/forum/index.php?showtopic=16321http://www.autoitscript.com/forum/index.php?showtopic=60997 github.com/jvanegmond Link to comment Share on other sites More sharing options...
SoulA Posted January 11, 2010 Share Posted January 11, 2010 http://www.autoitscript.com/forum/index.php?showtopic=16321 http://www.autoitscript.com/forum/index.php?showtopic=60997 I see. Good info thank you. Here is updated code to adhere. Also changed the progress bar to be more accurate and did a few GUI tweaks so it looked a tad nicer. Only thing I can think of to add is to be able to copy elements out of the list but I'm drawing a blank on how to do that. If someone else can come up with a good way please feel free to add on! expandcollapse popup#include <ButtonConstants.au3> #include <GUIConstantsEx.au3> #include <WindowsConstants.au3> #include <Constants.au3> AutoItSetOption("GUIOnEventMode", 1) Global $MAX_PROCESS = 10 ; We spawn a maximum of 10 processes at once $hGUI = GUICreate("Alive", 365, 320, -1, -1, $WS_SYSMENU) $hGo = GUICtrlCreateButton("Go", 210, 10, 57, 25) $hInput = GUICtrlCreateInput("", 5, 10, 200) $hAlive = GUICtrlCreateList("", 5, 64, 170, 200, -1, 0x00000100) $hDead = GUICtrlCreateList("", 185, 64, 170, 200, -1, 0x00000100) $hClear = GUICtrlCreateButton("Clear", 135, 265, 89, 25) $hExample = GUICtrlCreateLabel("Ex. 192.168.1.* or 192.168.1-2.1-10", 5, 40) $hAliveLabel = GUICtrlCreateLabel("Alive", 75, 265) $hDeadLabel = GUICtrlCreateLabel("Dead", 265, 265) $hProg = GUICtrlCreateProgress(190, 40, 165) $hMaxProc = GUICtrlCreateInput($MAX_PROCESS, 325, 10, 30) $hMaxProcLabel = GUICtrlCreateLabel("Max" & @CRLF & "Proc's", 285, 5, 30, 30) GUICtrlSetOnEvent($hGo, "alive") GUICtrlSetOnEvent($hClear, "clear") GUISetOnEvent($GUI_EVENT_CLOSE, "_Exit") GUICtrlSetState($hInput, $GUI_FOCUS) GUISetState(@SW_SHOW) While 1 Sleep(50) If _IsPressed("0D") And WinActive($hGUI) Then alive() WEnd Func alive() GUICtrlSetState($hGo, $GUI_DISABLE) GUICtrlSetState($hClear, $GUI_DISABLE) $sAddress = GUICtrlRead($hInput) If $sAddress = "" Then error1("Input was null") Return EndIf $aArray = _GetIpAddressList($sAddress) If $aArray[0] = "" Then error1("Input was incorrect. Check syntax.") Return EndIf $MAX_PROCESS = GUICtrlRead($hMaxProc) If $MAX_PROCESS = 0 Then $MAX_PROCESS = 1 Local $aProcess[$MAX_PROCESS] ; An array to keep a reference to spawned processes, in the next loop we fill it with value 0 For $i = 0 to UBound($aProcess) - 1 $aProcess[$i] = 0 Next Local $i = 0 Local $iFinished = 0 While True For $n = 0 to UBound($aProcess) - 1 If ($i <> UBound($aArray) AND $aProcess[$n] == 0) Then ; Check if we need a spot, and there is an existing spot $aProcess[$n] = _MSPing($aArray[$i]) $i += 1 Else If ($aProcess[$n] <> 0 And _MSPingIsReady($aProcess[$n])) Then GUICtrlSetData($hProg, ($iFinished / (UBound($aArray) - 1)) * 100) $sHostname = _MSPingGetHostname($aProcess[$n]) $sResult = _MSPingGetResult($aProcess[$n]) If ($sResult <> -1) Then GUICtrlSetData($hAlive, $sHostname & " is alive " & $sResult & " ms" & @CRLF) Else GUICtrlSetData($hDead, $sHostname & " is dead" & @CRLF) EndIf ; Free up an empty space for the next address to Ping $aProcess[$n] = 0 $iFinished += 1 ; <=== New line If $iFinished == UBound($aArray) Then ExitLoop 2 ; Return EndIf EndIf Next Sleep(50) ; Give existing ping commands some time to process the request WEnd GUICtrlSetData($hProg, 0) enableButtons() EndFunc Func error1($sMessage) MsgBox(0, "Error", $sMessage, 0, $hGUI) Sleep(50) enableButtons() GUICtrlSetState($hInput, $GUI_FOCUS) EndFunc Func enableButtons() GUICtrlSetState($hGo, @SW_ENABLE) GUICtrlSetState($hClear, @SW_ENABLE) EndFunc Func clear() GUICtrlSetData($hAlive, "") GUICtrlSetData($hDead, "") EndFunc Func _GetIpAddressList($ipFormat) Local $aResult[1] If StringInStr(StringStripWS($ipFormat, 3), " ") Or StringInStr($ipFormat, ".", "", 4) Then Return $aResult $ipFormat = StringReplace($ipFormat, "*", "1-255") $ipSplit = StringSplit($ipFormat, ".") If $ipSplit[0] <> 4 Then Return $aResult Local $ipRange[4][2], $totalPermu = 1 For $i = 0 To 3 If StringInStr($ipSplit[$i + 1], "-") Then If StringInStr($ipSplit[$i + 1], "-", "", 2) Then Return $aResult $m = StringSplit($ipSplit[$i +1 ],"-") For $i2 = 1 to $m[0] If Number($m[$i2]) > 255 Or Number($m[$i2]) < 0 Then Return $aResult $ipRange[$i][$i2 - 1] = Number($m[$i2]) Next Else $n = Number($ipSplit[$i + 1]) If $n > 255 Or $n < 0 Then Return $aResult $ipRange[$i][0] = $n $ipRange[$i][1] = $n EndIf $totalPermu *= $ipRange[$i][1] - $ipRange[$i][0] + 1 Next Local $aResult[$totalPermu], $i = 0 For $a = $ipRange[0][0] To $ipRange[0][1] For $b = $ipRange[1][0] To $ipRange[1][1] For $c = $ipRange[2][0] To $ipRange[2][1] For $d = $ipRange[3][0] To $ipRange[3][1] $aResult[$i] = $a & "." & $b & "." & $c & "." & $d $i += 1 Next Next Next Next Return $aResult EndFunc ;==>_GetIpAddressList Func _Exit() Exit EndFunc Func _MSPing($sHostname, $timeout = 50) Local $return_struc[4] ; [0] = Result (in ms) ; [1] = The hostname originally used ; [2] = Process handle (for internal use only) ; [3] = Buffer (for internal use only) $return_struc[1] = $sHostname $return_struc[2] = Run("ping " & $sHostname & " -n 1 -w " & $timeout, "", @SW_HIDE, $STDOUT_CHILD) Return $return_struc EndFunc Func _MSPingIsReady(ByRef $return_struc) Return ___MSPingReadOutput($return_struc) EndFunc Func _MSPingGetResult($return_struc) Return $return_struc[0] EndFunc Func _MSPingGetHostname($return_struc) Return $return_struc[1] EndFunc ; Internal use only Func ___MSPingReadOutput(ByRef $return_struc) $data = StdoutRead($return_struc[2]) If (@error) Then ___MSPingParseResult($return_struc) Return 1 Else $return_struc[3] &= $data Return 0 EndIf EndFunc ; Internal use only Func ___MSPingParseResult(ByRef $return_struc) $result = StringRegExp($return_struc[3], "([0-9]*)ms", 3) If @error Then $return_struc[0] = -1 Else $return_struc[0] = $result[0] EndIf EndFunc Func _IsPressed($sHexKey, $vDLL = 'user32.dll') ; $hexKey must be the value of one of the keys. ; _Is_Key_Pressed will return 0 if the key is not pressed, 1 if it is. Local $a_R = DllCall($vDLL, "int", "GetAsyncKeyState", "int", '0x' & $sHexKey) If Not @error And BitAND($a_R[0], 0x8000) = 0x8000 Then Return 1 Return 0 EndFunc ;==>_IsPressed Link to comment Share on other sites More sharing options...
Recommended Posts
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 accountSign in
Already have an account? Sign in here.
Sign In Now