PowerShell

Active Directory Fine-Grained Password Policies

This post isn’t going to set the world on fire because of it’s revelations and new features; instead, I am going to talk about a feature that has been around since Windows Server 2008 called Fine Grained Password Policies.

Active Directory Password Policies are, even in 2018, still misunderstood. For all the consulting engagements I do, I still encounter customer environments where admins have tried to configure multiple Group Policy Objects to control password policy at various levels within their OU structure. An example of this behaviour would be to set the Default Domain Policy object to a standard password complexity and then have an OU containing administrative accounts for Domain Admins which has a GPO applying a more complex policy.

Read more…

Active Directory 2016 Time-Based Group Membership

Group membership control and management is one of the cornerstones of Active Directory Domain Services. In Windows Server 2016, Microsoft introduced a new feature to Active Directory that forms part of the Microsoft Privileged Access Management (PAM) strategy.

When used in conjunction with automation, this can be used to provide Just-In-Time (JIT) access to protected and administratively sensitive services. When used in an environment that is synchronised with Azure Active Directory using Azure AD Connect, this can be used to provide JIT for hybrid solutions in Microsoft Azure (when RBAC has been applied to Azure Resource Manager objects).

In this post, I will briefly explain the processing for implementing time-based group membership in Active Directory.

Read more…

Set a Registry Value Using PowerShell Containing a Forward Slash

I don’t normally blog about PowerShell as it’s just a day-to-day thing that we all do and use (you do all use PowerShell right) but I came across a problem today that I thought I would share as I had to run the net to find the solution for myself.

A co-worker came to me today asking for help with some PowerShell code for a script he is writing. The script is to apply some registry settings to machines for a piece of security hardening work which includes disabling some of the less secure SSL and TLS cipher suites. All is going well until he gets to the line of the script that tries to disable the DES 56/56 cipher suite and PowerShell throws it back at him. The reason for it is because PowerShell is treating that forward slash character as a separator for a multi-value string.

Here is the line of code that you would run normally to create the registry key for DES 56/56:

New-Item -Path “HKLM:\SYSTEM\CurrentControlSet\Control\SecurityProviders\SCHANNEL\Ciphers\DES 56/56"

When this runs, PowerShell creates a registry key for DES 56 but then it creates a sub-key for the second 56 as it’s seen as a separator which obviously isn’t what we want. I tried all sorts to get around it such as changing the double quotes for single quotes and first placing the path into a variable and calling in the variable but it just would not have it.

I managed to eventually find a way around this but it means that we can’t use the PowerShell Cmdlet New-Item but instead, we have to use the .NET way of things. Here’s the code sample to make it work:

$Writable = $True
$Key = (Get-Item HKLM:\).OpenSubKey(“SYSTEM”, $Writable).CreateSubKey(“CurrentControlSet\Control\SecurityProviders\SCHANNEL\Ciphers\DES 56/56”)
$Key.SetValue(“Enabled”, “0”, [Microsoft.Win32.RegistryValueKind]::DWORD)

 

Managing Offline Sync in OneDrive for Business

Yesterday, I released a post explaining how we can control and manage some of the sharing capabilities of SharePoint Online. Those changes applied not only to SharePoint Online but also to OneDrive for Business such as whether or not a user can share a file publicly with an anonymous link.

In this post, I am going to focus on the offline sync capability of OneDrive for Business. This feature allows a user to have access to their OneDrive for Business files on their PC or Mac device and work on them offline and when they come back online, changes are synchronised back up to OneDrive for Business. The OneDrive for Business client allows not only syncing for offline access of a users personal site folders but also of team site folders and data. In some cases, people are even using this feature to replace their Folder Redirection shares on the local network to a file server and have users work go up to OneDrive for Business by default making the most of that 1TB per user allowance and reducing your on-premise storage management and purchasing costs. In other cases, you could use this to allow employees working remotely to have access to a central team site that contains all of your document templates or marketing collateral.

