ConfigMgr: ccmsetup fails with “Download failed through BITS” (0x80070422)

Compliance Last Error: 0x80070422,Windows: The service cannot be started, either because it is disabled or because it has no enabled devices associated with it

Last State Message: Failed to download files through BITS at address.

I found that some other process was listening on port 80 and BranchCache (peerdistsvc) would not start.

There are several posts online about how to change the ListenPort for BranchCache. I can get it running by executing:

Netsh.exe br set service mode=local
REG ADD "HKLM\Software\Microsoft\Windows NT\CurrentVersion\PeerDist\DownloadManager\Peers\Connection" /v ListenPort /t REG_DWORD /d 1365 /f
Netsh.exe br set service mode=distributed

Powershell script to get remote computer certificates

I have a script that gets the remote computer certificates from the MY store, but it didn’t get certs from any other store, or the Template name.  I found how to specify the store name (or get all stores) and a script to list the template name, so I’m posting an updated version.

To get the remote computer’s Personal store:

powershell .\Get-RemoteMachineCertificates.ps1 <COMPUTERNAME>

or

powershell .\Get-RemoteMachineCertificates.ps1 <COMPUTERNAME> my

To get the remote computer’s Trusted Root Certification Authorities store:

powershell .\Get-RemoteMachineCertificates.ps1 <COMPUTERNAME> root

To get all the certificates on the remote computer:

powershell .\Get-RemoteMachineCertificates.ps1 <COMPUTERNAME> *

Output resembles:

Path : Microsoft.PowerShell.Security\Certificate::localmachine\my
Subject : CN=computername.domain.name
FriendlyName :
Issuer : CN=Company Device Management CA, DC=domain, DC=name
ExpirationDate : 3/31/2023 3:14:07 PM
Thumbprint : 4E3B34D12348B5687F0366AA7B231268A324BBBB
IntendedPurposes : Client Authentication; KeyEncipherment, DigitalSignature
Template : Company SCCM Client v1

Get-RemoteMachineCertificates.ps1:

param([Parameter(Mandatory=$true)][string] $Computer, [string] $Store = "my")

function Get-CertificateTemplateName($certificate)
{
    # The template name is stored in the Extension data. 
    # If available, the best is the extension named "Certificate Template Name", since it contains the exact name.
    $templateExt = $certificate.Extensions | Where-Object{ ( $_.Oid.FriendlyName -eq 'Certificate Template Name') } | Select-Object -First 1   
    if($templateExt) {
        return $templateExt.Format(1)
    }
    else {
        # Our fallback option is the "Certificate Template Information" extension, it contains the name as part of a string like:
        # "Template=Web Server v2(1.3.6.1.4.1.311.21.8.2499889.12054413.13650051.8431889.13164297.111.14326010.6783216)"
        $templateExt = $certificate.Extensions | Where-Object{ ( $_.Oid.FriendlyName -eq 'Certificate Template Information') } | Select-Object -First 1   
        if($templateExt) {
            $information = $templateExt.Format(1)

            # Extract just the template name in $Matches[1]
            if($information -match "^Template=(.+)\([0-9\.]+\)") {
                return $Matches[1]
            } else {
                # No regex match, just return the complete information then
                return $information
            }
        } else {
            # No template name found
            return $null
        }
    }
}

Write-Host "

To list certificates from something other than the MY store, use the following:

Store Display Name                              Store name to use
=============================================   =================================
AAD Token Issuer                                'AAD Token Issuer'
Certificate Enrollment Requests                 REQUEST
Client Authentication Issuers                   ClientAuthIssuer
Enterprise Trust                                Trust
eSIM Certification Authorities                  'eSIM Certification Authorities'
Homegroup Machine Certificates                  'Homegroup Machine Certificates'
Intermediate Certification Authorities          CA
Local NonRemovable Certificates                 'Local NonRemovable Certificates'
MSIEHistoryJournal                              MSIEHistoryJournal
Other People                                    addressbook
Personal                                        My
Preview Build Roots                             FlightRoot
Remote Desktop                                  'Remote Desktop'
Smart Card Trusted Roots                        SmartCardRoot
sms                                             SMS
Test Roots                                      TestSignRoot
Third-Party Root Certification Authorities      AuthRoot
Trusted Devices                                 TrustedDevices
Trusted Packaged App Installation Authorities   TrustedAppRoot
Trusted People                                  TrustedPeople
Trusted Publishers                              TrustedPublisher
Trusted Root Certification Authorities          Root
Untrusted Certificates                          Disallowed
Windows Live ID Token Issuer                    'Windows Live ID Token Issuer'
WindowsServerUpdateServices                     WindowsServerUpdateServices

For all stores, use *
"  -ForegroundColor "Yellow"

$Store = "cert:localmachine\" + $Store

$parameters = @{
    ComputerName = $Computer
    ScriptBlock = {Get-ChildItem $args[0] -Recurse}
    ArgumentList = $Store
}

$certs = Invoke-Command @parameters

$certs | foreach-object {
    $Usages = foreach($key in $_.Extensions) {
        if('KeyUsages' -in $key.psobject.Properties.Name ) {$key.KeyUsages}
        if('EnhancedKeyUsages' -in $key.psobject.Properties.Name) {$key.EnhancedKeyUsages.FriendlyName}
    }
    $IntendedPurposes = $Usages -join "; "

    $Template = Get-CertificateTemplateName($_)

    $output = new-object PSObject
    $output | add-member NoteProperty -Name Path -Value $_.PSParentPath
    $output | add-member NoteProperty -name Subject -value $_.Subject
    $output | add-member NoteProperty -name FriendlyName -value $_.FriendlyName
    $output | add-member NoteProperty -name Issuer -value $_.Issuer
    $output | add-member NoteProperty -name ExpirationDate -value $_.GetExpirationDateString()
    $output | add-member NoteProperty -name Thumbprint -value $_.Thumbprint
    $output | add-member NoteProperty -name IntendedPurposes -value $IntendedPurposes
    $output | add-member NoteProperty -name Template -value $Template
    $output
}

Failed to obtain exclusive access to file c:\_smstasksequence\packages\xyz01a89\framepkg.exe – Install Software failed, hr=0x80091007

We have several non-imaging task sequences that install software and do general administrative items (I know, not recommended). During the execution of one of these task sequences, the following error appeared:

Failed to obtain exclusive access to file c:\_smstasksequence\packages\xyz01a89\framepkg.exe
HashFile- exclusive access check for the file failed.
Failed to hash file, Win32 error = 4103
Verify package XYZ01A89 is updated on distribution points
Failed to resolve the source for SMS PKGID=XYZ01A89, hr=0x80091007
Install Software failed, hr=0x80091007

An internet search suggests that AV might be interfering with the CM client. This post recommends excluding the %SystemDrive%\_SMSTaskSequence folder from antivirus scanning.

Windows Server 2016 – “Windows Defender Service” won’t start – 0x80070003 (2147942403)

We had a Windows Server 2016 server where the “Windows Defender Service” service would not start – trying to start the service resulted in the message:

Windows could not start the Windows Defender Service service on local computer 0x80070003

The system cannot find the path specified

I found a question on the Microsoft website from someone with the same issue.

The marked answer said:

Solution for us was copy over "C:\ProgramData\Microsoft\Windows Defender\platform" from a working installation.

But you have to copy it offline, if you have a VM, mount the .vhdx File on the Host.

I looked on the server and found that the “platform” folder was indeed missing:

Since I don’t manage the VMWare platform, I figured I’d try to copy it over while it was running.  I tried copying and pasting in Windows Explorer and copying from the command line and neither worked, command line failed with “File creation error – The system cannot find the file specified.”

Here’s what did work:

On a working server, I copied the folder to my user profile:

WORKING SERVER

C:\Users\_tdurning>xcopy /hickey “C:\ProgramData\Microsoft\Windows Defender\platform” platform

Then on the broken server, I used Windows Explorer to browse to my profile on the working server and copied the folder.

BROKEN SERVER

And just because I’m paranoid, I made a copy of it.

I then dragged the folder “platform – Copy” to the “C:\ProgramData\Microsoft\Windows Defender” folder.

I was then able to rename the folder from the command line:

And start the service.

ConfigMgr: query to display active applications using a global condition

-- Active Applications using a global condition

declare @LocaleID int = (select LocaleID from vSMSData)

select distinct
a.DisplayName [Application]
, a.IsDeployed
, a.NumberOfDeployments
, b.DeploymentType
, b.GlobalCondition
from fn_ListApplicationCIs(@LocaleID) a
inner join 
(
select
applicationRelation.FromCIID
, dt.DisplayName DeploymentType
, c.GlobalCondition
from fn_ListDeploymentTypeCIs(@LocaleID) dt
inner join vSMS_CIRelation dtRelation on dtRelation.FromCIID = dt.CI_ID
inner join vSMS_CIRelation applicationRelation on applicationRelation.ToCIID = dtRelation.FromCIID
inner join
(
select
gc.CI_ID
, gc.DisplayName GlobalCondition
from fn_ListGlobalConditions_List(@LocaleID) gc
where
gc.IsHidden = 0
and gc.ConditionInUse = 1
--and gc.DisplayName = 'Primary device'
) c on c.CI_ID = dtRelation.ToCIID
) b on a.CI_ID = b.FromCIID
and a.IsExpired = 0
--and a.IsDeployed = 1