Public/Set-SpecDeviceToCOMPort.ps1

function Set-SpecDeviceToCOMPort {
    <#
    .SYNOPSIS
    Moves a device to a specified COM port number.
 
    .DESCRIPTION
    The Set-SpecDeviceToCOMPort function allows you to move a device to a specified COM port number in Windows. It iterates through the available COM ports, checks if a device is attached, and, if necessary, updates the COM port settings to move the device to the desired COM port.
 
    .PARAMETER PortNumber
    Specifies the target COM port number to which the device should be moved. The default is COM1.
 
    .EXAMPLE
    Set-SpecDeviceToCOMPort -PortNumber 3
    Moves the attached device to COM3.
 
    .NOTES
    File Name : Set-SpecDeviceToCOMPort.ps1
    Author : owen.heaume
    Version : 1.0
    #>


    [CmdletBinding()]
    param (
        [parameter(Mandatory = $false)]
        [int]$PortNumber = 1
    )

    # Convert the port number to a string
    $PortNumberString = "COM$PortNumber"

    # Get the COM port details for all serial ports
    $comports = Get-WmiObject Win32_PnPEntity | Where-Object { $_.caption -match '\(COM\d+\)' }


    # Iterate through the COM ports
    foreach ($comPort in $comPorts) {
        $device = $comPort.PNPDeviceID

        # Check if a device is attached to the COM port
        if ($device) {
            #if the attached device is 'Intel*' then ignore it
            #if ($comport.description -match "\bIntel") {
            # Write-Host "Intel device detected - not moving com port for this device`n" -ForegroundColor DarkYellow
            # continue
            #}

            # Check if the device is already on the specified COM port
            $oldPort = Get-SpecComPort -inputString $comport.name
            if ($oldport -eq $PortNumberString) {
                Write-Host "Device '$($comPort.Description)' is already on '$PortNumberString' No action needed." -ForegroundColor DarkGray
                return
            } else {
                Write-Host "Device needs to move to specified com port. Moving to COM$PortNumber..." -ForegroundColor DarkYellow
                # Construct the registry paths for the device
                $deviceKey = "HKLM:\SYSTEM\CurrentControlSet\Enum\$($comPort.PNPDeviceID)"
                $portKey = "$deviceKey\Device Parameters"

                # Set the new port name and update Friendly Name
                try {
                    Set-ItemProperty -Path $portKey -Name "PortName" -Value $PortNumberString -ErrorAction Stop
                    Set-ItemProperty -Path $deviceKey -Name "FriendlyName" -Value "$($comPort.Description) ($PortNumberString)" -ErrorAction Stop
                    Write-Host "Device '$($comPort.Description)' set to '$PortNumberString'" -ForegroundColor DarkGreen

                    # "COM<number>" (currently in $oldPort" needs to be just the number) for Release-SpecPreviousComPort
                    $string = $oldport
                    $afterCOM = $string -split 'COM' | Select-Object -Last 1
                    $oldPort = $afterCOM

                    Write-Host "Releasing previous port from com database..." -ForegroundColor DarkCyan
                    $status = Release-SpecPreviousComPort -OldPort $OldPort
                } catch {
                    Write-Error "Failed to update the COM port settings: $_"
                }
            }

            # No need to continue checking other COM ports
            break
        }
    }
}