While this offline sync capability is very useful, it also comes with a price. Imagine a scenario with a disgruntled employee: Using their home PC, they login to OneDrive for Business and configure their client to sync their folders and files at home. Now, this user has copies of all of their corporate work product at home, free to take it or sell it to a competitor or such. Another scenario is that somebody gains access to your SharePoint Online environment and takes a copy of a sensitive folder of documents and then publishes them online, exposing your company.

Luckily, after all this scaremongering, we can control it although this is a new feature so it’s not something we could have done before.

Turn Off Offline Sync for a Library

The easiest way to protect sensitive content is to prevent it from being synchronised for offline access so that OneDrive for Business clients cannot take copies of it with them offline. Yes, this method as no neither of the methods given stop someone physically downloading a copy of files but it stops them doing it en-masse using the OneDrive for Business client as a bulk collection tool.

Within SharePoint Online, access the Library Settings for your particular library type and then head into the Advanced Settings section.

SharePoint Online Disable Offline Sync

As you can see, in the Advanced Settings, we have the option to disable offline sync. As I said before, this is a great option for really sensitive areas that you just flat-out do not want kept offline but it’s not ideal for your honest corporate employee nor is it very scalable as this is a per library setting so unless you want to iterate all your libraries with PowerShell or some automation tool, this will get old and very time consuming fast.

Limiting Offline Sync to Domain Clients

With this new feature for OneDrive for Business, we can now control whether or not a client is able to sync offline content based on whether their computer is a member of a given number of Active Directory domains. With this feature, we can allow our employees to sync files offline but we can limit the scope of it to our domain managed client PCs.

There are two caveats that come with this new capability. First, this is a tenant-wide setting so once you apply this, you will not be able to perform offline sync with OneDrive for Business for any library in your tenant outside of one of the configured domains. The second is in the detail in the previous paragraph – PCs. Because a domain joined Mac client is not really a fully-fledged domain member like a Windows Client OS, changing this setting disables offline sync for Mac devices regardless of whether they are joined to your domain or not. We can hope this is something that might get fixed in the future as this is the first release of this feature but we just don’t know right now.

Right now, this change does not effect or limit mobile OneDrive for Business apps in any way just as an FYI but that is where Office 365 MDM comes in to play which I will hopefully get a chance to cover in a future post.

So to get started implementing this, we first need to get the GUIDs for our domains. These are unique hexadecimal strings which uniquely identify our domain. To get the GUIDs for all of the domains in our forest, we can use the following PowerShell Cmdlets from a PC with the Active Directory PowerShell Module installed from the RSAT Tools.

Import-Module ActiveDirectory
$Domains = (Get-ADForest).Domains; ForEach($D in $Domains) {Get-ADDomain -Identity $D | Select Name, ObjectGuid}

This Cmdlet comes from the Microsoft TechNet page at https://technet.microsoft.com/en-us/library/dn938435.aspx on how to get domain GUIDs but I have added the Name column to the output. I know that it is likely in the real world that we may have resource or selected domains that we don’t want to allow sync to occur in so this way, we can see which domains relate to which GUID and we can filter them out as needed.

With the domain GUIDs in hand, we can now configure SharePoint Online. Using a PC with the SharePoint Online PowerShell Module installed, enter the following Cmdlets:

Connect-SPOService -Url https://tenantname-admin.sharepoint.com -Credential admin@domain.com
Set-SPOTenantSyncClientRestriction  -Enable -DomainGuids "786548DD-877B-4760-A749-6B1EFBC1190A; 877564FF-877B-4760-A749-6B1EFBC1190A"

So as you will be able to see in the example above, firstly, you need to change the Url parameter to match your Tenant Admin URL and you also need to enter your Global Administrator or SharePoint Online Administrator credentials. On the second line, I’ve entering the domain GUID for two domains which are semi-colon separated. If you have just one then omit the semi-colon.

Once the change is applied, users will no longer be able to sync content for offline access with OneDrive for Business unless they are using a corporate managed, domain joined machine in one of the domains you have specified or from any Mac clients. Any users who have configured offline sync with OneDrive for Business on non-domain joined machines prior to the change will stop syncing any new changes but the existing content will not be deleted from the client so it is important to implement this change early if you are starting out in Office 365 today.

 

Managing Sharing and Access in SharePoint Online

For many organisations using SharePoint on-premise, SharePoint Online is a very appealing proposition. For administrators, it’s easy to deploy as you no longer have to worry about farm topology design and sizing your SQL Server disks to meet your capacity and performance objectives nor do you have to open firewall holes left, right and centre to give your users the collaboration tools they require when they are on the move as access to your corporate SharePoint sites and OneDrive for Business is all done in the cloud.

For some organisations, SharePoint Online and it’s broad sharing capabilities will present a headache at the same time because managing the risk that comes with this open accessibility of information can add up and depending on your particular circumstances, you may want to restrict certain aspects of this to ensure that your corporate data stays safe. In this post, I’m going to address some of the things we can do to configure SharePoint Online to manage those risks using both some existing features and some newly added features.

Default Sharing Settings

By default, SharePoint is actually a pretty open book allowing your end-users to share anything with potentially anyone. We can share files with selected users within our organisation, all users within our organisation or external parties. The default configuration allows us to generate a sharing link that we can send out to third-parties and they will be able to view the file without needing to authenticate or prove who they are.

Get the SharePoint Online PowerShell Module

For this post, we are going to be working with the SharePoint Online PowerShell Module and you will need to have the latest version which includes all of the new Cmdlet parameters. To download this, you can get it from http://www.microsoft.com/en-gb/download/details.aspx?id=35588.

Connect to Your SharePoint Online Tenant

In order to use the SharePoint Online PowerShell Cmdlets, you need to be either a SharePoint Administrator a Global Administrator in your Office 365 tenant. Once you have the relevant permissions, open PowerShell and enter the Connect-SPOService to authenticate as follows:

Connect-SPOService -Url https://tenantname-admin.sharepoint.com -Credential admin@domain.com

You will be prompted to enter your password for the credential provided and once entered you will be connected to your SharePoint Online tenant. We can view the current configuration of the tenant sharing configuration using the Cmdlet Get-SPOTenant.

Restricting External User and Guest Sharing Setting

By default, SharePoint Online allows us to share with both registered external users and guest users with a link. We can control this setting with the SharingCapability parameter with the following examples:

Set-SPOTenant -SharingCapability ExternalUserAndGuestSharing
Set-SPOTenant -SharingCapability ExternalUserSharingOnly
Set-SPOTenant -SharingCapability Disabled

The top setting, ExternalUserAndGuestSharing is the default and allows sharing links to be sent to both authenticated users who sign in to access content with a Microsoft Account and guest users. The risk with this is that the links sent to guest users could be forwarded to other people once sent out or even shared publicly online exposing your content.

The second setting, ExternalUserSharingOnly allows sharing to take place but limits it to users who sign in with a Microsoft Account to access the content. Additionally, these links are one-time use which means once a user has accessed the link they will continue to be able to view that content but forwarding or outwardly sharing the link will not allow anyone else access to it without the original Microsoft Account credentials.

When applied using the above Cmdlets, this is set at the tenant level. Administrators of Site Collections within the tenant can change this setting on a per Site Collection basis however they cannot make the setting less secure that the tenant level setting. If for example, you set the tenant level setting to only allow authenticated users to access shared content, a Site Collection administrator would only be able to select between externally authenticated sharing or no sharing at all and the guest sharing option would be disabled.

We can couple the above setting for only allowing external users who are authenticated with another PowerShell Cmdlet.

Set-SPOTenant -RequireAcceptingAccountMatchInvitedAccount $True

This setting which is disabled by default but can be enabled, ensures that only the person who is sent an authenticated user sharing link can use the link. In it’s default state, a link for sharing can be sent out to a third-party user for them to authenticate with using a Microsoft Account however if they do not click the link to perform the initial binding to their Microsoft Account and instead, forwarded it to somebody else who signed in using their Microsoft Account would allow this alternate individual access to the document. Although this is quite a rare scenario to consider, it is still possible none-the-less.

For example, you send a link to dave@richardjgreen.net but Dave forwards the link to bill@richardjgreen.net and Bill opens the link and binds it to his Microsoft Account allowing Bill access to the document rather than Dave as you had intended.

