PowerShell for Windows Admins


March 30, 2010  2:34 PM

Shares: Creating III

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

In a previous post

https://itknowledgeexchange.techtarget.com/powershell/shares-creating-ii/

we looked at creating a file share. This function can be expanded to test for the existence of the folder and if we succeed or not.

001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
017
018
019
020
021
022
023
024
025
026
027
028
029
030
031
032
033
034
function New-Share {
[CmdletBinding(SupportsShouldProcess=$True)]
param (
    [string]$path,
    [string]$name,
    [int][ValidateRange(0,2)]$type,
    [int]$maxcon,
    [string]$desc
)

$fail = DATA {
ConvertFrom-StringData -StringData @’
0 = Success
2 = Access Denied
8 = Unknown Failure
9 = Invalid Name
10 = Invalid Level
21 = Invalid Parameter
22 = Duplicate Share
23 = Redirected Path
24 = Unknown Device or Directory
25 = Net Name Not Found
‘@

}

    if (!(Test-Path -Path $path)){Throw “Folder does not exist”}
    $s = [WmiClass]“Win32_Share” 
    $ret = $s.Create($path, $name, $type, $maxcon, $desc)
    if ($ret.ReturnValue -ne 0){
        Write-Host “Share $name was not created”
        Write-Host “Failure reason: $($fail[“$($ret.ReturnValue)”])”
    }
    else {Write-Host “Share $name was created”}
}

 

 

We add a hash table of the return codes from the create method. A simple Test-Path enables us to determine if the share exists.

We can test the return code and if the value is zero state the creation succeeded otherwise we report failure and the reason.

PS> New-Share -path c:\share1 -name Test1 -type 0 -maxcon $null -desc “Test share 1 from module”
Share Test1 was not created
Failure reason: Duplicate Share

Technorati Tags: ,

March 24, 2010  1:20 PM

Scripting Games 2010

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

Don’t expect to be anywhere but in front of your computer between 26 April and 7 May.  Why? because the 2010 Scripting Games are happening.

The usual 10 events with beginners and advanced versions.

A whole bunch of expert commentators – including me.

For more information and a few hints on things that could be useful see http://blogs.technet.com/heyscriptingguy/archive/2010/03/21/hey-scripting-guy-march-21-2010.aspx


March 24, 2010  1:19 PM

Book Review: Windows PowerShell 2.0 best practices

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

I’ve published a review of the book here

http://msmvps.com/blogs/richardsiddaway/archive/2010/03/23/book-review-windows-powershell-2-0-best-practices.aspx

There are some WMI techniques that may be of interest to readers of this blog

Technorati Tags: ,


March 21, 2010  7:22 AM

Shares: Creating II

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

Now we have seen how to create a share lets extend the script a bit.  This is how a lot of my scripts get developed.  I need to solve a particular problem so I write a script to do that task.  While I’m writing I try to see how I can make the script generic. Sometimes the script is written immediately to solve the generic problem and other times I have to solve the immediate problem and go back to the generic bit later.

001
002
003
004
005
006
007
008
009
010
011
012
function New-Share {
[CmdletBinding(SupportsShouldProcess=$True)]
param (
    [string]$path,
    [string]$name,
    [int][ValidateRange(0,2)]$type,
    [int]$maxcon,
    [string]$desc
)
    $s = [WmiClass]"Win32_Share" 
        $s.Create($path, $name, $type, $maxcon, $desc)
}

We take our earlier script and create a function. This forms part of my module for working with the file system.

I’m creating it as an advanced function so I can use the –whatif parameters later.  The function takes a set of parameters and creates the share.

Its used like this

New-Share -path c:\share1 -name Test1 -type 0 -maxcon $null -desc "Test share 1 from module"

Next stage is to add the code to test the existence of the folder and to check that the share creates properly

Technorati Tags: ,


March 12, 2010  4:06 PM

Shares: Creating I

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

we’ve seen a few things we can do with shares – its time to look at creating them. A simple share craetion script will look like this

001
002
003
004
005
006
New-Item -Path c:\ -Name share1 -ItemType Directory
New-Item -Path c:\share1 -Name shareA -ItemType Directory
New-Item -Path c:\share1 -Name shareB -ItemType Directory

$s = [WmiClass]"Win32_Share"
$s.Create("c:\share1", "Test1", 0, $null, "Test share1")

We create some folders in a hierarchy with New-Item and then create an instance of the Win32_Share class using the [WmiClass] type accelerator.

We can then call the create method. The parameters are:

  • folder path
  • share name
  • share type – 0 = disk share
  • maximum connections allowed – $null means unlimited
  • description

This sets default permissions on the share

Technorati Tags: ,


March 7, 2010  5:23 AM

Shares: Understanding the Access Mask

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

We saw earlier that the access mask was returned as a number.  We need to understand what that number means.

NOTE – BEFORE RUNNING THE SCRIPT ENSURE LINE 16 AND 17 ARE COMBINED.  THEY ARE SPLIT HERE TO FIT THE LISTING INTO THE DISPLAY WIDTH.  THE LINE SHOULD BE CONTINUOUS AND READ

1048576 =  Synchronizes access, allows a process to wait for an object to enter the signaled state.

