Jump to content
Sign in to follow this  
Rogue5099

Using Network Meter getting Array not defined

Recommended Posts

Rogue5099

Here is a link to that I got the code from.

On my computer this script works fine. On another computer I finally got it down to line 132 causing the problem, array not defined. ($Table_Data[0][0])

Here is the code striped with Obfuscated (/striponly) so I could get to the line of the error:

Global Const $GUI_EVENT_CLOSE = -3
Global Const $GUI_DISABLE = 128
Func _ArraySearch(Const ByRef $avArray, $vValue, $iStart = 0, $iEnd = 0, $iCase = 0, $iCompare = 0, $iForward = 1, $iSubItem = -1)
    If Not IsArray($avArray) Then Return SetError(1, 0, -1)
    If UBound($avArray, 0) > 2 Or UBound($avArray, 0) < 1 Then Return SetError(2, 0, -1)
    Local $iUBound = UBound($avArray) - 1
    If $iEnd < 1 Or $iEnd > $iUBound Then $iEnd = $iUBound
    If $iStart < 0 Then $iStart = 0
    If $iStart > $iEnd Then Return SetError(4, 0, -1)
    Local $iStep = 1
    If Not $iForward Then
        Local $iTmp = $iStart
        $iStart = $iEnd
        $iEnd = $iTmp
        $iStep = -1
    EndIf
    Local $iCompType = False
    If $iCompare = 2 Then
        $iCompare = 0
        $iCompType = True
    EndIf
    Switch UBound($avArray, 0)
        Case 1
            If Not $iCompare Then
                If Not $iCase Then
                    For $i = $iStart To $iEnd Step $iStep
                        If $iCompType And VarGetType($avArray[$i]) <> VarGetType($vValue) Then ContinueLoop
                        If $avArray[$i] = $vValue Then Return $i
                    Next
                Else
                    For $i = $iStart To $iEnd Step $iStep
                        If $iCompType And VarGetType($avArray[$i]) <> VarGetType($vValue) Then ContinueLoop
                        If $avArray[$i] == $vValue Then Return $i
                    Next
                EndIf
            Else
                For $i = $iStart To $iEnd Step $iStep
                    If StringInStr($avArray[$i], $vValue, $iCase) > 0 Then Return $i
                Next
            EndIf
        Case 2
            Local $iUBoundSub = UBound($avArray, 2) - 1
            If $iSubItem > $iUBoundSub Then $iSubItem = $iUBoundSub
            If $iSubItem < 0 Then
                $iSubItem = 0
            Else
                $iUBoundSub = $iSubItem
            EndIf
            For $j = $iSubItem To $iUBoundSub
                If Not $iCompare Then
                    If Not $iCase Then
                        For $i = $iStart To $iEnd Step $iStep
                            If $iCompType And VarGetType($avArray[$i][$j]) <> VarGetType($vValue) Then ContinueLoop
                            If $avArray[$i][$j] = $vValue Then Return $i
                        Next
                    Else
                        For $i = $iStart To $iEnd Step $iStep
                            If $iCompType And VarGetType($avArray[$i][$j]) <> VarGetType($vValue) Then ContinueLoop
                            If $avArray[$i][$j] == $vValue Then Return $i
                        Next
                    EndIf
                Else
                    For $i = $iStart To $iEnd Step $iStep
                        If StringInStr($avArray[$i][$j], $vValue, $iCase) > 0 Then Return $i
                    Next
                EndIf
            Next
        Case Else
            Return SetError(7, 0, -1)
    EndSwitch
    Return SetError(6, 0, -1)
EndFunc   ;==>_ArraySearch
Global Const $MIB_IF_TYPE_SOFTWARE_LOOPBACK = 24
Global Const $tagMIB_IFROW = 'wchar Name[256];dword Index;dword Type;dword Mtu;dword Speed;dword PhysAddrLen;byte PhysAddr[8];dword AdminStatus;dword OperStatus;' & 'dword LastChange;dword InOctets;dword InUcastPkts;dword InNUcastPkts;dword InDiscards;dword InErrors;dword InUnknownProtos;dword OutOctets;dword OutUcastPkts;' & 'dword OutNUcastPkts;dword OutDiscards;dword OutErrors;dword OutQLen;dword DescrLen;char Descr[256]'
$GUI = GUICreate('Network Speed v1.0', '250', '20', '-1', '-1', '-1', '128')
$NetSpeed = GUICtrlCreateInput("DL: 0 kB/sec  UL: 0 kB/sec", '0', '0', '250', '20', '1')
GUICtrlSetFont(-1, '9', '600', '', 'Arial')
GUICtrlSetState(-1, $GUI_DISABLE)
GUISetState(@SW_SHOW, $GUI)
WinSetOnTop($GUI, '', '1')
Global $IPHlpApi_Dll = DllOpen('IPHlpApi.dll')
Global $sLast_Label
Global $Global_IF_Count = _GetNumberofInterfaces()
Global $Table_Data = _WinAPI_GetIfTable()
Global $hUpdate = DllCallbackRegister('_UpdateStats', 'none', '')
DllCall('user32.dll', 'int', 'SetTimer', 'hwnd', 0, 'int', 0, 'int', 1000, 'ptr', DllCallbackGetPtr($hUpdate))
Global $aStart_Values = _GetAllTraffic()
While 1
    $nMsg = GUIGetMsg()
    Switch $nMsg
        Case $GUI_EVENT_CLOSE
            GUIDelete()
            Exit
    EndSwitch
    Sleep(15)
WEnd
Func _UpdateStats()
    Local $aEnd_Values, $iRecived, $iSent, $sNew_Label, $iLargest_Value
    $aEnd_Values = _GetAllTraffic()
    $iRecived = $aEnd_Values[0] - $aStart_Values[0]
    $iSent = $aEnd_Values[1] - $aStart_Values[1]
    If Not ($iRecived + $iSent) Then
        Local $sZero = 'DL: 0.0 kB/sec  UL: 0.0 kB/sec'
        If $sLast_Label <> $sZero Then GUICtrlSetData($NetSpeed, $sZero)
        $aStart_Values = $aEnd_Values
        $sLast_Label = $sZero
        Return
    EndIf
    If $iSent >= $iRecived Then
        $iLargest_Value = $iSent
    Else
        $iLargest_Value = $iRecived
    EndIf
    If $iLargest_Value >= 1048576 Then
        $sNew_Label = 'DL: ' & StringFormat('%.2f', Round($iRecived / 1048576, 2)) & ' mB/sec  ' & 'UL: ' & StringFormat('%.2f', Round($iSent / 1048576, 2)) & ' mB/sec'
        If $sNew_Label <> $sLast_Label Then GUICtrlSetData($NetSpeed, $sNew_Label)
    Else
        $sNew_Label = 'DL: ' & StringFormat('%.1f', Round($iRecived / 1024, 1)) & ' kB/sec  ' & 'UL: ' & StringFormat('%.1f', Round($iSent / 1024, 1)) & ' kB/sec'
        If $sNew_Label <> $sLast_Label Then GUICtrlSetData($NetSpeed, $sNew_Label)
    EndIf
    $sLast_Label = $sNew_Label
    $aStart_Values = $aEnd_Values
EndFunc   ;==>_UpdateStats
Func _GetAllTraffic()
    Local $Total_Values[2], $Adapter_Values
    Local $ifcount = _GetNumberofInterfaces()
    If $Global_IF_Count <> $ifcount Then
        $Global_IF_Count = $ifcount
        $Table_Data = _WinAPI_GetIfTable()
        $aStart_Values = _GetAllTraffic()
    EndIf
    For $i = 1 To $Table_Data[0][0]
        $Adapter_Values = _WinAPI_GetIfEntry($Table_Data[$i][1])
        If IsArray($Adapter_Values) Then
            $Total_Values[0] += $Adapter_Values[0]
            $Total_Values[1] += $Adapter_Values[1]
        Else
            $Table_Data = _WinAPI_GetIfTable()
        EndIf
    Next
    Return $Total_Values