This setting when enabled records the email address that the sharing link was sent to and will only allow the Microsoft Account named in the original invitation to use it and bind to it. My personal take on this is that if you are changing the default sharing behaviour to only allow authenticated user sharing then this setting is a must have.

Hiding Wide-Scoped Sharing Options

In SharePoint Online, not only can we share content externally but we can share content internally. Sometimes, especially in large organisations, this over-sharing can lead to people seeing things they perhaps shouldn’t. Microsoft have very recently added new Cmdlets to the PowerShell library for SharePoint Online to allow us to control this as shown below:

Set-SPOTenant -ShowAllUsersClaim $False
Set-SPOTenant -ShowEveryoneClaim $False
Set-SPOTenant -ShowEveryoneExceptExternalUsersClaim $False

These settings when configured as False using these Cmdlets remove certain groups from the people pickers in SharePoint Online when we invoke a sharing request.

The first setting, ShowAllUsersClaim controls whether users have the ability to share something with everyone within your Azure Active Directory tenant. This object includes both users who are internal to your organisation and users who have previously accepted sharing invitations. When this is disabled, users will not be able to see the All Users objects listed in the people picker so will not be able to broadly share anything to the entire organisation

The second setting, ShowEveryoneClaim controls whether to show or hide the Everyone object. The everyone object includes both internal users and external users but it includes external users of the authenticated and unauthenticated varieties so this object is the most damaging in terms of scope. You could argue this is less of an issue if you have already disabled the ability to share with unauthenticated users using the Cmdlets in the previous section but if that is the case, why confuse your end-users with the two different entities.

The final setting option is ShowEveryoneExceptExternalUsersClaim. This last option controls the Everyone Except External Users object. This object controls whether or not you are able to share something to your entire organisation but not to individuals outside it whether they are authenticated or not.

My personal feeling on this is that All Users and Everyone should be hidden for most people and that you could leave the final option for Everyone Except External Users enabled if you want to give your users the ability to broadly share within the organisation.

Limiting OneDrive for Business Sync Capabilities

UPDATE: In a partner post which I released the day after this was published, I have covered how we can manage and limit the OneDrive for Business client and it’s offline synchronisation capabilities to managed devices. You can see that post at http://richardjgreen.net/managing-offline-sync-onedrive-for-business/.

Power On Hosts Out of Band with IPMI and PowerShell

As part of my home lab project, I built my servers using Supermicro X8DTH-6F motherboards for many reasons however one of these reasons was that the motherboard hosts an IPMI base management controller (BMC) interface for managing the power state of the host out-of-band along with the ability to access the IP KVM and virtual media support to allow me to access the server console session remotely and even attach .iso media over the network.

In my quest to make my lab more accessible I wanted to be able to script the procedure for starting it and shutting it down and whilst I haven’t given a whole heap of thought to the whole thing just yet, I have made an interesting discovery in the quest. Windows Server 2008 R2 introduced a PowerShell syntax PcsvDevice with various commands including Get, Start and Stop along with another Cmdlet Set-PcsvDeviceBootConfiguration.

These Cmdlets were first introduced in Windows Server 2008 R2 and the syntax for some of the parameters changed in Windows Server 2012 which is worth noting if you have used these Cmdlets previously. Using the Get-PcsvDevice Cmdlet, we can query IPMI, WS-Man and SMASH based base management controllers and get some information back from them. We need to feed this command some parameters such as a credential and an IP address for the BMC.

$Cred = Get-Credential ADMIN
$Ip = "172.16.150.21"
Get-PcsvDevice -TargetAddress $Ip -ManagementProtocol IPMI -Credential $Cred

As you can see, I set variables for $Cred and $Ip to set the username and the IP address to connect with and the ManagementProtocol parameter allows us to specify whether the controller is IPMI or WS-Man based. The result from this command in my environment is as follows.

PowerShell Get-CsvDevice Output

So from the screenshot, we can see that the Get-PcsvDevice Cmdlet can detect my Supermicro IPMI interface and the EnabledState column in the output shows that my host is currently Disabled or in other words, powered off. So now that I know PowerShell can find my BMC, I want to be able to power on the host. By piping the Get-PcsvDevice Cmdlet into the Start-PcsvDevice Cmdlet, we can do just that.

$Cred = Get-Credential ADMIN
$Ip = "172.16.150.21"
Get-PcsvDevice -TargetAddress $Ip -ManagementProtocol IPMI -Credential $Cred | Start-PcsvDevice

After entering the Cmdlet, I heard my server spin up in the rack downstairs. I opened up a command prompt in a separate window and started pinging the management IP address of the host which would start pinging once Windows Server 2012 R2 started after the boot POST.

PowerShell Start-PcsvDevice Output

As you can see from this second screenshot, the host started to ping on its management address and I assure you, there is no magic here like me running downstairs and hitting the power button, this all happened via PowerShell remotely. Running the Get-PcsvDevice Cmdlet again now would return a similar output except the EnabledState column now reports Enabled as the host is powered on.

The opposing Cmdlet is Stop-PcsvDevice however I won’t be demonstrating this one and I’ll provide a warning to go with it. This PowerShell Cmdlet does not instruct the IPMI or WS-Man interface to perform a graceful soft shutdown using the operating system commands. It performs a hard off as it someone had just held down the power button. If your server is running and accessible via normal in-band management means, power it down that way such as the PowerShell Cmdlet Stop-Computer.

The other command which is available to us is Set-PcsvDeviceBootConfiguration. I won’t demonstrate this one either as I like my server how it’s configured right now but this Cmdlet can be used to change the boot order of a server. If for example, you wanted to set a server to Boot from LAN over PXE so that you could apply some out-of-band update or image to it then you could do that. You can get the syntax for Set-PcsvDeviceBootConfiguration or any of the other Cmdlets from TechNet at https://technet.microsoft.com/en-us/library/dn283384.aspx.

 

SMB Multichannel Constraint FQDN and Hostname

Today, whilst working on something in my home lab, I noticed an issue with SMB Multichannel which if you are using SMB Multichannel in your environment you will want to be aware of.

I’ll cover how to make SMB Multichannel actually work in another post, but for now, I’ll just cover the issue. I had configured my SMB networks using the New-SmbMultichannelConstraint Cmdlet to prevent the SMB traffic for my Hyper-V VMs from using my management network and I had assumed that all would work nicely, however when I ran the Get-SmbMultichannelConnection Cmdlet, I noticed that the Client IP and Server IP columns showed the address of my management network adapters and not the SMB adapters when it struck me.

I had registered the SMB Multichannel Constraint using the NetBIOS hostname of the servers however my Hyper-V server is using the FQDN of the storage server to connect to the SMB share with the VM data in it. I ran the New-SmbMultichannelConstraint Cmdlet again but this time registering the FQDN of the hosts on both side of the connections and shortly afterwards, running the Get-SmbMultichannelConnection Cmdlet, I observed that the connections where now being made to and from the Client and Server IPs in the SMB networks.

The bottom line here is that you should register SMB Multichannel Constraints for both your NetBIOS and FQDN server names. You may well design your Hyper-V deployment to use the FQDN after registering the constraint for the FQDN but you don’t know what other administrators are going to do long-term and having both the NetBIOS hostname and FQDN registered will prevent and potential issues down the road.

Invalid License Key Error When Performing Windows Edition Upgrade

Last week, I decided to perform the in-place edition upgrade from Windows Server 2012 R2 Essentials to Windows Server 2012 R2 Standard on my home server as part of a multitude of things I’m working on at home right now. Following the TechNet article for the command to run and the impact and implications of doing the edition upgrade at http://technet.microsoft.com/en-us/library/jj247582 I ran the command as instructed in the article but I kept getting a license key error stating that my license key was not valid.

As my server was originally licensed under a TechNet key, I wondered if the problem could be down to different licensing channels preventing me from installing the key. On the server, I ran the command cscript slmgr.vbs /dlv to display the detailed license information and the channel was reported as Retail as I expected for a TechNet key. The key I am trying to use is an MSDN key which also should be reported as part of the Retail channel but to verify that, I downloaded the Ultimate PID Checker from http://janek2012.eu/ultimate-pid-checker/ and my Windows Server 2012 R2 Standard license key, sure enough is good, valid and just as importantly, from the Retail channel.

So my existing and new keys are from the same licensing channel and the new key checks out as being valid so what is the problem? Well it turns out, PowerShell was the problem.

Typically I launch a PowerShell prompt and then I enter cmd.exe if I need to run a something which explicitly requires a Command Prompt. This makes it easy for me to jump back and forth between PowerShell and Command Prompt within a single window hence the reason for doing it. I decided to try it differently so I opened a new Administrative Command Prompt standalone, without using PowerShell as my entry point and the key was accepted and everything worked as planned.

The lesson here is this: If you are entering a command into a PowerShell prompt and it’s not working, try it natively within a Command Prompt as that just maybe is your problem.

Deploying Windows Server 2012 Primary Computer Setting

For companies (or homes) using roaming profiles and folder redirection, Microsoft gave you are great new feature in Windows Server 2012 called Primary Computer. This feature hasn’t been talked about that much although it really should have been. The Primary Computer feature allows you to define the primary computer for a user in Active Directory on a user object. Once applied to a user account it prevents the distribution of their roaming profile on non-primary devices and for folder redirection, disables the ability to sync the folders with Offline Files for non-primary devices.

So What is the Benefit

This is ideal for several reasons. Firstly, it helps to reduce profile corruption for roaming profile users when roaming between machines which may be running different versions of Windows or different architectures. Also for roaming profile users, it greatly improves logon and logoff times for non-primary devices. If a user is logging on to a kiosk computer for example, they don’t need their roaming profile and they probably just want to access a service or application quickly so why wait for it? For users of folder redirection, this means that the user is able to access their files when the computer is on the network and can access the file share resource which hosts those redirected folders, but they are non cached using Offline Files. For the business, this is a great security benefit as it means that somebody logging on to a temporary machine isn’t going to be caching all of those files, files which they could potentially leave on the train or in an aeroplane overhead locker. For laptops which typically have small hard disk capacities this is useful for both roaming profile and folder redirection scenarios as it means that you aren’t pulling down potentially gigabytes of data to the local machine clogging up the disk.

Implementing Primary Devices Using Active Directory Administration Center

First, launch the Active Directory Administrative Center and navigate your OU structure to find the computer object for the computer that you want to make primary for a given user, or if you already know the machine name, use the search feature to locate it.

Primary Computer Finding Distinguished Name

From the computer account object, scroll down to the bottom of the view and select the Attribute Editor tab. Scroll through the list of attributes to find the distinguishedName attribute and select the View button to show the full DN.

Primary Computer Copy Distinguished Name

On the String Attribute Editor, right click the pre-highlighted text and select the Copy option from the context menu. Cancel out of the Attribute Editor and cancel out of the computer object view.

With the DN of the computer now in the clipboard, find the user that you want to make this the primary computer for either by searching or again, navigating your OU structure.

Primary Computer Set User msDS-PrimaryComputer

On the user account, do as we did with the computer account a moment ago, scroll down and select the Attribute Editor tab. Scroll through the list of attributes until you locate the msDS-PrimaryComputer attribute then click the Edit button. Right-click in Value to Add box and select Paste from the context menu to paste in the DN of the computer then select the Add button.

Click OK to close the Multi-Valued String Editor dialog then click OK to exit out of the user account properties. Your work here is done.

Implementing Primary Devices Using PowerShell

Out of the box, there is actually no neat way of implementing Primary Devices using PowerShell. To do it, we have to plug a few Cmdlets together. Firstly, get the attributes for the computer and store them in an object. $Computer = Get-ADComputer Computer1 (where Computer1 is the name of the computer). Next, we map the computer that we just stored in the $Computer object to the user. Set-ADUser User1 -Add @{‘msDS-PrimaryComputer’ = “$Computer”} (where User1 is the name of the user). With those two Cmdlets out of the way, the partnership between the user and the computer should now be done, but we can verify this with the following Cmdlet. Get-ADUser User1 -Properties msDS-PrimaryComputer

Configuring Folder Redirection and Roaming Profiles

Now that we’ve setup Primary Computer attributes for some users, it would probably be a good idea if our Group Policy settings for Roaming Profile and Folder Redirection actually honoured these settings and only transferred out the data to the users’ primary computers. The setting for Folder Redirection is available as both a User Setting and a Computer Setting in Group Policy whereas the Roaming Profile setting is only available as a Computer Setting. Because of the fact you can’t apply both of these policy settings from a single policy if you decide to use user targeting, my advice is to apply this as a computer policy. It makes good sense to keep these two settings together as it means you can see that you are applying the Primary Computer setting to both roaming profiles and folder redirection in one view and it means you can give your Group Policy Object a meaningful name like Primary Computer Roaming Settings or the like.

From the Group Policy Management Console, navigate to the Computer Configuration > Administrative Templates > System. From the System node, you will find the Folder Redirection and User Profiles nodes.

Inside the Folder Redirection node, enable the Redirect folders on primary computers only policy setting. Inside the User Profiles node, enable the Download roaming profiles on primary computers only setting.

Storage Spaces Inaccessible After Windows Server 2012 R2 Upgrade

Windows Server 2012 R2 has some nice new features and improvements on existing features for users of Storage Spaces so there is a definite appeal for users of Windows Server 2012 to want to upgrade to Windows Server 2012 R2.  If you opt to do an in-place upgrade to preserve your existing Storage Spaces so that you can get your service up and running with the hope of being able to use them straight off the bat in Windows Server 2012 R2, you may encounter an error Read-only by user action and you need to perform some corrective steps to use them again.

Storage Space Read-Only User Action

This is what your Storage Spaces may look like if you open the Storage Spaces control panel item after the upgrade. As you can see, the spaces are in-tact and will report all of the space names and capacity from prior to the upgrade but instead of being online as you are used to seeing, you instead have this information icon and a message alongside the pool capacity indicator Read-only by user action. This is a built in protection feature of Windows Server 2012 R2 which takes your Storage Spaces offline by default after an upgrade. We just simply need to bring them online to use them. This is very similar to how in Windows Server 2003, a disk connected from an external system from a software RAID set could be marked as Foreign and the configuration of the disk needs to be imported first.

Changing the Storage Pool Status to Read/Write

To do this, open an administrative PowerShell prompt. At PowerShell, enter the two Cmdlets as follows:

Get-StoragePool | Where-Object {$_.IsReadOnly -eq $True} | Set-StoragePool -IsReadOnly $False
Get-VirtualDisk | Where-Object {$_.IsManualAttach -eq $True} | Set-VirtualDisk -IsManualAttach $False

If you forget to elevate the PowerShell prompt by running it as an administrator you will get access denied responses to the two Cmdlets as you aren’t running the Cmdlets with your administrative rights. Simply close PowerShell and re-open it by right-clicking and using the Run as Administrator option.

Bring the Storage Spaces Online

Once you’ve entered the Cmdlets above, returning to the Storage Spaces control panel applet now, you will see the information shown has updated.

Storage Space Offline by Policy

As you can see, the Storage Spaces are now reporting their status as OK but they are marked as Offline by Policy. To change this and to bring the Storage Spaces online, simply click the Bring Online option next to each Storage Space and it will be brought online and granted a drive letter.

Check, Verify and Reminder

It’s important to note here that the drive letter assigned will be the next free letter and not perhaps, the drive letter that you used on the previous installation of Windows Server 2012. If you have a requirement for the Storage Space to be on a particular letter then you will need to go into the Properties of the individual spaces after it has been brought online and change the letter.

It’s also good to remember that any file shares you had on these Storage Spaces may be un-shared through the upgrade process so you should check the existence of your shares either by using the Properties on the drive or folder which you needed to be shared or by using the Share and Storage Management administrative console.

Once you’ve got your Storage Spaces all brought online after the actions above, you should be looking like normality again as shown below.

Storage Space Online Normal

Hopefully someone out there finds this useful and it saves at least a few hair extractions from taking place after a Windows Server 2012 to Windows Server 2012 R2 in-place upgrade. Now it’s time to go and enjoy those new features.