001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
017
018
019
020
021
022
023
024
025
026
027
028
029
030
031
032
$acmsk = DATA {
ConvertFrom-StringData -StringData @’
1 = Read/List
2 = Write/Create File
4 = Append/Create Subdirectory
8 = Read extended attributes.
16 = Write extended attributes.
32 = Execute file/Traverse directory
64 = Delete directory
128 = Read file attributes.
256 = Change file attributes.
65536 = Delete
131072 = Read access to the security descriptor and owner.
262144 = Write access to the discretionary access control list (DACL).
524288 = Assigns the write owner.
1048576 = Synchronizes access, allows a process to wait
for an object to enter the signaled state.
‘@

}

$flags = @(1,2,4,8,16,32,64,128,256,65536,131072,262144,524288,1048576)

$share = Get-WmiObject -Class Win32_Share -Filter “Name=’Test'”
$mask = Invoke-WmiMethod -InputObject $share -Name GetAccessMask

foreach ($flag in $flags){

    if ($mask.ReturnValue -band $flag) {
        Write-Host $acmsk[“$($flag)”]
    }

}

 

The Access Mask is a bit mask that is used to determine which permissions have been granted. The various flags are defined in hash table, In this example I decided to used Get-WmiObject to retrieve the share and then use Invoke-WmiMethod to run the getAccessMask method. In PowerShell v1 we could have run

$mask = $share.GetAccessMask()

Once we have the mask we do a bitwise AND against the mask to determine if each permission has been granted.

Technorati Tags: ,,


March 6, 2010  6:06 AM

Share Type

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

One other point we need to cover is the type of share. We have a number of choices as shown in the script. The Type property has to be converted from a number to an understandable value – unless you want to learn the share types off by heart.

001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
$shtyp = DATA {
ConvertFrom-StringData -StringData @’
0 = Disk Drive
1= Print Queue
2 = Device
3 = IPC
2147483648 = Disk Drive Admin
2147483649 = Print Queue Admin
2147483650 = Device Admin
2147483651= IPC Admin
‘@

}

Get-WmiObject -Class Win32_Share | 
select Name, Path, Description,
@{Name=“ShareType”; Expression = {$shtyp[“$($_.Type)”]}}

A calculated field can be used to derive the share type as shown.

Technorati Tags: ,,


March 6, 2010  4:37 AM

Sharing

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

One area of our Windows machines that we definitely need to think about is the shares we create on a machine. These control access to resources – especially file resources.

We can find the shares on a machine using the Win32_Share class. The name of the share and its path together with a description form the default display.

Remember we can use the –computername parameter to access remote machines. I tend not to use it in these posts to keep the script lengths down.

PS> Get-WmiObject -Class Win32_Share | Format-Table -AutoSize

Name            Path                              Description
—-            —-                              ———–
ADMIN$          C:\Windows                        Remote Admin
C$              C:\                               Default share
D$              D:\                               Default share
HP DeskJet 812C HP DeskJet 812C,LocalsplOnly      HP DeskJet 812C
IPC$                                              Remote IPC
print$          C:\Windows\system32\spool\drivers Printer Drivers
Test            C:\Test
Users           C:\Users

Next move is to find what we can do with them.

PS> Get-WmiObject -Class Win32_Share | Get-Member -MemberType method | select name

Name
—-
Delete
GetAccessMask
SetShareInfo

shows three methods.  Delete and SetShareInfo we can perform by using the cmdlets Remove-WmiObject and Set-WmiInstance respectively.

What does GetAccessMask do for us?

$share = Get-WmiObject -Class Win32_Share -Filter “Name=’Test'”

PS> $share.GetAccessMask()

__GENUS          : 2
__CLASS          : __PARAMETERS
__SUPERCLASS     :
__DYNASTY        : __PARAMETERS
__RELPATH        :
__PROPERTY_COUNT : 1
__DERIVATION     : {}
__SERVER         :
__NAMESPACE      :
__PATH           :
ReturnValue      : 2032127

Next we need to unravel this return value

Technorati Tags: ,,


March 5, 2010  3:23 PM

50% discount extended

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

Manning www.manning.com have extended their 50% discount across the weekend as follows:

(Today) Friday March 5, 2010: 50% off all MEAPs. Use code dotd0305tw

Saturday March 6, 2010: 50% off all print books. Use code dotd0306tw

Sunday March 7, 2010: 50% off all ebooks. Use code dotd0307tw

Looks like its a good time to buy a book


March 4, 2010  2:35 PM

What’s the time

Richard Siddaway Richard Siddaway Profile: Richard Siddaway

I was answering a question about time synchronisation and it got me wondering about check the time on multiple machines.

001
002
003
004
005
006
007
008
009
010
011
012
$computer = “.” 
Get-WmiObject -Class Win32_LocalTime -ComputerName $computer | foreach {
    “Local Time”
    Get-Date -Day $_.Day -Month $_.Month -Year $_.Year `
      -Hour $_.Hour -Minute $_.Minute -Second $_.Second
}

Get-WmiObject -Class Win32_UTCTime -ComputerName $computer | foreach {
    “UTC Time”
    Get-Date -Day $_.Day -Month $_.Month -Year $_.Year `
      -Hour $_.Hour -Minute $_.Minute -Second $_.Second
}

We can use a simple bit of WMI to check both the Local time and UTC time if we span multiple time zones.  if you need to check many machines put the code in a function and pass the computer names from a  csv file

Technorati Tags:


Forgot Password

No problem! Submit your e-mail address below. We'll send you an e-mail containing your password.

Your password has been sent to: