ConfigMgr: Using SQL to find applications that use VBS scripts in install/uninstall command lines and VBScript detection methods

Another one about finding VBS usage… Since Microsoft has announced the deprecation of VBScript.  VBS files can be used in the install and/or uninstall command line:

and also can be chosen as the script language in a detection script:

I originally wrote this in PowerShell, but it was taking an awfully long time, so I decided to try it in SQL.

declare @LocaleID int = (select LocaleID from vSMSData)
declare @CommandLineSearchString varchar (100) = '%.vbs%'
declare @DetectionMethod varchar (100) = 'Script' 
declare @DetectionScriptLanguage varchar (100) = 'VBScript'
;

WITH XMLNAMESPACES (DEFAULT 'http://schemas.microsoft.com/SystemCenterConfigurationManager/2009/AppMgmtDigest')
select
  app.DisplayName [Application]
, app.Description
, dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Title)[1]', 'nvarchar(max)') [Deployment Type]

, case when dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/InstallAction/Args/Arg)[1]', 'nvarchar(max)') like @CommandLineSearchString
		then dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/InstallAction/Args/Arg)[1]', 'nvarchar(max)') else '' end [InstallCommandLine]

, case when dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/UninstallAction/Args/Arg)[1]', 'nvarchar(max)') like @CommandLineSearchString
		then dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/UninstallAction/Args/Arg)[1]', 'nvarchar(max)') else '' end [UninstallCommandLine]

, case when dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/CustomData/DetectionMethod)[1]', 'nvarchar(max)') = @DetectionMethod
		 and dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/CustomData/DetectionScript/@Language)[1]', 'nvarchar(max)') = @DetectionScriptLanguage
		then @DetectionMethod + ' - ' + @DetectionScriptLanguage else '' end [DetectionMethod-ScriptLanguage]

from v_ConfigurationItems dt
INNER JOIN v_CIRelation AS rel ON dt.CI_ID = rel.ToCIID
INNER JOIN fn_ListApplicationCIs_List(@LocaleID) AS app ON app.CI_ID = rel.FromCIID
where
(dt.CIType_ID = 21 and dt.IsLatest = 1)
and
(
	   dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/InstallAction/Args/Arg)[1]', 'nvarchar(max)') like  @CommandLineSearchString
	or dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/UninstallAction/Args/Arg)[1]', 'nvarchar(max)') like  @CommandLineSearchString
	or
	(
	dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/CustomData/DetectionMethod)[1]', 'nvarchar(max)') = @DetectionMethod
	and dt.SDMPackageDigest.value ('(/AppMgmtDigest/DeploymentType/Installer/CustomData/DetectionScript/@Language)[1]', 'nvarchar(max)') = @DetectionScriptLanguage
	)
)

Results look like:

ConfigMgr: Using PowerShell to find task sequences that execute a vbs script in a Run Command Line step

Since Microsoft has announced the deprecation of VBScript, my manager asked me to find where it’s being used.  One place where it may be used is in a Run Command Line step in a Task Sequence.  I wrote this script that checks all the task sequences for it.  Run this script with a PowerShell session that has the ConfigurationManager module loaded and connected to the site.

Get-CMTaskSequence -Fast | ForEach-Object {
    $PackageID = $_.PackageID
    $Name = $_.Name
    $DisplayedName = $False
    Get-CMTaskSequenceStep -TaskSequenceId $_.PackageID `
    -ActionClassName SMS_TaskSequence_RunCommandLineAction `
    | Where-Object {$_.CommandLine -like "*.vbs*"} | ForEach-Object {
        if ($DisplayedName -eq $False) {
            Write-Host
            Write-Host $PackageID - $Name
            $DisplayedName = $True
        }
        Write-Host $_.Name: $_.CommandLine -ForegroundColor Yellow
    }
    $DisplayedName = $False
} 

The output will be the task sequence package IDs and names, along with the step names and command lines:

ConfigMgr: SQL Query to find whether “Microsoft ODBC Driver 18 for SQL Server” is installed on site systems and a command line to install it

Microsoft recently announced SQL ODBC driver support for Configuration Manager. The “What’s new in version 2309 of Configuration Manager current branch” page states:

 Important

Microsoft ODBC Driver for SQL Server 18.1.0 or later needs to be installed on Site Servers and site system roles before upgrading to 2309 version.

This query will show the version of “Microsoft ODBC Driver 18 for SQL Server”, as well as the version of “Microsoft SQL Server 2012 Native Client”

select
  upper (ss.ServerName) ServerName
, s.operatingSystem0
, odbc.Publisher0
, odbc.ARPDisplayName0
, odbc.ProductVersion0
, ncli.Publisher0
, ncli.ARPDisplayName0
, ncli.ProductVersion0
from vSMS_SC_SysResUse_SDK ss
inner join v_R_System s on ss.ServerName = s.Name0 or ss.ServerName = s.Name0 + '.' + s.Full_Domain_Name0
left  join v_GS_INSTALLED_SOFTWARE ncli on ncli.ResourceID = s.ResourceID and ncli.ARPDisplayName0 = 'Microsoft SQL Server 2012 Native Client'
left  join v_GS_INSTALLED_SOFTWARE odbc on odbc.ResourceID = s.ResourceID and odbc.ARPDisplayName0 = 'Microsoft ODBC Driver 18 for SQL Server'
where ss.RoleName = 'SMS Site System'
order by upper (ss.ServerName)

I have already installed the ODBC driver on all my site systems, so my output looks like:

I downloaded msodbcsql.msi from here and created an application with the following command line in the deployment type:

msiexec /i "msodbcsql.msi" /q /norestart IACCEPTMSODBCSQLLICENSETERMS=YES

ConfigMgr: SQL query to show the versions of SQL Server 2012 Native Client on site systems

select
  upper (ss.ServerName) ServerName
, s.operatingSystem0
, isw.Publisher0
, isw.ARPDisplayName0
, isw.ProductVersion0
from vSMS_SC_SysResUse_SDK ss
inner join v_R_System s on ss.ServerName = s.Name0 or ss.ServerName = s.Name0 + '.' + s.Full_Domain_Name0
inner join v_GS_INSTALLED_SOFTWARE isw on isw.ResourceID = s.ResourceID
where ss.RoleName = 'SMS Site System' and isw.ARPDisplayName0 = 'Microsoft SQL Server 2012 Native Client'
order by upper (ss.ServerName)
, s.operatingSystem0
, isw.Publisher0
, isw.ARPDisplayName0
, isw.ProductVersion0

How to get the latest version (v11.4.7462.6) of SQL Server Native Client

I noticed in the List of prerequisite checks for Configuration Manager that the ConfigMgr’s prereq checker only validates the minimum version of the SQL Server Native Client [SQL Server 2012 SP4 (11.*.7001.0)] on the site server and not the remote site systems.  Since ConfigMgr uses the SQL Native Client on a whole host of site system roles, my supervisor asked me to update the SQL Server Native Client on all site systems to the latest version.

From the list of prerequisite checks page:

Configuration Manager uses SQL Server Native Client on the following site system roles:

  • Site database server
  • Site server: central administration site, primary site, or secondary site
  • Management point
  • Device management point
  • State migration point
  • SMS Provider
  • Software update point
  • Multicast-enabled distribution point
  • Asset Intelligence update service point
  • Reporting services point
  • Enrollment point
  • Endpoint Protection point
  • Service connection point
  • Certificate registration point
  • Data warehouse service point

Use this to see the versions of SQL Server 2012 Native Client on site systems.

The Microsoft page Installing SQL Server Native Client instructed me to download it from the SQL Server 2012 Feature Pack web page:

“You can also get sqlncli.msi from the SQL Server 2012 Feature Pack web page. To download the most recent version of the SQL Server Native Client, go to Microsoft® SQL Server® 2012 Feature Pack.”

However, that version won’t install on Windows Server 2019 Standard:

The Installing SQL Server Native Client page starts by stating that:

 “The SQL Server Native Client (often abbreviated SNAC) has been removed from SQL Server 2022 (16.x) and SQL Server Management Studio 19 (SSMS).”

This implied to me that it is included in SSMS 18, so I went to the Release notes for SQL Server Management Studio (SSMS) and downloaded version 18.12.1.  I installed it on a workstation and found version 11.4.7462.6 of sqlncli.msi here:

C:\ProgramData\Package Cache\{9D93D367-A2CC-4378-BD63-79EF3FE76C78}v11.4.7462.6\x64\sqlncli.msi

ccmexec.log: Winmgmt service current status is 0x4.

Came in this morning and the ccmexec service on one of the site systems was stopped. I checked ccmexec.log and saw this:

Completed phase 1 initialization.  Service is now fully operational.	CcmExec	10/10/2023 7:53:16 AM	5020 (0x139C)
*** System is now free to go to sleep	CcmExec	10/10/2023 7:53:16 AM	1304 (0x0518)
Winmgmt service current status is 0x4. Process Id 2428.	CcmExec	10/10/2023 7:53:16 AM	9044 (0x2354)

I tried restarting the service, but it stopped again with the same message. I checked the winmgmt service, it was running and I was able to run a WMI query.

An uninstall/reinstall of the client fixed it.

ccmsetup.exe /uninstall

ccmsetup.exe /usepkicert /allowmetered /nocrlcheck /BITSPriority:FOREGROUND SMSSITECODE=<SITE> DNSSUFFIX=<DNS.SUFFIX>