Don't you hate it when you get to the office and discover you lost your house keys? You go desperately through all your pockets, but they are nowhere to be found. With a sigh, you are about to go digging through all the lost crannies in your bag when the boss pops in and reminds you that those application servers need their public-facing NICs moved to a new address space.

Of course, you could always connect remotely to each and click about 85 times in each remote session multiplied by the number of servers and NICs. And that's assuming they're not running Server Core (Server Core is good for you; please use Server Core whenever you can). Given a large enough number of servers, your house would crumble to dust before you were done. And the keys would be useless at that point anyway, assuming you've found them in the meantime.

Or, you could work smart and use Windows Admin Center. We all know that nothing is faster than a web browser when it comes to making a lot of changes. No, I'm not dissing the WAC, but honestly, it is not quite the fastest way to do A LOT of changes.

Well, worry not. The function below helps you to update the IP address of a specific computer on a specific NIC. You can also disable DHCP and even clean up the old IP addresses from the DNS.

Let's look at the code and then we can go through some of the interesting details.

function Update-IPv4Address {
<# 
.SYNOPSIS
Update-IpAddress changes the IP of a NIC and deletes the old IP Address configured on that NIC. It can also disable DHCP (or not) for that interface and disable (or not) DNS registration.
.EXAMPLE
Update-IPv4Address -ComputerName Fs1 -InterfaceAlias Ethernet1 -NewIPv4Address 192.168.1.101 -PrefixLength 24 -DisableDhcp Yes -DisableDnsRegistration No -Verbose
Sets IP Address 192.168.1.101 on server Fs1, on NIC "Ethernet1." DHCP is disabled for the NIC, and DNS registration is enabled.
.EXAMPLE
Update-IPv4Address -ComputerName Node1 -InterfaceAlias "Ethernet #5" -NewIPv4Address 10.0.1.5 -PrefixLength 16
Sets IP Address 10.0.1.5/16 on server Node1, on NIC "Ethernet #5." DHCP is disabled for the NIC, and registration is enabled.
.EXAMPLE
Update-IPv4Address -ComputerName Server3 -InterfaceAlias "LAN2" -NewIPv4Address 192.168.5.5 -PrefixLength 24 -DisableDnsRegistration Yes
Sets IP Address 192.168.5.5/24 on server Server3, on the NIC "LAN2." DHCP is disabled for the NIC, and DNS registration is disabled.

#>

[CmdletBinding()]

Param(
[Parameter(Mandatory=$false)][string]$ComputerName = $env:COMPUTERNAME, # Name of the computer where the IP Address will be udpated
[Parameter(Mandatory=$true)][string]$InterfaceAlias, # Network Interface Card on which the IP Address will be updated
[Parameter(Mandatory=$true)][string]$NewIPv4Address, # New IP Address for the selected NIC
[Parameter(Mandatory=$true)][ValidateRange(2,30)][int]$PrefixLength, # Subnet Mask for the new IP Address
[Parameter(Mandatory=$false)][ValidateSet("Yes","No")][string]$DisableDhcp = "Yes", # Define whether DHCP is enabled for the NIC 
[Parameter(Mandatory=$false)][ValidateSet("No","Yes")][string]$DisableDnsRegistration = "No", # Define whether DNS registration is enabled for the NIC
[Parameter(Mandatory=$false)][string]$DnsServer # Name of the DNS server on which the new IP address will be updated and old addresses will be removed (if DNS registration is required). If a DNS server is not mentioned, the command will be run against the logon DC (which is usually a DNS server)
)

# If a Computer Name is not provided, the operation will be performed on the local computer.
if (!($ComputerName)) { Write-Verbose "A computer name was not specified. The operation will be performed on this computer" }

# If DisableDhcp is not specified, DHCP will be disabled by default for the NIC.
if (!($DisableDhcp)) { Write-Verbose "No option was specified for disabling DHCP. DHCP on the NIC $InterfaceAlias will be disabled automatically." }

# If DisableDnsRegistration is not specified, DNS Registration will be enabled by default for the NIC.
if (!($DisableDnsRegistration)) { Write-Verbose "No option was specified for DNS registration. DNS registration for the NIC $InterfaceAlias will be enabled automatically." }

# Test whether the computer is available for remote management. Abort if it cannot be reached.
if (!(Test-NetConnection -ComputerName $ComputerName -CommonTCPPort WINRM -InformationLevel Quiet)) {
    Write-Warning "The computer $ComputerName is not reachable. Make sure the computer name `"$ComputerName`" is correct and that the computer is reachable"
    break
    }

# Test whether the NIC is present on the $ComputerName. Abort if there is no NIC with the specified Name.
if (!(Get-NetAdapter -CimSession $ComputerName | where Name -EQ $InterfaceAlias)) {
    Write-Warning "The NIC $InterfaceAlias could not be found on  $ComputerName. Aborting the operation."
    break
    }

# If DNS registration is required for the NIC, check that the DNS server service is running on the $DnsServer (and abort if it is not).
if ($DisableDnsRegistration -eq "No") {
    if (!(Get-Module -ListAvailable DnsServer)) {
        Write-Warning "The function requires the module DNSServer in order to perform operations on a DNS server. Please install the Powershell Module for DNS Management and run the function again. The syntax for installing the DNS Server PowerShell Module is: Install-WindowsFeature -Name RSAT-DNS-Server"
        break
        }
  
    # If a DNS server is not specified, DNS operations will be attempted on the logon DC (DCs are usually DNS servers).
    if (!($DnsServer)) {
        $DnsServer = ($env:LOGONSERVER).Replace("\","")
        }
    # If the service is not running, the operation will be aborted.
    if (((Get-Service -ComputerName $DnsServer -ServiceName DNS -ErrorAction SilentlyContinue).Status) -ne "Running") {
        Write-Warning "You have selected to enable DNS registration for the NIC $InterfaceAlias but have not provided a valid DNS server. Please run the command again and specify a valid DNS server"
        break
        }
    }

# Get the current IPv4 address(es). These will be replaced with the new IP Address.
$OldIpv4Address = Get-NetIPAddress -CimSession $ComputerName -InterfaceAlias $InterfaceAlias -AddressFamily IPv4 

# Perform changes if the new IP address is different.
if ($NewIPv4Address -notin $OldIpv4Address.IPv4Address) {

    # Set the new IP address to the target on the NIC.
    Write-Verbose  "Adding the IP Address $NewIPv4Address to the NIC $InterfaceAlias on computer $ComputerName"
    New-NetIPAddress -CimSession $ComputerName  -InterfaceAlias $InterfaceAlias -AddressFamily IPv4 -IPAddress $NewIpv4Address -PrefixLength $PrefixLength -Type Unicast | Out-Null

    # Configure DNS and DNS registration, if required. Also register the client in DNS.
    if ($DisableDnsRegistration -eq "No") {
        
        # Notify that the function will attempt to use the logon DC for the local computer as DNS server.
        Write-Verbose  "No DNS server was specified. Will use the logon DC ($DnsServer) for the computer $env:COMPUTERNAME as DNS server" 
        
        # Get the IP Address(es) of the DNS server(s) from the local computer.
        $DnsServerIpAddress = (Get-WmiObject -Class Win32_NetworkAdapterConfiguration -Filter IPEnabled=TRUE | where DNSDomain -EQ $env:USERDNSDOMAIN).DNSServerSearchOrder
        
        # Get a list of entries in DNS for the old IP Address(es) for $ComputerName.
        $OldServerDnsEntries = Get-DnsServerResourceRecord -ComputerName $DnsServer -ZoneName "$env:USERDNSDOMAIN" -RRType A | Where-Object {$_.Hostname -like $ComputerName} | Select-Object HostName,@{Name="IpAddress";Expression={$_.RecordData.IPV4Address.IPAddressToString}}
        
        # Set the IP address(es) for the DNS Server(s) on the NIC.
        Write-Verbose  "Add the DNS server(s) $DnsServerIpAddress to the NIC $InterfaceAlias on computer $ComputerName"
        Set-DnsClientServerAddress -CimSession $ComputerName -InterfaceAlias $InterfaceAlias -ServerAddresses $DnsServerIpAddress
        
        # Enable DNS registration for the NIC.
        Write-Verbose  "Enable DNS registration for the interface $InterfaceAlias on $ComputerName"
        Set-DnsClient -CimSession $ComputerName -InterfaceAlias $InterfaceAlias -RegisterThisConnectionsAddress $true
        # Register the server in DNS.
        Register-DnsClient
        
        # Wait for the host to learn the new IP Address of the computer $ComputerName.
        Write-Verbose  "Waiting for this computer ($env:COMPUTERNAME) to learn the new IP Address of the computer $ComputerName..."

        # Wait for the new IP Address to appear in DNS.
        while ($NewIPv4Address -notin ((Resolve-DnsName -Name $ComputerName -Server $DnsServer).IPAddress)) {
            Clear-DnsClientCache
            Start-Sleep -Seconds 1 
            #$CheckIp = (Resolve-DnsName -Name $ComputerName -Server $DnsServer).IPAddress
            }
        }
    
    # Disable DNS registration, if required.
    else {
        Write-Verbose  "Disable DNS registration for the NIC $InterfaceAlias on $ComputerName"
        Set-DNSClient -CimSession $ComputerName -InterfaceAlias $InterfaceAlias –RegisterThisConnectionsAddress $False
        }

    # Disable DHCP, if required.
    if ($DisableDhcp -eq "Yes") {
        Write-Verbose  "Disabling DHCP for the interface $InterfaceAlias on $ComputerName"
        Set-NetIPInterface -CimSession $ComputerName  -InterfaceAlias $InterfaceAlias -AddressFamily IPv4 -Dhcp Disabled -ErrorAction SilentlyContinue
        }

    # Go through each of the old IP Addresses and remove them from DNS.
    foreach ($i in $OldIpv4Address) {
        # Clean up old IP address entries in DNS and on the NIC.
        if ($i.IPv4Address -in $OldServerDnsEntries.IpAddress) {
            Write-Verbose  "Removing IP Address $($i.IPv4Address) from DNS"
            Remove-DnsServerResourceRecord -ComputerName $DnsServer -ZoneName "$env:USERDNSDOMAIN" -RRType A -Name $ComputerName -RecordData $i.IPv4Address -Force -ErrorAction SilentlyContinue
            Start-Sleep -Seconds 1
            }
        }

    Clear-DnsClientCache
    # Remove the old IP Addresses from the interface.
    foreach ($i in $OldIpv4Address) {
        Write-Verbose  "Removing IP Address $($i.IPAddress) from NIC $InterfaceAlias on $ComputerName"
        Remove-NetIPAddress -CimSession $ComputerName -InterfaceAlias $InterfaceAlias -AddressFamily IPv4 -IPAddress $i.IPAddress -Confirm:$false
        }
    }
# If the new IP address is not different, display a notification that the address is the same.
else { 
    Write-Verbose  "The IP address provided is already set on the NIC `"$InterfaceAlias`" on computer $ComputerName. No change was made" 
    }
}

There are a few parameters the function expects you to provide:

  • First, a computer name. If none is provided, it will attempt to perform the changes on the local computer. The function is kind enough to mention this to you (if you selected Verbose mode).
  • Then, you will need to provide a new IP address. I'm quite proud of this function, but I'll be the first to admit it is not able to guess an IP address for you. I know, I know...
  • You can disable DHCP on the NIC by setting the parameter DisableDhcp. If you don't specify it, it will be disabled by default. Once again, the function is kind enough to inform you about this (still assuming you're running the function with the Verbose switch).
  • You can also disable DNS registration for the NIC. Normally, you wouldn't be interested in doing that on a "public-facing" NIC, but if the network interface will be used for management or as part of a cluster-traffic-only subnet, you may want to skip this. You need to specify this with the value "Yes;" otherwise, DNS registration will not be disabled. Once again, the function is kind enough to inform you about this.
  • A DNS server. This is where the function will attempt to connect and clean up the old IP address. If one is not provided, it will attempt to do this on the DC your computer is logged on to. Normally, the DCs are DNS servers, too. If they are not DNS servers in your environment, or you are not in an AD environment, well ... please do provide a DNS server. You're probably used to it by now, but ... yes, the function will inform you. Just make sure you've selected Verbose mode.

You can get more information by using Get-Help Update-IPv4Address.

(Hint: also try the switch -Examples).

Once you've provided all these bits of information, the function will attempt to connect to the target computer. As this will be done via WinRM, the function will check for connectivity on that port. You don't need ping for this, and you don't need to allow all inbound traffic in the Windows Firewall. You don't allow all inbound traffic through the Windows Firewall for your computers, do you? Do you? I know, I was just making sure. Good job. Anyway, WinRM is enabled by default on modern Windows Server versions. If you disabled it previously, you'll need to enable it, at least for the computer where you're doing this.

Anyway, if the computer is reachable, the function will check whether the new IP address isn't already configured on your target computer and on the target NIC. If it is, you'll be prompted about this, and the function will stop. Gently.

If the IP address is different, the function will perform the following:

  • Assign the new IP address to the specified NIC on the target computer.
  • Configure DNS registration (if instructed to do so).
  • Register the address in DNS.
  • Wait for the local computer (the computer from which you're running the function) to "learn" the new IP address of the target computer.
  • Disable DNS registration (if prompted to do so). Of course, if you omitted this or mentioned that you wanted DNS registration, this step will not be performed.
  • Remove the old IP address(es) from the specified NIC on the target computer. If Verbose mode is selected, you will be informed about these old addresses, too.
Remotely updating and IP address with Update IPv4Address

Remotely updating and IP address with Update IPv4Address

First, we look at the IP address of our target computer, DC1. (If you're interested in Get-IPAddressPretty, give us a shout and I'll create a quick post about it, too.) The NIC we're interested in has the current IP address 10.0.1.51.

Then, we use our shiny function to update the IP address of the NIC (creatively) named "TheOtherNic" to 10.0.1.101. Check the result and you'll see the new address assigned to the NIC.

Subscribe to 4sysops newsletter!

Finally, we update it again (this time to 10.0.1.102), using the Verbose switch. This will show more information about what the function does.

avatar
7 Comments
  1. checker33 1 year ago

    Hi, very helpful. But how can i wrap this , so use the function under domain administrator creds?

    • Author

      Hi, Checker33. Thank you for the feedback, I am glad you found this useful.

      Yes, you may include the function in a custom PowerShell Module that you can load manually or automatically in your PowerShell console, editor etc. If the previous sentence sounds intimidating, create a new file with the extension ".psm1" (like "MyCustomfunctions.psm1"). Paste the code from this post in the psm1 file, and save it. When you want to run the function, import the module (Import-Module 'C:\temp\MyCustomfunctions.psm1") and then the function will be available.

      You may also save as a normal PowerShell script file (PS1), and then reference it using the . (dot). Yes, the command begins with a dot followed by a space and then the path to the PS1 file.

      . "C:\temp\MyCustomfunctions.ps1"

      If you're interested in more details, I could write a post on how to do this (both manually or automatically).

      Cheers. Emanuel

  2. David H 1 year ago

    Would it be possible to have this script be performed by MAC Address from a list?  I am ultimate trying to update my DNS Server on about 200 PCs.  I have a script that updates the DNS for ALL the NICs in the PC, but I dont want it on the NICs that are on private networks, actually would love to disable DNS registration on those NICS as well .

    • Author

      Hi, David.

      If you have a list of servers and their NICs, you a command like below to rename the NICs you want to make changes to, and then run the function explained here based on that Interface Alias.

      Get-NetAdapter -CimSession ServerX | where MacAddress -Like AB-CD-EF* | Rename-NetAdapter -NewName "NoIpForYou"

      If you only want to disable DNS registration on certain Mac Addresses you already have, you could even ditch the function and do something like this:

       Set-DnsClient -InterfaceIndex $((Get-NetAdapter  -CimSession ServerY | where MacAddress -Like AB-CD-EF*).ifIndex) -RegisterThisConnectionsAddress $false

      avatar
  3. Jake 12 months ago

    Hey David,

     

    Great function, I'll gladly use this.  Just a quick note, it appears to be lacking a closing brace for your function?  I think I understand the contents enough to put it in the right place, just wanted to mention it.

    • Author

      Hello, Jake.

      By the looks of it, yes, you are right. The last bracket in the code is the closing one for the last else statement.

      As the function was working (I checked and tested it thoroughly), most likely the function's closing bracket was lost in the posting process. 🙂

      I don't have access to change it (or I don't think I do), I'll point this to someone that definitely has.

      Cheers for the heads-up!

      Em.

       

Leave a reply to Emanuel Halapciuc (Rank: 2)
Click here to cancel the reply

Please enclose code in pre tags

Your email address will not be published. Required fields are marked *

*

© 4sysops 2006 - 2021

CONTACT US

Please ask IT administration questions in the forums. Any other messages are welcome.

Sending

Log in with your credentials

or    

Forgot your details?

Create Account