EndFunc   ;==>_GetAllTraffic
Func _WinAPI_GetIfEntry($iIndex)
    Local $Ret, $Stats[2]
    Static $tMIB_IFROW = DllStructCreate($tagMIB_IFROW)
    DllStructSetData($tMIB_IFROW, 2, $iIndex)
    $Ret = DllCall($IPHlpApi_Dll, 'dword', 'GetIfEntry', 'ptr', DllStructGetPtr($tMIB_IFROW))
    If (@error) Or ($Ret[0]) Then Return SetError($Ret[0], 0, 0)
    $Stats[0] = DllStructGetData($tMIB_IFROW, 'InOctets')
    $Stats[1] = DllStructGetData($tMIB_IFROW, 'OutOctets')
    Return $Stats
EndFunc   ;==>_WinAPI_GetIfEntry
Func _GetNumberofInterfaces()
    Local $Adaptor_Count = DllCall($IPHlpApi_Dll, 'int', 'GetNumberOfInterfaces', 'dword*', 0)
    Return $Adaptor_Count[1]
EndFunc   ;==>_GetNumberofInterfaces
Func _WinAPI_GetIfTable($iType = 0)
    Local $Ret, $Row, $Type, $Tag, $Tab, $Addr, $Count, $Lenght, $tMIB_IFTABLE
    Local $tMIB_IFROW = DllStructCreate($tagMIB_IFROW)
    $Row = 'byte[' & DllStructGetSize($tMIB_IFROW) & ']'
    $Tag = 'dword;'
    For $i = 1 To 32
        $Tag &= $Row & ';'
    Next
    $tMIB_IFTABLE = DllStructCreate($Tag)
    $Ret = DllCall($IPHlpApi_Dll, 'dword', 'GetIfTable', 'ptr', DllStructGetPtr($tMIB_IFTABLE), 'long*', DllStructGetSize($tMIB_IFTABLE), 'int', 1)
    If (@error) Or ($Ret[0]) Then Return SetError($Ret[0], 0, 0)
    $Count = DllStructGetData($tMIB_IFTABLE, 1)
    Dim $Tab[$Count + 1][20]
    $Tab[0][0] = 0
    $Tab[0][1] = 'Index'
    $Tab[0][2] = 'Type'
    $Tab[0][3] = 'Mtu'
    $Tab[0][4] = 'Speed'
    $Tab[0][5] = 'Address'
    $Tab[0][6] = 'AdminStatus'
    $Tab[0][7] = 'OperStatus'
    $Tab[0][8] = 'InOctets'
    $Tab[0][9] = 'InUcastPkts'
    $Tab[0][10] = 'InNUcastPkts'
    $Tab[0][11] = 'InDiscards'
    $Tab[0][12] = 'InErrors'
    $Tab[0][13] = 'InUnknownProtos'
    $Tab[0][14] = 'OutOctets'
    $Tab[0][15] = 'OutUcastPkts'
    $Tab[0][16] = 'OutNUcastPkts'
    $Tab[0][17] = 'OutDiscards'
    $Tab[0][18] = 'OutErrors'
    For $i = 1 To $Count
        $tMIB_IFROW = DllStructCreate($tagMIB_IFROW, DllStructGetPtr($tMIB_IFTABLE, $i + 1))
        $Type = DllStructGetData($tMIB_IFROW, 'Type')
        If $Type <> $MIB_IF_TYPE_SOFTWARE_LOOPBACK Then
            $Tab[0][0] += 1
            $Lenght = DllStructGetData($tMIB_IFROW, 'PhysAddrLen')
            $Addr = ''
            For $j = 1 To $Lenght
                $Addr &= Hex(DllStructGetData($tMIB_IFROW, 'PhysAddr', $j), 2) & '-'
            Next
            $Addr = StringTrimRight($Addr, 1)
            _ArraySearch($Tab, $Addr, 1, $Tab[0][0] - 1, 1, 0, 1, 5)
            If @error <> 6 Or $Addr = '' Or StringLen($Addr) > 17 Then
                $Tab[0][0] -= 1
                ContinueLoop
            EndIf
            $Tab[$Tab[0][0]][0] = DllStructGetData($tMIB_IFROW, 'Name')
            $Tab[$Tab[0][0]][1] = DllStructGetData($tMIB_IFROW, 'Index')
            $Tab[$Tab[0][0]][2] = $Type
            $Tab[$Tab[0][0]][3] = DllStructGetData($tMIB_IFROW, 'Mtu')
            $Tab[$Tab[0][0]][4] = DllStructGetData($tMIB_IFROW, 'Speed')
            $Tab[$Tab[0][0]][5] = $Addr
            $Tab[$Tab[0][0]][6] = DllStructGetData($tMIB_IFROW, 'AdminStatus')
            $Tab[$Tab[0][0]][7] = DllStructGetData($tMIB_IFROW, 'OperStatus')
            $Tab[$Tab[0][0]][8] = DllStructGetData($tMIB_IFROW, 'InOctets')
            $Tab[$Tab[0][0]][9] = DllStructGetData($tMIB_IFROW, 'InUcastPkts')
            $Tab[$Tab[0][0]][10] = DllStructGetData($tMIB_IFROW, 'InNUcastPkts')
            $Tab[$Tab[0][0]][11] = DllStructGetData($tMIB_IFROW, 'InDiscards')
            $Tab[$Tab[0][0]][12] = DllStructGetData($tMIB_IFROW, 'InErrors')
            $Tab[$Tab[0][0]][13] = DllStructGetData($tMIB_IFROW, 'InUnknownProtos')
            $Tab[$Tab[0][0]][14] = DllStructGetData($tMIB_IFROW, 'OutOctets')
            $Tab[$Tab[0][0]][15] = DllStructGetData($tMIB_IFROW, 'OutUcastPkts')
            $Tab[$Tab[0][0]][16] = DllStructGetData($tMIB_IFROW, 'OutNUcastPkts')
            $Tab[$Tab[0][0]][17] = DllStructGetData($tMIB_IFROW, 'OutDiscards')
            $Tab[$Tab[0][0]][18] = DllStructGetData($tMIB_IFROW, 'OutErrors')
            $Tab[$Tab[0][0]][19] = StringLeft(DllStructGetData($tMIB_IFROW, 'Descr'), DllStructGetData($tMIB_IFROW, 'DescrLen') - 1)
        EndIf
    Next
    If $Tab[0][0] < $Count Then ReDim $Tab[$Tab[0][0] + 1][20]
    Return $Tab
EndFunc   ;==>_WinAPI_GetIfTable

Share this post


Link to post
Share on other sites
Melba23

Rogue5099,

At a quick glance the problem would seem to be that the array in question is only created if a previous If statement is true:

Func _GetAllTraffic()
    Local $Total_Values[2], $Adapter_Values
    Local $ifcount = _GetNumberofInterfaces()
    If $Global_IF_Count <> $ifcount Then ; Condition set here <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
        $Global_IF_Count = $ifcount
        $Table_Data = _WinAPI_GetIfTable() ; Array created here <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
        $aStart_Values = _GetAllTraffic()
    EndIf
    For $i = 1 To $Table_Data[0][0] ; What if the array has not been created earlier? <<<<<<<<<<<<<<<<<
        $Adapter_Values = _WinAPI_GetIfEntry($Table_Data[$i][1])
        If IsArray($Adapter_Values) Then
            $Total_Values[0] += $Adapter_Values[0]
            $Total_Values[1] += $Adapter_Values[1]
        Else
            $Table_Data = _WinAPI_GetIfTable()
        EndIf
    Next
    Return $Total_Values
EndFunc   ;==>_GetAllTraffic

Add some errorchecking -and test the array exists before trying to access it. Or declare the arry as Local when you enter the function. ;)

M23


Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind._______My UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Share this post


