I was going to write a long and rambling post about this, but I helpfully found someone who’s already done it for me: http://www.west-wind.com/weblog/posts/32765.aspx

Some salient highlights:

This is an application I’ve created and have full control over in terms of build, but I can’t figure out why it will not pin to the Windows 7 taskbar. All other applications pin just fine, but this particular one will not pin or be dragged onto the taskbar. Not from a running application, not from a dragged shortcut or by using the context menu to pin it to the taskbar. The Task menu that pops up has nothing more than a Close this Application on it instead of the usual pin options.

Windows has a few reserved names that include things like Documentation, Help, Setup, Readme etc. that are not pinned to the taskbar. These are exceptions in Windows […] But it turns out the rules in Windows aren’t exact matches, but it looks for anything that contains these names. So anything that contains the word Help in the EXE name is considered a special item.

These ‘restricted’ values are determined by a registry key at:


with these default values:

Documentation;Help;Install;More Info;Readme;Read me;Read First;Setup;Support;What’s New;Remove

One can only speculate why in the hell Microsoft decided a) To do this and b) Not to document it anywhere or c) Make it apparent in the UI that there’s a reason you can’t pin these files.

In addition to this, it’s fairly well known that you can’t pin things from Network locations either, though this can be worked around by doing the following:

  1. Create a new empty text file in a local folder
  2. Rename the file to the same as your desired network-located file
  3. Right-Click on the file and Pin it to the Start Menu/Task Bar
  4. Right-Click on the pinned item (If it’s on the Task Bar you’ll then need to right-click again on the item in the pop-up list) and choose properties
  5. Change the Target and Start In values to the network-located file, pick an icon if needed and click OK

Again, it’s unclear why Microsoft chose to arbitrarily restrict your ability to pin things in this manner, but I really hope they fix it at some point because it’s an awful lot of arsing around to do something that should be very straightforward.

The following script will allow you to add or remove registered user accounts to/from Sophos Safeguard Enterprise clients on a large scale (OU, domain or even org-wide). Needs to be run from a machine with Safeguard Server installed (or have the authentication method changed, of course). Obviously you can’t add Local accounts, but you can remove them – it hasn’t been tested with Workgroups.

Important bits are as follows; Vars to set are:

  • $NewUser – This needs to be the “display name” (As seen in the SG management console) of the account you want to Add to machines
  • $OldUser – This needs to be the “display name” (As above) of the account you want to Remove from machines
  • $SearchPath – This needs to be the ADSPath for the OU or Domain you want to operate in, make it blank to work on the Root
  • $Criteria – This is a bit more complex, it can be set to anything from 2.8.1 of the API docs – we’re using “POA” as it seems the most sensible – to filter which machines to make the changes on. If you’re using something that doesn’t return True for what you want then the script will require some further modifications to work properly.
  • There are two Commented sections further down the script that you can remove if you only want to Add or Remove accounts rather than do both at once – my intent is to swap one account for another, hence the script format – just snip out everything between the marked lines.

    Error handling errs on the side of caution, but I’m sure you could still screw up a lot of machines if you’re not careful, so the usual disclaimers apply (In other words: “This script is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. THERE IS NO WARRANTY FOR THE SCRIPT, TO THE EXTENT PERMITTED BY APPLICABLE LAW”).

    #Safeguard User Swap Tool
    #Adam Beardwood 30/11/2010
    #v1.0 - Initial Release
    #Declare useful vars
    $NewUser = "New User"
    $SearchPath = "dc=somedomain,dc=co,dc=uk"
    $OldUser = "Old User"
    $Criteria = "POA"
    #Load Utimaco API Assembly
    #Declare annoying [ref] vars
    [ref]$Machines = $null
    [ref]$Machine = $null
    [ref]$Type = $null
    [ref]$Val = $null
    [ref]$Prop = $null
    [ref]$Users = $null
    [ref]$User = $null
    [ref]$NUser = $null
    [ref]$NType = $null
    #Create scripting object, initialize it and Authenticate account (Requires Safeguard Server to be installed)
    $Scripting = new-object Utimaco.SafeGuard.AdministrationConsole.Scripting.Base
    catch{write-host "Error: This machine doesn't appear to have the Safeguard Server component installed, so it can't authenticate in this way. Quitting...";exit 1}
    #Create Directory, Inventory and UMA Instances & Initialize them
    $Directory = $Scripting.CreateDirectoryClassInstance()
    $Inventory = $Scripting.CreateInventoryClassInstance()
    $UMA = $Scripting.CreateUMAClassInstance()
    #Get ADSPath for $NewUser Account
    $Result = $Directory.GetOneObject($NewUser,$SearchPath,2,$NUser,$NType)
    #Verify we have located it, otherwise bail
    if($Result -ne 0){write-host "Error: Could not locate $NUser account. Quitting...";exit 1}
    #Initialize a directory search for computer accounts in the $SearchPath domain
    #For each result returned
    for ($i=0; $i -lt $($Machines.value); $i++){
    	#Get the object's ADS path and then check the POA status
    	$Result = $Inventory.GetComputerInventory($($Machine.Value),$Criteria,$Val,$Prop)
    	#If the reported ADS path doesn't actually exist, skip this machine
    	if($Result -ne 0){write-host "Error: Object isn't where it's supposed to be. Skipping...";continue}
    	#If POA is enabled
    	if($($Prop.Value) -eq $True){
    		#Initialize a UMA search for User accounts on the machine
    #----- This Section is for Removing Accounts
    		#For each result returned
    		for ($j=0; $j -lt $($Users.value); $j++){
    			#Get the user's ADS path
    			#If the given user path matches $OldUser
    			if($($User.value) -match $OldUser){
    				#Delete the account from the machine
    				write-host "Removed $OldUser Account from $($Machine.value)"
    #----- End Removing Accounts Section
    #----- This Section is for Adding Accounts
    		#Add $ModUser Account
    		write-host "Added $NewUser Account to $($Machine.value)"
    #----- End Adding Accounts Section
    		#Finalize the UMA search in preparation for the next one
    #Finalize ScriptingDirectory
    #Free all the resources

There are three things that almost everyone that I meet in IT seems incapable of understanding; Share Permissions vs NTFS Permissions, NTFS Full Control vs Modify permissions and Group Policy vs Local Permissions.

For those who don’t know, Windows folders presented over a network via CIFS share have two levels of permissions: Share Permissions, which are mostly a lingering reminder of the pre-NTFS days, when they were only way to control access to network resources and are pretty basic with only Read, Change & Full Control available to you. Then there are NTFS permissions, which are the normal Windows file system permissions, and have a dizzying array of permission settings available, but usually come down to List, Read, Modify & Full Control.

Best practice is to either leave the share permissions as the default (Everyone: Read) or, if some or all users need to modify files in the share, change them to Everyone: Change. That’s it. Everything else should be handled through NTFS permissions (or other local file system permissions where available) because they’re more granular, can be used to set different permissions on files and subfolders of a share (unlike share permissions which apply to the share as a whole) and, importantly, apply equally to users who log onto the machine locally as well as those connecting via the share. Yet somehow, people are obsessed with screwing around with Share permissions, adding random users or groups to them when they’ve already set Everyone: Change or leaving them as Everyone: Read and then complaining that users can’t write to the share, but can write to the same location locally on the server if they connect via RDP or console.

Seguing nicely into NTFS permissions we find the inability of people to understand the difference between Modify and Full Control. Ever deal with a 3rd party when troubleshooting a permissions issue with one of their apps and they will almost always tell you “The users need Full Control on that folder/file, not just Modify” but will almost never be able to tell you why, or what the difference is. I’ll tell you what the difference is; “Change Permissions” and “Delete subfolders and files”. They are the only two things that Full Control gives you over Modify, namely the ability to alter the permissions on the object and to delet[e] subfolders and files, even if the Delete permission has not been granted on the subfolder or file. In other words, for 99% of use cases, no difference whatsoever.

Finally, Group Policy vs Local Permissions, not NTFS permissions mind, but user account permissions. Specifically, this refers to the way that people are unable to grasp that having local Administrator rights on a machine does not magically allow you to do things that are restricted by Group Policy. If your user account or PC has a GPO applied to it that prevents access to the Control Panel, then adding your account to the local Administrators groups isn’t going to make the slightest bit of difference to your ability to access said Control Panel. What it will do, of course, is allow you to work around Group Policy settings in certain circumstances by modifying registry permissions so that the system can’t apply the GPOs on startup/login, but most people aren’t aware that it’s even possible, let alone how to go about it so my point remains valid.

If I could only make people understand these three things, I’d probably eliminate 20% of the support issues I have to deal with on a daily basis. Oh well, a man can dream…