BradV
(Seasoned Scripter)
2015-12-22 07:19 PM
error in parameterdefinition

OK, I'm sure it is staring me right in the face, but I can't see it. \:\)

I couldn't find any UDFs to check installed .net versions. So, I was referencing Determine Which .NET Framework Versions Are Installed. I created:
 Code:
Function CheckDotNet(options $strComputer)
   ; Function:   CheckDotNet
   ;
   ; Author:     Brad Van Orden
   ;             Based on Microsoft Developer Network article:
   ;             How to: Determine Which .NET Framework Versions Are Installed
   ;
   ; Syntax:     CheckDotNet(\[{$strComputer])
   ;
   ; Parameters:  Optional name of remote system to query.
   ;              If omitted, will query the current system.
   ;
   ; Returns:    Two dimensional array.  The first dimension will be the major
   ;             version number.  The second the complete version.
   ;
   ; Dependencies: None
   ;
   DIM $strComputer, $strKey, $intIndex, $strKeyName, $strVers, $arrVer[0,1]
   ;
   If $strComputer = ""
      $strComputer = "."
   EndIf
   ;
   $strKey = "\HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\NET Framework Setup\NDP"
   $intIndex = 0
   If KeyExist($strKey)
      $strKeyName = EnumKey($strKey, $intIndex)
      While Not @ERROR
         If $strKeyName <> "CDF"
            ; Want to ignore the CDF key
            REDIM PRESERVE $arrVer[$intIndex, $intIndex + 1]
            If Left($strKeyName, 2) = "v1"
               ; The version 1 setup is different.  Need to treat it separately.
               $arrVer[$indIndex, 0] = Left($strKeyName, 2)
               $arrVer[$intIndex, 1] = Substr($strKeyName, 2)
               $intIndex = $intIndex + 1
            Else
               If $strKeyName <> "v4.0"
                  ; Ignore that subkey
                  If $strKeyName = "v4"
                     $strVers = ReadValue("\\" + $strComputer + $strKey + "\Full", "Version")
                     $arrVer[$intIndex, 0] = $strKeyName
                     $arrVer[$intIndex, 1] = $strVers
                     $intIndex = $intIndex + 1
                  Else
                     $strVers = ReadValue("\\" + $strComputer + $strKey, "Version")
                     $arrVer[$intIndex, 0] = $strKeyName
                     $arrVer[$intIndex, 1] = $strVers
                     $intIndex = $intIndex + 1
                  EndIf
               EndIf
            EndIf
         EndIf
      Loop
   EndIf
   $CheckDotNet = $arrVer
EndFunction


I then attempted to call it with:
 Code:
Break On
DIM $SO
$SO = SetOption('Explicit',          'On')
$SO = SetOption('NoMacrosInStrings', 'On')
DIM $arrDotNet[0,1], $strFile, $intI, $intErr
$strFile = "c:\temp\dotnet.ini"
$arrDotNet = CheckDotNet()
For $intI = 1 to Ubound$($arrDotNet)
   $intErr = WriteProfileString($strFile,"localhost",$arrDotNet[$intI,0],$arrDotNet[$intI,1])
Next
but keep getting :
 Code:
ERROR: error in parameterdefinition of [checkdotnet]!
Script:U:\check_dotnet.kix
Note: I might have some typos. I can't directly upload the script. Anyone point out my mistake? Thanks!


JochenAdministrator
(KiX Supporter)
2015-12-22 08:41 PM
Re: error in parameterdefinition

Hi Brad,

easy one..

Function CheckDotNet(options $strComputer)

should be

Function CheckDotNet(optional $strComputer)

didn't check the rest...


BradV
(Seasoned Scripter)
2015-12-23 11:47 AM
Re: error in parameterdefinition

That was it! Thanks! \:\)

BradV
(Seasoned Scripter)
2015-12-23 12:54 PM
Re: error in parameterdefinition

I had a few errors in the code. Also, forgot REDIM PRESERVE doesn't work on multi-dimensional arrays. I just made it an arbitrarily large array. Here are the corrections:
 Code:
Function CheckDotNet(optional $strComputer)
   ; Function:   CheckDotNet
   ;
   ; Author:     Brad Van Orden
   ;             Based on Microsoft Developer Network article:
   ;             How to: Determine Which .NET Framework Versions Are Installed
   ;
   ; Syntax:     CheckDotNet(\[{$strComputer])
   ;
   ; Parameters:  Optional name of remote system to query.
   ;              If omitted, will query the current system.
   ;
   ; Returns:    Two dimensional array.  The first dimension will be the major
   ;             version number.  The second the complete version.
   ;
   ; Dependencies: None
   ;
   DIM $strKey, $intIndex, $strKeyName, $strVers, $arrVer[10,11]
   ;
   If $strComputer = ""
      $strComputer = "."
   EndIf
   ;
   $strKey = "\HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\NET Framework Setup\NDP"
   $intIndex = 0
   $intI     = 0
   If KeyExist("\\" + $strComputer + $strKey)
      $strKeyName = EnumKey("\\" + $strComputer + $strKey, $intIndex)
      While Not @ERROR
         If $strKeyName <> "CDF"
            ; Want to ignore the CDF key
            If Left($strKeyName, 2) = "v1"
               ; The version 1 setup is different.  Need to treat it separately.
               $arrVer[$intI, 0] = Left($strKeyName, 2)
               $arrVer[$intI, 1] = Substr($strKeyName, 2)
               $intI = $intI + 1
            Else
               If $strKeyName <> "v4.0"
                  ; Ignore that subkey
                  If $strKeyName = "v4"
                     $strVers = ReadValue("\\" + $strComputer + $strKey + "\" + $strKeyName + "\Full", "Version")
                     $arrVer[$intI, 0] = $strKeyName
                     $arrVer[$intI, 1] = $strVers
                     $intI = $intI + 1
                  Else
                     $strVers = ReadValue("\\" + $strComputer + $strKey + "\" + $strKeyName, "Version")
                     If Left($strKeyName, 2) = "v2"
                        $arrVer[$intI, 0] = Left($strKeyName, 2)
                     Else
                        $arrVer[$intI, 0] = $strKeyName
                     EndIf
                     $arrVer[$intI, 1] = $strVers
                     $intI = $intI + 1
                  EndIf
               EndIf
            EndIf
         EndIf
         $intIndex = $intIndex + 1
         $strKeyName = EnumKey("\\" + $strComputer + $strKey, $intIndex)
      Loop
   EndIf
   ; To mark the end of the array, place a -1 in the next array position.
   $arrVer[$intI, 0] = -1
   $CheckDotNet = $arrVer
EndFunction


I have an ini file with all of the computers in the active directory and use that when probing all of the systems. It just looks like:
 Code:
[computers]
comp1=name1
comp2=name2
I then called with:
 Code:
Break On
DIM $SO
$SO = SetOption('Explicit',          'On')
$SO = SetOption('NoMacrosInStrings', 'On')
DIM $arrDotNet[10,11], $strFile, $intI, $intErr
DIM $strWks, $strComps, $colComps, $objComp
include "functions.kix"
;
$strFile  = "c:\temp\dotnet.ini"
$strComps = "c:\temp\computers.ini"
;
$colComps = Split(ReadProfileString($strComps, "computers", ""),chr(10))
For Each $objComp in $colComps
   If $objComp <> ""
      $strWks = ReadProfileString($strComps, "computers", $objComp)
      ? "Checking for installed .net versions on: " + $strWks
      $arrDotNet = CheckDotNet($strWks)
      $intI = 0
      While $arrDotNet[$intI, 0] <> -1
         $intErr = WriteProfileString($strFile,$strWks,$arrDotNet[$intI,0],$arrDotNet[$intI,1])
         $intI = $intI + 1
      Loop
   Else
      ? "Did not receive results from: " + $strWks
      $intErr = WriteProfileString($strFile,$strWks,"DOTNET","Could not read from this system.")
   EndIf
Next
which gave me the dotnet versions on each host. \:\)


NTDOCAdministrator
(KiX Master)
2015-12-29 07:49 PM
Re: error in parameterdefinition

You posted the wrong keyword again in your updated code

Function CheckDotNet(options $strComputer)


ERROR : undefined variable [intI]!



NTDOCAdministrator
(KiX Master)
2015-12-29 07:55 PM
Re: error in parameterdefinition

Looks like there is possibly something else wrong in the code somewhere as it reads a remote system but doesn't seem to see a .NET 4x version so then marks it as though it cannot read it when in fact it did read it. Guessing here that it's due to how the loop is called (calling a blank line maybe)... don't have time to debug it at the moment.


[workstation-14]
v2=2.0.50727.5420
v3.0=3.0.30729.5420
v3.5=3.5.30729.5420
v4=4.5.51209
[workstation-15]
v1=1.1.4322
v2=2.2.30729
v3.0=3.2.30729
v3.5=3.5.30729.01
DOTNET=Could not read from this system.


Glenn BarnasAdministrator
(KiX Supporter)
2015-12-30 12:11 AM
Re: error in parameterdefinition

Changing your INI format from Comp1=name1 to name1=1, name2=1, etc, means you can use EnumIni to enumerate the list of computer names directly, rather than having to enumerate the list of values and then use ReadProfileString to get the actual names. \:\)

You could also use the value to mean something, such as 1=process and 0=ignore, but I use this generic method often when I just need a list of names from the INI file.

Glenn


BradV
(Seasoned Scripter)
2016-01-06 12:21 PM
Re: error in parameterdefinition

Doc you are correct that I have some error in my logic. I need to look at it again. Glenn, great suggestion about the ini. I'll try to implement that as well. \:\)

NTDOCAdministrator
(KiX Master)
2016-01-07 07:37 PM
Re: error in parameterdefinition

Don't forget that by default (I believe) Windows 7 has remote registry disabled and has to be enabled to remotely read it. XP had it enabled by default.