Link to post
Share on other sites
BrewManNH

It could be that you're not checking to see if the _WinAPI_GetIfTable returns an array when it succeeds, or a string when it fails. If it's failing for some reason, it's going to return the value in $Ret[0] as the error, and a value of 0 as the return value.


If I posted any code, assume that code was written using the latest release version unless stated otherwise. Also, if it doesn't work on XP I can't help with that because I don't have access to XP, and I'm not going to.
Give a programmer the correct code and he can do his work for a day. Teach a programmer to debug and he can do his work for a lifetime - by Chirag Gude
How to ask questions the smart way!

I hereby grant any person the right to use any code I post, that I am the original author of, on the autoitscript.com forums, unless I've specifically stated otherwise in the code or the thread post. If you do use my code all I ask, as a courtesy, is to make note of where you got it from.

Back up and restore Windows user files _Array.au3 - Modified array functions that include support for 2D arrays.  -  ColorChooser - An add-on for SciTE that pops up a color dialog so you can select and paste a color code into a script.  -  Customizable Splashscreen GUI w/Progress Bar - Create a custom "splash screen" GUI with a progress bar and custom label.  -  _FileGetProperty - Retrieve the properties of a file  -  SciTE Toolbar - A toolbar demo for use with the SciTE editor  -  GUIRegisterMsg demo - Demo script to show how to use the Windows messages to interact with controls and your GUI.  -   Latin Square password generator

Share this post


Link to post
Share on other sites
Rogue5099

"Subscript used with non Array Variable" is the exact error. I declared the variable at the start of the function:

Local $Table_Data = _WinAPI_GetIfTable()

Edit: I didn't write the code I just copied/pasted and removed extras. I have no idea what it searches i.e. adapters so forth. Weird thing is that it doesn't error on my computer but it does my friends. Only difference is mine is a laptop and his is desktop (both have wireless and LAN options)

Edit2: Declaring Array Locally is not necessary because it is define Globaly.

Edited by Rogue5099

Share this post


Link to post
Share on other sites
Melba23

Rogue5099,

You might have declared it as an array initially, but what is the error return from _WinAPI_GetIfTable (it does not appear in my Help file)? If you do not get an array returned then accessing it will fail. That is why I suggested errorchecking with IsArray before using it. ;)

M23


Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind._______My UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Share this post


Link to post
Share on other sites
Rogue5099

If IsArray($Table_Data) Then
        For $i = 1 To $Table_Data[0][0]
            $Adapter_Values = _WinAPI_GetIfEntry($Table_Data[$i][1])
            If IsArray($Adapter_Values) Then
                $Total_Values[0] += $Adapter_Values[0];Recived
                $Total_Values[1] += $Adapter_Values[1];Sent
            Else
                $Table_Data = _WinAPI_GetIfTable()
            EndIf
        Next
    EndIf

This works not getting the error but of course it doesn't display the upload download speeds either. I guess not getting an error is better than not getting the network rates.

Edit:

This is where it should be returning a non-array value but this is as far as I can go due to me not knowing anything about .dll's. This is within the _WinAPI_GetIfTable() function.

$Row = 'byte[' & DllStructGetSize($tMIB_IFROW) & ']'
    $Tag = 'dword;'
    For $i = 1 To 32
        $Tag &= $Row & ';'
    Next
    $tMIB_IFTABLE = DllStructCreate($Tag)
    $Ret = DllCall($IPHlpApi_Dll, 'dword', 'GetIfTable', 'ptr', DllStructGetPtr($tMIB_IFTABLE), 'long*', DllStructGetSize($tMIB_IFTABLE), 'int', 1)
    If (@error) Or ($Ret[0]) Then Return SetError($Ret[0], 0, 0)
Edited by Rogue5099

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  

×