<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-20327311</id><updated>2012-01-11T08:22:47.172-05:00</updated><title type='text'>PowerShell For Fun</title><subtitle type='html'>Some Windows PowerShell scripts and utilities I wrote just for fun. If you were interested in scripting with PowerShell (a biologist would be better), you might have some fun here.</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>61</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-20327311.post-673581471031617043</id><published>2007-11-30T14:22:00.000-05:00</published><updated>2007-11-30T16:32:52.919-05:00</updated><title type='text'>PowerShell Script: Amazon WII Watch</title><content type='html'>I just wanted a WII for Christmas gift and didn't want to spend $500 on ebay.&lt;br /&gt;&lt;br /&gt;A Small powershell script will do!&lt;br /&gt;&lt;br /&gt; &lt;br /&gt;# Begin of script&lt;br /&gt;# =============================================================&lt;br /&gt;# This code is for test purposes only. Use it at your own risk.&lt;br /&gt;# =============================================================&lt;br /&gt;param([string] $query= "B0009VXBAQ", [string] $button = "btn-atc._V46858960_.gif")&lt;br /&gt;&lt;br /&gt;#Submit query sequence&lt;br /&gt;"================================================================="&lt;br /&gt;"ASIN: " + $query&lt;br /&gt;"Button: " + $button&lt;br /&gt;""&lt;br /&gt;"Submit query ..."&lt;br /&gt;$uri="http://www.amazon.com/gp/product/" + $query&lt;br /&gt;$AmazonClient = new-object System.Net.WebClient&lt;br /&gt;&lt;br /&gt;#checking for results&lt;br /&gt;While ($true)&lt;br /&gt;{&lt;br /&gt;$pagecontent = $AmazonClient.DownloadString($uri);&lt;br /&gt;"================================================================="&lt;br /&gt;# Get Availability&lt;br /&gt;if ($pagecontent -match $button)&lt;br /&gt;{&lt;br /&gt;    write-host "In Stock`a`a`a" -foregroundcolor Red&lt;br /&gt; }&lt;br /&gt;else&lt;br /&gt;{&lt;br /&gt;    write-host "out of Stock" -foregroundcolor yellow&lt;br /&gt;}&lt;br /&gt;[datetime]::Now.tostring()&lt;br /&gt;"Wait..."&lt;br /&gt;Start-sleep 60&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;#End of script&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;=================================================================&lt;br /&gt;out of Stock&lt;br /&gt;2007-11-30 13:07:52&lt;br /&gt;Wait...&lt;br /&gt;=================================================================&lt;br /&gt;In Stock&lt;br /&gt;&lt;br /&gt;2007-11-30 13:08:58&lt;br /&gt;Wait...&lt;br /&gt;=================================================================&lt;br /&gt;out of Stock&lt;br /&gt;2007-11-30 13:10:01&lt;br /&gt;Wait...&lt;br /&gt;=================================================================&lt;br /&gt;In Stock&lt;br /&gt;&lt;br /&gt;2007-11-30 13:11:05&lt;br /&gt;Wait...&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-673581471031617043?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/673581471031617043/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2007/11/powershell-script-amazon-wii-watch.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/673581471031617043'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/673581471031617043'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2007/11/powershell-script-amazon-wii-watch.html' title='PowerShell Script: Amazon WII Watch'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-5628975857178904212</id><published>2007-02-28T14:07:00.000-05:00</published><updated>2007-02-28T14:14:09.424-05:00</updated><title type='text'>New Project Home at CodePlex.com</title><content type='html'>Private workspaces @ gotdotnet.com will be phased out on 3/20/2007. I moved new project home to CodePlex.com @ &lt;a href="http://www.codeplex.com/powershellremoting"&gt;http://www.codeplex.com/powershellremoting&lt;/a&gt;. You can get news, report bugs and request feature there.&lt;br /&gt;&lt;br /&gt;We are working on a beta release on X64 and VISTA. We will come up a road map for future PowerShell Remoting development soon. If you have any suggestions, please reply here or discussion section @ &lt;a href="http://www.codeplex.com/powershellremoting"&gt;new Powershell Remoting project home&lt;/a&gt;.     &lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-5628975857178904212?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/5628975857178904212/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2007/02/new-project-home-at-codeplexcom.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/5628975857178904212'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/5628975857178904212'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2007/02/new-project-home-at-codeplexcom.html' title='New Project Home at CodePlex.com'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-280122012654205011</id><published>2007-01-25T14:47:00.000-05:00</published><updated>2007-01-25T14:54:16.756-05:00</updated><title type='text'>PowerShell Remoting Go OpenSource!</title><content type='html'>&lt;p&gt;You can now download full source code of PowerShell Remoting from my &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;workspace&lt;/a&gt;. &lt;br /&gt;&lt;/p&gt;&lt;br /&gt;Let's welcome our new developers: &lt;span style="font-weight:bold;"&gt;Romangeeko&lt;/span&gt; and &lt;span style="font-weight:bold;"&gt;JaviRuso&lt;/span&gt;. We are still looking for developers. If you are intersted, please Email me (shenzhonghao AT gmail DOT com).&lt;br /&gt; &lt;br /&gt;Enjoy.&lt;br /&gt;&lt;br /&gt;&lt;p&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt;    &lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;   &lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-280122012654205011?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/280122012654205011/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2007/01/powershell-remoting-go-opensource.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/280122012654205011'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/280122012654205011'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2007/01/powershell-remoting-go-opensource.html' title='PowerShell Remoting Go OpenSource!'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-116595261034903834</id><published>2006-12-12T14:31:00.000-05:00</published><updated>2006-12-12T14:43:30.416-05:00</updated><title type='text'>Looking For Developers</title><content type='html'>I am very busy with my daytime job and my new born daughter. So I don't have enough time for PowerShell Remoting Project. But I would like to continue the development of this project in a community (probably open source). &lt;br /&gt;&lt;br /&gt;I have been contact some friends also intersted in PowerShell Remoting.There are also a couple of user requesting for source code of PowerShell Remoting. If you are interested in this project and would like to contribute your time to it, please Email me (shenzhonghao AT gmail DOT com). It would be great if you could include some details about your previous development experience. Any other suggestion about this project is also welcome.   &lt;br /&gt;&lt;br /&gt;  &lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-116595261034903834?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/116595261034903834/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/12/looking-for-developers.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/116595261034903834'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/116595261034903834'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/12/looking-for-developers.html' title='Looking For Developers'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-116361952387760014</id><published>2006-11-15T14:35:00.000-05:00</published><updated>2006-11-22T14:27:54.700-05:00</updated><title type='text'>PowerShell Remoting version 0.2.9.0 For V1.0</title><content type='html'>PowerShell Remoting version 0.2.9.0  &lt;br /&gt;1. Rebuild For PowerShell V1.0 RTW. &lt;br /&gt;2. Fix "All User" profile not load at server problem. &lt;br /&gt;&lt;br /&gt;&lt;br&gt;&lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;Download here&lt;/a&gt; (381k)&lt;br /&gt;&lt;br&gt; Some user reported that PowerShellRemoting.ClientPSHost.dll is not registered properly in x64 platform. So I also uploaded a x64 build of PowerShell Remoting.&lt;font color="red"&gt; Warning: This package have not been tested on x64 platform, use it at your own risk. &lt;br /&gt;&lt;br&gt;&lt;br&gt;Please uninstall old version of Powershell Remoting before uninstall PowerShell RC2. After install PowerShell v1.0, you can install new version of Powershell Remoting.&lt;/font&gt;&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-116361952387760014?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/116361952387760014/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/11/powershell-remoting-version-0290-for.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/116361952387760014'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/116361952387760014'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/11/powershell-remoting-version-0290-for.html' title='PowerShell Remoting version 0.2.9.0 For V1.0'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-115937567639428150</id><published>2006-09-27T12:42:00.000-04:00</published><updated>2006-09-29T11:30:52.010-04:00</updated><title type='text'>PowerShell Remoting version 0.2.8.0 For RC2 Drop</title><content type='html'>Windows PowerShell Team finally released PowerShell RC2. If you are running windows server 2003, you can enjoy new active directory provider. If you are a windows XP (non-English) user like me, I suggest you download &lt;a href="http://www.microsoft.com/downloads/details.aspx?FamilyID=cf02f527-9527-49cc-bdc5-23c3c22493e0&amp;amp;DisplayLang=en"&gt;Windows PowerShell 1.0 RC2 Language-Neutral Package for Windows XP (KB925228) &lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Some important changes not in release note.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Big window, different color&lt;/b&gt;&lt;br /&gt;&lt;blockquote&gt;&amp;gt; $host.ui.rawui&lt;br /&gt;&lt;br /&gt;ForegroundColor&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : DarkYellow&lt;br /&gt;BackgroundColor&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : DarkMagenta&lt;br /&gt;CursorPosition&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 0,4&lt;br /&gt;WindowPosition&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 0,0&lt;br /&gt;CursorSize&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 25&lt;br /&gt;BufferSize&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 120,3000&lt;br /&gt;WindowSize&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 120,44&lt;br /&gt;MaxWindowSize&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 120,44&lt;br /&gt;MaxPhysicalWindowSize : 128,44&lt;br /&gt;KeyAvailable&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;WindowTitle&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : Windows PowerShell&lt;br /&gt;&lt;/blockquote&gt;If you like color setting of old version&lt;br /&gt;&lt;blockquote&gt;&amp;gt;$host.ui.rawui. ForegroundColor = "gray"&lt;br /&gt;&amp;gt;$host.ui.rawui. BackgroundColor = "black"&lt;br /&gt;&amp;gt;clear&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;Path change&lt;/b&gt;&lt;br /&gt;1. Home&lt;br /&gt;C:\WINDOWS\system32\windowspowershell&lt;br /&gt;&lt;br /&gt;2. User Profile folder&lt;br /&gt;&amp;lt;My Documents&amp;gt;\WindowsPowerShell&lt;br /&gt;&lt;br /&gt;3. Assembly change&lt;br /&gt;System.Management.Automation now goes to GAC&lt;br /&gt;&lt;br /&gt;PowerShell Remoting version 0.2.8.0  &lt;br /&gt;1. Rebuild for PowerShell RC2 version&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;Download from here.&lt;/a&gt; (381k)&lt;br /&gt;&lt;br /&gt;&lt;font color="red"&gt;Please uninstall old version of Powershell Remoting before uninstall PowerShell RC1. After install PowerShell RC2, you can install new version of Powershell Remoting.&lt;/font&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-115937567639428150?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/115937567639428150/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/09/powershell-remoting-version-0280-for.html#comment-form' title='7 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115937567639428150'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115937567639428150'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/09/powershell-remoting-version-0280-for.html' title='PowerShell Remoting version 0.2.8.0 For RC2 Drop'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>7</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-115492091258094974</id><published>2006-08-06T23:19:00.000-04:00</published><updated>2006-08-06T23:21:52.600-04:00</updated><title type='text'>Do You Know There is a $Host Variable</title><content type='html'>PowerShell has a build-in &lt;b&gt;$host&lt;/b&gt; variable which expose a System. Management. Automation. Internal. Host. InternalHost object. It is an internal object so you can't access it from assembly but monad team made it directly accessible from PowerShell script. $host is interesting and powerful. Just an example how powerful it is: my &lt;a href="http://www.gotdotnet.com/Workspaces/Workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;PowerShell Remoting&lt;/a&gt; "steal" the $host.UI for user interface remoting.&lt;br /&gt;&lt;br /&gt;$Host is an implementation of System. Management. Automation. Host. PSHost abstract class. PSHost defined some important properties and methods which will be used for all cmdlet. For more detailed information about &lt;b&gt;PSHost&lt;/b&gt;, you can consult &lt;a href="http://windowssdk.msdn.microsoft.com/en-us/library/system.management.automation.host.aspx"&gt;Monad SDK online&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Let's see what we can do with $host&lt;br /&gt;&lt;b&gt;1. Some read-only properties provide information about current host. &lt;/b&gt;&lt;br /&gt;These could be useful when you have to distinguish among multiple hosts (For example, my PowerShell Remoting has a remote host. Remote host have different Name, InstanceId, Version, etc).&lt;br /&gt;&lt;ul&gt;&lt;li&gt;CurrentCulture&lt;/li&gt;&lt;li&gt;CurrentUICulture&lt;/li&gt;&lt;li&gt;InstanceId&lt;/li&gt;&lt;li&gt;Name&lt;/li&gt;&lt;li&gt;PrivateData&lt;/li&gt;&lt;li&gt;Version&lt;/li&gt;&lt;/ul&gt;&lt;b&gt;&lt;br /&gt;2. Two methods to support legacy application (like ping.exe). &lt;/b&gt;&lt;br /&gt;Usually you do not need to call them directly. Monad engine will call them automatically if you invoke legacy application.&lt;br /&gt;&lt;ul&gt;&lt;li&gt;NotifyBeginApplication()&lt;/li&gt;&lt;li&gt;NotifyEndApplication()&lt;/li&gt;&lt;/ul&gt;&lt;b&gt;&lt;br /&gt;3. Two methods about nested prompt. &lt;/b&gt;&lt;br /&gt;I already discussed &lt;a href="http://mshforfun.blogspot.com/2006/06/enter-nested-prompt-function.html"&gt;how to use those methods previously&lt;/a&gt;. &lt;br /&gt;&lt;ul&gt;&lt;li&gt;EnterNestedPrompt()&lt;/li&gt;&lt;li&gt;ExitNestedPrompt() &lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;b&gt;4. One method to force PowerShell exit. &lt;/b&gt;&lt;br /&gt;This could be useful if some sever error occurs and you want to quit PowerShell.exe from your script. You can also pass error code to environment. For example:&lt;br /&gt;&lt;blockquote&gt;&amp;gt;$host.SetShouldExit(10000)&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;5. $host.UI&lt;/b&gt;&lt;br /&gt;This is an implementation of PSHostUserInterface object which expose some import user interface API.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;5.1 &lt;font color="#000099"&gt;public override&lt;/font&gt; Dictionary&amp;lt;string, PSObject&amp;gt; Prompt(string caption, string message, Collection&amp;lt;FieldDescription&amp;gt; descriptions)&lt;/b&gt;&lt;br /&gt;This API is called when cmdlet required field(s) is null or empty. It is capable of get user input ([string]) and cnvert them to almost any .Net type in current appdomain. But the task of constructing Collection&amp;lt;FieldDescription&amp;gt; from script can be daunting. &lt;br /&gt;&lt;br /&gt;&lt;b&gt;5.2 &lt;font color="#000099"&gt;public &lt;/font&gt;&lt;font color="#000099"&gt;override &lt;/font&gt;int PromptForChoice(string caption, string message, Collection&amp;lt;ChoiceDescription&amp;gt; choices, int defaultChoice)&lt;/b&gt;&lt;br /&gt;This is standard PowerShell text-base menu system. Don't re-invent wheels! If you want to provide a menu for user input, look nowhere and this method got you all covered. &lt;a href="http://mow001.blogspot.com/2005/12/msh-prompt-user-function-with-help.html"&gt;Mow has a nice example of how to use this methods&lt;/a&gt;.&lt;br /&gt;&lt;b&gt;&lt;br /&gt;5.3 Some more input API to get user input&lt;/b&gt;&lt;br /&gt;&lt;ul&gt;&lt;li&gt;ReadLine: Read a line from standard input, similar to read-host cmdlet&lt;/li&gt;&lt;li&gt;PromptForCredential: Get PSCredential object from User input, similar to get-credential cmdlet.&lt;/li&gt;&lt;li&gt;ReadLineAsSecureString: read from standard input and convert to SecureString, similar to Read-host -AsSecureString&lt;/li&gt;&lt;/ul&gt;&lt;b&gt;&lt;br /&gt;5.4 Some output API to direct output to different channel and with color support.&lt;/b&gt;&lt;br /&gt;&lt;ul&gt;&lt;li&gt;Write: Write to standard output without /n/r&lt;/li&gt;&lt;li&gt;WriteLine: Write a line to standard output&lt;/li&gt;&lt;li&gt;WriteProgress: Wrtie to Progress panel, similar to Write-progress cmdlet &lt;/li&gt;&lt;li&gt;WriteDebugLine: Write to Debug channel, similar to Write-debug cmdlet&lt;/li&gt;&lt;li&gt;WriteErrorLine: Write to Standard Error, similar to Write-error cmdlet&lt;/li&gt;&lt;li&gt;WriteVerboseLine: Write to Verbose channel, similar to Write-verbose cmdlet&lt;/li&gt;&lt;li&gt;WriteWarningLine: Wrtie to Warning channel, similar to Write-warning cmdlet&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;b&gt;5.5 $Host.UI.RawUI&lt;/b&gt;&lt;br /&gt;This is an implementation of PSHostRawUserInterface abstract class. This is a new concept in PowerShell. &lt;a href="http://mshforfun.blogspot.com/2006/05/perfect-prompt-for-windows-powershell.html"&gt;In the prompt post, we use this object to do a lot of tricks&lt;/a&gt;. &lt;br /&gt;&lt;br /&gt;&lt;b&gt;5.5.1 Some properties to control Console window size, window title, cursor, buffer size, background/foreground color &lt;/b&gt;&lt;br /&gt;&lt;ul&gt;&lt;li&gt;BackgroundColor&lt;/li&gt;&lt;li&gt;BufferSize&lt;/li&gt;&lt;li&gt;CursorPosition&lt;/li&gt;&lt;li&gt;CursorSize&lt;/li&gt;&lt;li&gt;ForegroundColor&lt;/li&gt;&lt;li&gt;KeyAvailable&lt;/li&gt;&lt;li&gt;MaxPhysicalWindowSize&lt;/li&gt;&lt;li&gt;MaxWindowSize&lt;/li&gt;&lt;li&gt;WindowPosition&lt;/li&gt;&lt;li&gt;WindowSize&lt;/li&gt;&lt;li&gt;WindowTitle&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;b&gt;5.5.2 Some console buffer API. Lee has a great &lt;a href="http://www.leeholmes.com/blog/burnconsolemshPartIIAWorkingImplementation.aspx"&gt;burn-console &lt;/a&gt;script to demonstrate these methods.&lt;/b&gt;&lt;br /&gt;&lt;ul&gt;&lt;li&gt;FlushInputBuffer&lt;/li&gt;&lt;li&gt;GetBufferContents&lt;/li&gt;&lt;li&gt;LengthInBufferCells&lt;/li&gt;&lt;li&gt;NewBufferCellArray&lt;/li&gt;&lt;li&gt;ScrollBufferContents&lt;/li&gt;&lt;li&gt;SetBufferContents&lt;/li&gt;&lt;/ul&gt;&lt;b&gt;&lt;br /&gt;5.5.3&amp;nbsp;&amp;nbsp; &lt;font color="#000099"&gt;public override&lt;/font&gt; KeyInfo ReadKey(ReadKeyOptions options)&lt;/b&gt;&lt;br /&gt;It is a powerful API to read keyboard input. Check out the retuned KeyInfo object, with this method, one can theoretically write a script act like a simple screen editor. &lt;br /&gt;Here is the ReadKeyOption enum:&lt;br /&gt;&lt;blockquote&gt;[Flags]&lt;br /&gt;&lt;font color="#000099"&gt;public&lt;/font&gt; enum ReadKeyOptions&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; AllowCtrlC = 1,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; IncludeKeyDown = 4,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; IncludeKeyUp = 8,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoEcho = 2&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;For example&lt;br /&gt;&lt;blockquote&gt;&amp;gt; $host.ui.RawUI.ReadKey(12)&lt;br /&gt;a&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; VirtualKeyCode&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Character&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ControlKeyState&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; KeyDown&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; --------------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ---------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ---------------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; -------&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 65&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; a&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 262176&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; True&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;Just to remind you, my &lt;a href="http://www.gotdotnet.com/Workspaces/Workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;PowerShell Remoting&lt;/a&gt; remote host implemented all Host, UI and RawUI. So feel free to explore those interesting API on you remote host.&lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-115492091258094974?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/115492091258094974/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/08/do-you-know-there-is-host-variable.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115492091258094974'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115492091258094974'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/08/do-you-know-there-is-host-variable.html' title='Do You Know There is a $Host Variable'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-115327887308071933</id><published>2006-07-18T23:11:00.000-04:00</published><updated>2006-07-21T15:03:10.723-04:00</updated><title type='text'>Runspace Remoting</title><content type='html'>&lt;a href="http://www.hanselman.com/"&gt;Scott Hanselman&lt;/a&gt; is one of the early users and supporters of my PowerShell Remoting. He did an interesting post about &lt;a href="http://www.hanselman.com/blog/ScriptBlockAndRunspaceRemotingInPowerShell.aspx"&gt;Runspace Remoting&lt;/a&gt;. Briefly, he used export-clixml to serialize objects at server and used import-clixml to reconstruct PSObject at client. &lt;a href="http://mshforfun.blogspot.com/2006/03/securely-extend-monad-pipline-over.html"&gt;I have tried similar mechanism and failed&lt;/a&gt;. Actually &lt;a href="http://www.blogger.com/comment.g?blogID=20327311&amp;amp;postID=114383256894350753"&gt;Karl Prosser and I have been talking about using export-clixml/import-clixml&lt;/a&gt; a while ago . Great job, Scott!&lt;br /&gt;&lt;br /&gt;Despite of my failure on serialization/de-serialization of PSObject, there is other reasons made me choose &lt;b&gt;user interface remoting&lt;/b&gt;:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;&lt;a href="http://mshforfun.blogspot.com/2006/03/securely-extend-msh-host-user.html"&gt;Monad was designed to capable of user interface remoting&lt;/a&gt;. Monad engine will manage to display and format (out-default) remote objects. Monad engine can even truncate objects collection for you if there are too many objects in the pipline. &lt;/li&gt;&lt;li&gt;Not all tasks require local objects exactly matching remote objects. For most remote scripting tasks, user interface remoting is good enough. User interface remoting deliver similar user experience as local shell. SSHD already proved itself successful story by similar mechanism.&amp;nbsp; &lt;/li&gt;&lt;li&gt;User can manipulate "Real" remote objects via user interface remoting (No "&lt;i&gt;&lt;b&gt;Heisenberg Uncertainly Principle of PowerShell&lt;/b&gt;&lt;/i&gt;").&lt;br /&gt;&lt;/li&gt;&lt;li&gt;Serialization/de-serialization method has its own limitations.&lt;br /&gt;&lt;ul&gt;&lt;li&gt;It can use a lot of resources and band-width. Consider the situation when multiple runspace ouput huge collection of objects at the same time, even with proper threading management server could still be overloaded. &lt;br /&gt;&lt;/li&gt;&lt;li&gt;What if you just need one simple property of an object with hundreds or thounds of properties, you would have to serialize all public properties of that object and transfer it to client.&lt;br /&gt;&lt;/li&gt;&lt;li&gt;It can loose some property associate with original objects.&lt;/li&gt;&lt;/ul&gt;&lt;/li&gt;&lt;li&gt;"Clustering" multiple servers is possible with user interface remoting. I am trying to "fork" single client input to multiple servers by simply add current client component to server component. (There are still some problems with this model)&lt;/li&gt;&lt;/ol&gt;&lt;br /&gt;PS: To Monad Team, a public helper API to serialize PSObject to string will be really helpful.&lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-115327887308071933?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/115327887308071933/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/07/runspace-remoting.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115327887308071933'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115327887308071933'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/07/runspace-remoting.html' title='Runspace Remoting'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-115284981527507634</id><published>2006-07-13T23:51:00.000-04:00</published><updated>2006-07-14T00:03:35.286-04:00</updated><title type='text'>How to: Using PowerShell through SSH</title><content type='html'>It is possible to use PowerShell through SSH. Read &lt;a href="http://hivearchive.com/2006/07/03/using-powershell-through-ssh/"&gt;the story from The Hive Archive&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;But there are certain limitations:&lt;br /&gt;1. You have to install cygwin, sshd and ssh client like putty (Well I can certainly live with that. Actually they are always on my hard drive). &lt;br /&gt;2. No prompt&lt;br /&gt;3. some Raw UI might not work&lt;br /&gt;&lt;br /&gt;I am really looking forward to the new version of PowerShell with buildin Remoting function. According to Jeffrey Snover : &lt;em&gt;Our plans for remoting are to leverage WS-MGMT the remoting protocol recently standardized through the DMTF&lt;/em&gt;. &lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-115284981527507634?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/115284981527507634/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/07/how-to-using-powershell-through-ssh.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115284981527507634'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115284981527507634'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/07/how-to-using-powershell-through-ssh.html' title='How to: Using PowerShell through SSH'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-115276202311148291</id><published>2006-07-12T23:37:00.000-04:00</published><updated>2006-07-14T21:54:19.243-04:00</updated><title type='text'>Why There Is an Out-Default Cmdlet</title><content type='html'>PowerShell have a couple of output control cmdlets:&lt;br /&gt;&lt;blockquote&gt;&amp;gt; gcm out-*&lt;br /&gt;&lt;br /&gt;CommandType&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Definition&lt;br /&gt;-----------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ----------&lt;br /&gt;Cmdlet&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-Default&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-Default [-InputObject &amp;lt;P...&lt;br /&gt;Cmdlet&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-File&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-File [-FilePath] &amp;lt;String...&lt;br /&gt;Cmdlet&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-Host&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-Host [-Paging] [-InputOb...&lt;br /&gt;Cmdlet&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-Null&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-Null [-InputObject &amp;lt;PSOb...&lt;br /&gt;Cmdlet&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-Printer&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-Printer [[-Name] &amp;lt;String...&lt;br /&gt;Cmdlet&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-String&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-String [-Stream] [-Width...&lt;br /&gt;&lt;/blockquote&gt;Out-Default cmdlet is one of the most mysterious one.&lt;br /&gt;&lt;blockquote&gt;&amp;gt; help out-default&lt;br /&gt;&lt;br /&gt;NAME&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Out-Default&lt;br /&gt;&lt;br /&gt;SYNOPSIS&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; The default controller of output.&lt;br /&gt;&lt;br /&gt;DETAILED DESCRIPTION&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; The standard treatment at the end of a pipeline is to send all objects to o&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; ut-default.&amp;nbsp; Out-default then sends them all to format-default. It takes th&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; e objects that return and sends them to the default destination.&amp;nbsp; For this&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; reason, it is functionally equivalent to out-host but is not called from th&lt;br /&gt;e console.&lt;br /&gt;&lt;/blockquote&gt;The help message does not help at all. Luckily enough, &lt;a href="http://blogs.msdn.com/powershell/archive/2006/04/30/586973.aspx"&gt;Jeffrey Snover has a blog entry&lt;/a&gt; talking about this cmdlet.&amp;nbsp; In summary, It will "figure out how to format and output the object stream" and send them to host via Out-host cmdlet.&lt;br /&gt;&lt;br /&gt;Here is my two cents:&lt;br /&gt;1. Out-Default cmdlet is &lt;b&gt;NOT&lt;/b&gt; for interactive console User. &lt;br /&gt;Every interactive command from console will have Out-Default appended automatically by Monad engine. Add Out-Default in the middle of pipline could even cause unexpected output.&lt;br /&gt;&lt;blockquote&gt;&amp;gt; gps | format-table&lt;br /&gt;&amp;gt; gps | out-default | format-table&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; # format-table will not work.&lt;br /&gt;&lt;/blockquote&gt;2. Out-Default cmdlet is for Monad hosting application.&lt;br /&gt;To have a full-blown Monad hosting application, you have to create your own "Host" (System.Management.Automation.Host.PSHost) which implement interface to process output (If you don't have your PSHost output interface implemented, your will get an exception when Out-default finally called out-host.). Every interactive command from user input should have Out-Default appended. Then the output of user command were assessed by out-default, formatted by format-* cmdlet, and eventually sent to user interface by out-host cmdlet. &lt;br /&gt;&lt;blockquote&gt;using System.Management.Automation;&lt;br /&gt;using System.Management.Automation.Host;&lt;br /&gt;using System.Management.Automation.Runspaces;&lt;br /&gt;&lt;br /&gt;namespace HostingExample&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;class TestHost&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;{&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;static void Main(string[] args)&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;{&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;string command = "gps";&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;PSHost myhost = new MyHost(); &lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;Runspace myRunspace = RunspaceFactory.CreateRunspace(myhost);&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;myRunspace.Open();&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;Pipeline pipeline1 = myRunspace.CreatePipeline(command, true);&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;pipeline1.Commands[0].MergeMyResults(PipelineResultTypes.Error, PipelineResultTypes.Output);&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;pipeline1.Commands.Add("out-default");&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;Pipeline1.Invoke();&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;}&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;}&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;Class MyHost : PSHost&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;{&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // MyHost class should be derived from PSHost abstract class. &lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;}&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;Although you don't have to (and probably should not) type "Out-Default" at the end of your command, it is always there working for you. Given this reason, Out-Default cmdlet is registered and loaded as default cmdlets.&lt;br /&gt;&lt;br /&gt;You see it is there, you do not use it, but it is definitely important.&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-115276202311148291?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/115276202311148291/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/07/why-there-is-out-default-cmdlet.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115276202311148291'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115276202311148291'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/07/why-there-is-out-default-cmdlet.html' title='Why There Is an Out-Default Cmdlet'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-115189679421169112</id><published>2006-07-02T23:17:00.000-04:00</published><updated>2006-07-02T23:19:54.230-04:00</updated><title type='text'>Naive and Generic Object Collections in Powershell</title><content type='html'>I believed that you must have dealt with collections in Powershell Scriting. PowerShell has a nice way to support naive object array (object[]):&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&amp;gt;$a = 1,2,3&amp;nbsp;&amp;nbsp; #comma were interpreted as object[]&lt;br /&gt;&amp;gt;$a.gettype().AssemblyQualifiedName&lt;br /&gt;&lt;font color="#ff0000"&gt;System.Object[]&lt;/font&gt;, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089&lt;br /&gt;&lt;br /&gt;&amp;gt;$a= 1..10&amp;nbsp;&amp;nbsp; # .. were interpreted as continuous filled object[]&lt;br /&gt;&amp;gt;$a.gettype().AssemblyQualifiedName&lt;br /&gt;&lt;font color="#ff0000"&gt;System.Object[]&lt;/font&gt;, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089&lt;br /&gt;&lt;/blockquote&gt;For naive object ArrayList/stack/Queue, you have to use new-object cmdlet&lt;br /&gt;&lt;blockquote&gt;&amp;gt; $a = new-object System.Collections.Stack&lt;br /&gt;&amp;gt; $a.GetType().AssemblyQualifiedName&lt;br /&gt;System.Collections.Stack, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKey&lt;br /&gt;Token=b77a5c561934e089&lt;br /&gt;&amp;gt; $a.Push($([System.Net.IPAddress] "192.168.0.1"))&lt;br /&gt;&lt;/blockquote&gt;Most of time, you are fine with naive object model because PowerShell will do the type conversion for you. &lt;br /&gt;&lt;blockquote&gt;&amp;gt;$a= 1..10&lt;br /&gt;&amp;gt;$a |gm&lt;br /&gt;&amp;nbsp;&amp;nbsp; TypeName: &lt;font color="#ff0000"&gt;System.Int32&lt;/font&gt;&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; MemberType Definition&lt;br /&gt;----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ---------- ----------&lt;br /&gt;CompareTo&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int32 CompareTo(Int32 value), System.Int32 Com...&lt;br /&gt;Equals&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean Equals(Object obj), System.Boolean Equ...&lt;br /&gt;GetHashCode Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int32 GetHashCode()&lt;br /&gt;GetType&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Type GetType()&lt;br /&gt;GetTypeCode Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.TypeCode GetTypeCode()&lt;br /&gt;ToString&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String ToString(), System.String ToString(IFor...&lt;br /&gt;&lt;/blockquote&gt;But sometimes it is not good enough. You probably want to use generic object model. &lt;br /&gt;&lt;br /&gt;For generic array (like System.Net.IPAddress[]), it requires a conversion:&lt;br /&gt;&lt;blockquote&gt;&amp;gt;$a = ($([System.Net.IPAddress] "192.168.0.1"),$([System.Net.IPAddress] "127.0.0.1") )&lt;br /&gt;&amp;gt;$a.gettype().AssemblyQualifiedName&lt;br /&gt;&lt;font color="#ff0000"&gt;System.Object[]&lt;/font&gt;, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089&lt;br /&gt;&amp;gt;$b= [System.Net.IPAddress[]] $a&lt;br /&gt;&amp;gt; $b.GetType().AssemblyQualifiedName&lt;br /&gt;&lt;font color="#ff0000"&gt;System.Net.IPAddress[]&lt;/font&gt;, System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089&lt;br /&gt;&lt;/blockquote&gt;For generic collection (like System.Collections.ObjectModel.Collection&amp;lt;System.Net.IPAddress&amp;gt;), it becomes a little nasty (it requires Assembly Qualified Name) :&lt;br /&gt;&lt;blockquote&gt;&amp;gt;$a = New-Object System.Collections.ObjectModel.Collection"`1[[System.Net.IPAddress, System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]]"&lt;br /&gt;&amp;gt; $a.GetType().AssemblyQualifiedName&lt;br /&gt;System.Collections.ObjectModel.Collection`1[[System.Net.IPAddress, System, Vers&lt;br /&gt;ion=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]], mscorlib, Vers&lt;br /&gt;ion=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089&lt;br /&gt;&amp;gt; $a.Add($([System.Net.IPAddress] "192.168.0.1"))&lt;br /&gt;&lt;/blockquote&gt;What about generic Stack?&lt;br /&gt;&lt;blockquote&gt;&amp;gt; $a = New-Object System.Collections.Generic.Stack"`1[[System.Net.IPAddres&lt;br /&gt;s, System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]]"&lt;br /&gt;&amp;gt; $a.GetType().AssemblyQualifiedName&lt;br /&gt;System.Collections.Generic.Stack`1[[System.Net.IPAddress, System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]], System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089&lt;br /&gt;&amp;gt; $a.Push($([System.Net.IPAddress] "192.168.0.1"))&lt;br /&gt;&amp;gt; $a.pop()&lt;br /&gt;IPAddressToString : 192.168.0.1&lt;br /&gt;Address&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 16820416&lt;br /&gt;AddressFamily&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : InterNetwork&lt;br /&gt;ScopeId&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; :&lt;br /&gt;IsIPv6Multicast&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;IsIPv6LinkLocal&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;IsIPv6SiteLocal&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-115189679421169112?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/115189679421169112/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/07/naive-and-generic-object-collections.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115189679421169112'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115189679421169112'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/07/naive-and-generic-object-collections.html' title='Naive and Generic Object Collections in Powershell'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-115163798628441993</id><published>2006-06-29T23:18:00.000-04:00</published><updated>2006-06-29T23:26:26.300-04:00</updated><title type='text'>PowerShell Remoting version 0.2.7.1</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client1.3.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client1.3.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client2.1.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client2.1.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client3.1.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client3.1.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a href="http://www.gotdotnet.com/Workspaces/Workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;Download here&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;&lt;font color="red"&gt;Uninstall old version of PowerShell Remoting before install newer version.&lt;/font&gt;&lt;/span&gt;&lt;br /&gt;&lt;ol&gt;&lt;li&gt;New GUI client manager: Save/delete server information &amp;amp; connection option,  generate connection script automatically, launch powershell remoting client  directly.&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Add option to reject connection if user found invalid remote X509 certificate.&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Bug fix: Null login credential (press Cancel in CredUI window) cause server  crash and client throw Null reference exception. &lt;/li&gt;&lt;br /&gt;&lt;li&gt;Bug fix: other minor bugs&lt;/li&gt;&lt;/ol&gt;&lt;span style="font-weight: bold;"&gt;Check out the help.chm in release package for details.&lt;/span&gt; &lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-115163798628441993?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/115163798628441993/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/06/powershell-remoting-version-0271.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115163798628441993'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115163798628441993'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/06/powershell-remoting-version-0271.html' title='PowerShell Remoting version 0.2.7.1'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-115103355513937622</id><published>2006-06-22T23:27:00.000-04:00</published><updated>2006-06-26T14:42:18.080-04:00</updated><title type='text'>Enter Nested Prompt function</title><content type='html'>In windows PowerShell, $Host object provides direct access to some important APIs. One of the interesting functions is &lt;b&gt;$Host.EnterNestedPrompt()&lt;/b&gt;. Frankly speaking, it did not appeal to me at all when I first tried it. But I discovered this beauty after I implemented my own PSHost&amp;nbsp; in &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;PowerShell Remoting&lt;/a&gt;,&lt;br /&gt;&lt;br /&gt;What did it do?&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Suspend &amp;amp; Save current execution context state. &lt;/li&gt;&lt;li&gt;Create a new nested execution context.(Nested pipline, new prompt execution helper and new script excution helper)&lt;/li&gt;&lt;li&gt;Push the new nested execution context to stack. (PowerShell use a static stack. In my PowerShell Remoting, it is more complicate. Every client has its own host; every host has its own stack for nested prompt.)&lt;/li&gt;&lt;li&gt;Increase &lt;b&gt;$NESTEDPROMPTLEVEL&lt;/b&gt;&lt;/li&gt;&lt;/ol&gt;That is to say:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Your current pipeline is suspended. All variables and errors state were saved. &lt;/li&gt;&lt;li&gt;In the meantime, you still have access to monad engine. You can have new prompt, run new script or other interactive command.&lt;/li&gt;&lt;li&gt;When you are done with the new scope, you can call invoke $Host.ExitNestedPrompt()&amp;nbsp; or "exit" (which will call $Host.ExitNestedPrompt())&amp;nbsp; to return to previous pipeline. &lt;/li&gt;&lt;/ol&gt;What can I do with it?&lt;br /&gt;&lt;ol&gt;&lt;li&gt;First, Let's see how "&lt;b&gt;Suspend&lt;/b&gt;" works when using &lt;font color="#ff0000"&gt;-confirm option&lt;/font&gt; or "&lt;font color="#ff0000"&gt;Set-PSDebug -Step&lt;/font&gt;"&lt;/li&gt;&lt;blockquote&gt;&amp;gt; kill 2804 -Confirm&lt;br /&gt;&lt;br /&gt;Confirm&lt;br /&gt;Are you sure you want to perform this action?&lt;br /&gt;Performing operation "Stop-Process" on Target "Notepad (2804)".&lt;br /&gt;[Y] Yes&amp;nbsp; [A] Yes to All&amp;nbsp; [N] No&amp;nbsp; [L] No to All&amp;nbsp; [S] Suspend&amp;nbsp; [?] Help&lt;br /&gt;(default is "Y"):&lt;br /&gt;&lt;br /&gt;&amp;gt; Set-PSDebug -Step&lt;br /&gt;&amp;gt; D:\ps1\special.ps1&lt;br /&gt;&lt;br /&gt;Continue with this operation?&lt;br /&gt;&amp;nbsp;&amp;nbsp; 1+ D:\ps1\special.ps1&lt;br /&gt;[Y] Yes&amp;nbsp; [A] Yes to All&amp;nbsp; [N] No&amp;nbsp; [L] No to All&amp;nbsp; [S] Suspend&amp;nbsp; [?] Help&lt;br /&gt;(default is "Y"):&lt;br /&gt;&lt;/blockquote&gt;When you choose [S]Suspend, you actually called $Host.EnterNestedPrompt() which break current script and provide you an nested prompt.&lt;br /&gt;&lt;li&gt;Secondly, $Host.EnterNestedPrompt() can be used as break point when debugging your script. &lt;/li&gt;To make a break point, you can add $Host.EnterNestedPrompt() at anywhere in your script. When your script execute to it, you will have a nested prompt to explore variables and errors at this break point.&lt;br /&gt;&lt;blockquote&gt;&amp;gt; 1..10 | %{if($_ -eq 5) {$host.EnterNestedPrompt()};$_}&lt;br /&gt;1&lt;br /&gt;2&lt;br /&gt;3&lt;br /&gt;4&lt;br /&gt;&amp;gt;&amp;gt;&amp;gt; $_&lt;br /&gt;5&lt;br /&gt;&amp;gt;&amp;gt;&amp;gt; exit&lt;br /&gt;5&lt;br /&gt;6&lt;br /&gt;7&lt;br /&gt;8&lt;br /&gt;9&lt;br /&gt;10&lt;/blockquote&gt;&lt;/ol&gt;Be careful&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Nested prompt and original prompt share same variables provider. So when you change a variable in nested prompt, the change will remain effective in original prompt.&lt;/li&gt;&lt;li&gt;Comannd will be written in history when it is completed. So a suspended command will not be found in history. &lt;br /&gt;&lt;/li&gt;&lt;li&gt;The maximum depth of nested prompt level ($NESTEDPROMPTLEVEL) is 128. So always check $NESTEDPROMPTLEVEL for current nested prompt level. You can write it into your prompt function.&lt;/li&gt;&lt;li&gt;Do not try to make a nested function using $Host.EnterNestedPrompt(). But you can always do this.&lt;/li&gt;&lt;blockquote&gt;function factorial&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; param ([int]$n = 1)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($n -le 0)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; "Invalid parameter."&lt;br /&gt;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($n -eq 1)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return 1&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return $n * (factorial ($n-1))&lt;br /&gt;}&lt;/blockquote&gt;&lt;/ol&gt;Reference: &lt;a href="http://blogs.msdn.com/monad/archive/2006/04/15/576996.aspx"&gt;Start-NewScope&lt;/a&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-115103355513937622?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/115103355513937622/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/06/enter-nested-prompt-function.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115103355513937622'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115103355513937622'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/06/enter-nested-prompt-function.html' title='Enter Nested Prompt function'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-115012747838106576</id><published>2006-06-12T11:30:00.000-04:00</published><updated>2006-06-12T11:52:09.456-04:00</updated><title type='text'>What Access Rights Do You Have?</title><content type='html'>A PowerShell script to check User/Group access rights on FileSystem and Registry.&lt;br /&gt;&lt;br /&gt;Yesterday, I was reading post on Mark's Sysinternals Blog: &lt;a href="http://www.sysinternals.com/blog/2006/05/power-in-power-users.html"&gt;The Power in Power Users&lt;/a&gt;. It says "&lt;b&gt;a user that belongs to the Power Users group can easily elevate themselves to fully-privileged administrators&lt;/b&gt;". He used a tool called &lt;b&gt;AccessChk&lt;/b&gt; to find out what access rights does "Power User" group have. &lt;br /&gt;&lt;br /&gt;If you read my serise posts on &lt;a href="http://mshforfun.blogspot.com/2006/01/combination-rights-inheritance-and.html"&gt;access control list in monad&lt;/a&gt;.&amp;nbsp; you will find out that we can get/set access rule in PowerShell directly without using extra tools. So I wrote a PowerShell script (Check-AccessRights.ps1) to get similar function as AccessChk. It is pretty dirty, but dose the job. You may want to try&lt;br /&gt;&lt;blockquote&gt;D:\ps1\Check-AccessRights.ps1 .\ &lt;br /&gt;# Check your access rights on current path (could be filesystem or registry)&lt;br /&gt;&lt;/blockquote&gt;or&lt;br /&gt;&lt;blockquote&gt;D:\ps1\Check-AccessRights.ps1 HKLM:\sytem\CurrentControlSet\Services $true "Power Users"&lt;br /&gt;# HKLM:\sytem\CurrentControlSet\Services is Path to check&lt;br /&gt;# $true is to get child object ACL recursively&lt;br /&gt;# "Power Users" is user/group&lt;br /&gt;&lt;/blockquote&gt;Be prepared if you use -Recurse option ($true), you may want to redirect results to a file.&lt;br /&gt;&lt;blockquote&gt;#################################################################&lt;br /&gt;#&lt;br /&gt;# File: Check-AccessRights.ps1&lt;br /&gt;# Author: Tony (http://MSHForFun.blogspot.com/)&lt;br /&gt;# Parameters:&lt;br /&gt;#&amp;nbsp;&amp;nbsp;&amp;nbsp; $Path:&amp;nbsp; PowerShell Path (for example, c:\ or HKLM:\)&lt;br /&gt;#&amp;nbsp;&amp;nbsp;&amp;nbsp; $Recurse: Check child object recursively&lt;br /&gt;#&amp;nbsp;&amp;nbsp;&amp;nbsp; $Account: User name / Group (for example, "domain\alice", &lt;br /&gt;#&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; "Power Users")&lt;br /&gt;#&lt;br /&gt;################################################################&lt;br /&gt;param([string] $Path = {throw "Please specify a path"}, [bool] $Recurse = $false, [string] $Account)&lt;br /&gt;if (-not (test-path $Path))&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Path + " not exists!"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return&lt;br /&gt;}&lt;br /&gt;if ([string]::ISNullOrEmpty($Account))&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $SID = ([System.Security.Principal.WindowsIdentity]::GetCurrent()).Owner&lt;br /&gt;}&lt;br /&gt;else&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $SID = (new-object System.Security.Principal.NTAccount($Account)).Translate([System.Security.Principal.SecurityIdentifier])&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($SID -eq $null) {return}&lt;br /&gt;}&lt;br /&gt;"Account: " + $SID.ToString()&lt;br /&gt;"Path: " + $Path&lt;br /&gt;$AccessRules = (get-acl $Path).Access&lt;br /&gt;if ($AccessRules -eq $null)&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; "Can't get access rules!"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return&lt;br /&gt;}&lt;br /&gt;$AccessRules|foreach-object {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $CurrentSID = $_.IdentityReference.Translate([System.Security.Principal.SecurityIdentifier])&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($CurrentSID.ToString() -eq $SID.ToString())&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $_&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;} &lt;br /&gt;if ($Recurse)&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Get-ChildItem $Path -Recurse| foreach {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; "========================================"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; "Child Path: " + $_.ToString()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $AccessRules = (get-acl $Path).Access&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($AccessRules -eq $null)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; "Can't get access rules!"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $AccessRules|foreach-object {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $CurrentSID = $_.IdentityReference.Translate([System.Security.Principal.SecurityIdentifier])&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($CurrentSID.ToString() -eq $SID.ToString())&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $_&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; } &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-115012747838106576?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/115012747838106576/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/06/what-access-rights-do-you-have.html#comment-form' title='8 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115012747838106576'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/115012747838106576'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/06/what-access-rights-do-you-have.html' title='What Access Rights Do You Have?'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>8</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114973866711629890</id><published>2006-06-07T23:45:00.000-04:00</published><updated>2006-06-07T23:51:07.133-04:00</updated><title type='text'>PowerShellIDE: the Good, the Bad and the Ugly</title><content type='html'>&lt;a href="http://www.powershell.com/"&gt;PowerShellIDE&lt;/a&gt;? Yes, an IDE for PowerShell! Oh, boy! That's a whole lot fun. If you like PowerShell, you should try this out.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;The good&lt;/b&gt;:&lt;br /&gt;It is advertised (it is free at this moment) as "&lt;b&gt;The World's First PowerShell Editor&lt;/b&gt;" (what is "PowerShell Analyzer" then?) and wrapped in a dazzling GUI (you should really checkout its Mac style chooser). &lt;br /&gt;&lt;br /&gt;You got intellisense functionality, a debugger, variable explorer and properties window. &lt;br /&gt;&lt;br /&gt;You can set up a breakpoint in your script and checkout pipline in a GUI environment. &lt;br /&gt;&lt;br /&gt;It is the first GUI Monad hosting application I have seen which can handle legacy console application (like ping.exe or netshe.exe)&lt;br /&gt;&lt;br /&gt;&lt;b&gt;The bad&lt;/b&gt;:&lt;br /&gt;1. Not yet implemented.&lt;br /&gt;You'd better forgot about following API:&lt;br /&gt;Read-host -AsSecureString (ReadLineAsSecureString)&lt;br /&gt;PromptForCredential&lt;br /&gt;SetBufferContents&lt;br /&gt;Getbuffercontents&lt;br /&gt;&lt;br /&gt;2. It is not the same!&lt;br /&gt;Don't expect same user experience with&lt;br /&gt;Write-progress&lt;br /&gt;$host.UI.ReadLine() (Oops, Popup window)&lt;br /&gt;$host.UI.RawUI.ReadKey() &lt;br /&gt;&lt;br /&gt;&lt;b&gt;The ugly&lt;/b&gt;:&lt;br /&gt;PowerShellIDE has to be run under Administrator account. This is killing me. Come on, men! Why it has to read prefetch?&lt;br /&gt;&lt;blockquote&gt;PowerShellIDE.E:3300&amp;nbsp;&amp;nbsp; &amp;nbsp;OPEN&amp;nbsp;&amp;nbsp; &amp;nbsp;C:\WINDOWS\Prefetch\POWERSHELLIDE.EXE-3628D30E.pf&amp;nbsp;&amp;nbsp; &amp;nbsp;ACCESS DENIED&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;Some other thoughts&lt;/b&gt;:&lt;br /&gt;I came across someone's post (I forgot where) talking about PowerShell: "This thing is for Programmer." Now, we have an IDE for PowerShell. It again prove "This thing is for Programmer." Remember the famous joke about Microsoft Visual Studio:" The IDE is so good and you were having so much fun with it. Eventually you forgot what you were doing." This is exactly what happened here:&lt;br /&gt;&lt;br /&gt;Despite of intellisense, the entire "breakpoint, pipline reader and properties" thing can be done in PowerShell.exe command line directly. Just add "&lt;font color="#ff0000"&gt;&lt;b&gt;$host.EnterNestedPrompt()&lt;/b&gt;&lt;/font&gt;" in my script, I can get current pipline status, explore properties as I wish. But in the windows world, everyone indulged themselves to the IDE thing. People always try to find an IDE desperately even there is no need for that. I bet those guys from "&lt;span style="font-weight:bold;"&gt;slash dot&lt;/span&gt;" will laugh at us again.&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114973866711629890?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114973866711629890/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/06/powershellide-good-bad-and-ugly.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114973866711629890'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114973866711629890'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/06/powershellide-good-bad-and-ugly.html' title='PowerShellIDE: the Good, the Bad and the Ugly'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114956886812693818</id><published>2006-06-06T00:25:00.000-04:00</published><updated>2006-06-06T00:41:08.340-04:00</updated><title type='text'>PowerShell Remoting version 0.2.6.0</title><content type='html'>&lt;div style="clear: both;"&gt;&lt;/div&gt;&lt;a href="http://www.gotdotnet.com/Workspaces/Workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;Download here&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;&lt;font color="red"&gt;Uninstall old version of PowerShell Remoting before install newer version.&lt;/font&gt;&lt;/span&gt;&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Write Server Information &amp;amp; Error to EventLog (Source: PowerShellRemoting).  Log file will no longer be used by newer version.&lt;/li&gt;&lt;br /&gt;&lt;li&gt;SSL support using SSLStream.&lt;/li&gt;&lt;br /&gt;&lt;font color="#ff0000"&gt;Warning: SSL is for advanced user.&lt;/font&gt; &lt;br /&gt;If you want to provide SSL support to server, you should&lt;br /&gt;&lt;ul&gt; &lt;br /&gt;&lt;li&gt;Get X509 certificate for server. For testing purpose, you can use makecert.exe (included in .NET framework SDK) &lt;br /&gt;&lt;/li&gt;&lt;li&gt;Install X509 certificate at StoreLocation: LocalMachine, StoreName: My (personal). &lt;br /&gt;&lt;/li&gt;&lt;li&gt;Grand "NetworkService" account read access to X509 certificate associated private key file. &lt;br /&gt;&lt;/li&gt;&lt;li&gt;Set [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PowerShellRemoting\Parameters\ X509] to thumbprint of X509 Certificate.&lt;br /&gt;&lt;br /&gt;There is pretty good walkthrough at &lt;a href="http://blogs.technet.com/jhoward/archive/2005/02/02/365323.aspx"&gt;John Howard's blog&lt;/a&gt;.&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;li&gt;X509 Option &lt;/li&gt;&lt;br /&gt;[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PowerShellRemoting\Parameters]&lt;br /&gt;"X509"="0"&lt;br /&gt;&lt;br /&gt;&lt;li&gt;DebugHost Option (Default 0: false)&lt;/li&gt;&lt;br /&gt;[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PowerShellRemoting\Parameters]&lt;br /&gt;"DebugHost"=dword:00000000 &lt;br /&gt;&lt;br /&gt;&lt;li&gt;Bug fix: Write-Progress throw null object Exception.&lt;/li&gt;&lt;/ol&gt;&lt;span style="font-weight:bold;"&gt;Check out the help.chm in release package for details.&lt;/span&gt; &lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114956886812693818?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114956886812693818/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/06/powershell-remoting-version-0260.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114956886812693818'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114956886812693818'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/06/powershell-remoting-version-0260.html' title='PowerShell Remoting version 0.2.6.0'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114904804238664260</id><published>2006-05-30T23:56:00.000-04:00</published><updated>2006-05-31T00:00:42.400-04:00</updated><title type='text'>Download Gene Sequences Using NCBI eFetch Tools</title><content type='html'>Recently, I was working on a bioinformatics research project which needed to download hundreds of gene mRNA sequences. I have all the gene IDs in one text file. So a simple PowerShell Script could solve my problem.&lt;br /&gt;&lt;br /&gt;I have a &lt;a href="http://mshforfun.blogspot.com/2006/01/author-monad-cmdlet-as-web-service.html"&gt;old post talking about NCBI Entrez eUtils tools&lt;/a&gt;. Today, I will use the &lt;font color="#ff0000"&gt;&lt;b&gt;eFetch&lt;/b&gt;&lt;/font&gt; tool (also included in eUtils). The script is simple and self-explaining.&lt;br /&gt;&lt;blockquote&gt;# ===========================================================================&lt;br /&gt;#&lt;br /&gt;# Author:&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Tony (http://MSHForFun.blogspot.com)&lt;br /&gt;# File:&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Efetch.ps1&lt;br /&gt;# Description: Download gene sequences using NCBI eUtils.eFetch tool&lt;br /&gt;# Reference: http://eutils.ncbi.nlm.nih.gov/entrez/query/static/eutils_example.pl&lt;br /&gt;# Reference: http://eutils.ncbi.nlm.nih.gov/entrez/query/static/efetch_help.html&lt;br /&gt;# Reference: http://eutils.ncbi.nlm.nih.gov/entrez/query/static/efetchseq_help.html&lt;br /&gt;#&amp;nbsp; &lt;br /&gt;# ===========================================================================&lt;br /&gt;param&lt;br /&gt;(&lt;br /&gt;&amp;nbsp; [string] $Path=$(throw "Please Specify a file")&lt;br /&gt;)&lt;br /&gt;$BaseURL = "http://www.ncbi.nlm.nih.gov/entrez/eutils/efetch.fcgi?db=nucleotide&amp;amp;id="&lt;br /&gt;$Option= "&amp;amp;rettype=fasta&amp;amp;retmode=text"&lt;br /&gt;$WebClient = new-object System.Net.WebClient&lt;br /&gt;$SavePath = $Path + ".result"&lt;br /&gt;if (test-path $savePath)&lt;br /&gt;{&lt;br /&gt;&amp;nbsp; del $SavePath&lt;br /&gt;}&lt;br /&gt;foreach ( $id in (get-content $path))&lt;br /&gt;{&lt;br /&gt;&amp;nbsp; # Construct eFetch URL&lt;br /&gt;&amp;nbsp; $URL=$BaseURL + $id + $Option&lt;br /&gt;&amp;nbsp; Write-Progress -Activity "Download Sequences" -Status "Submit gene $Id"&lt;br /&gt;&amp;nbsp; # Submit and download data&lt;br /&gt;&amp;nbsp; $Data = $WebClient.DownloadString($URL)&lt;br /&gt;&amp;nbsp; # Parse Data&lt;br /&gt;&amp;nbsp; if ($Data.Length -gt 1)&lt;br /&gt;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Write-Progress -Activity "Download Sequences" -Status "$id OK"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; # Write to Console&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $data&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; # Wrtie To file&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $data &amp;gt;&amp;gt; $SavePath&lt;br /&gt;&amp;nbsp; }&lt;br /&gt;&amp;nbsp; else&lt;br /&gt;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Write-Progress -Activity "Download Sequences" -Status "$Id is not found!" &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; "$Id is not found!`n`r"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; "$Id is not found!`n`r" &amp;gt;&amp;gt; $SavePath&lt;br /&gt;&amp;nbsp; }&lt;br /&gt;&amp;nbsp; # Try not to overload NCBI Server&lt;br /&gt;&amp;nbsp; start-sleep 1&lt;br /&gt;}&lt;br /&gt;# Clear Progress pane&lt;br /&gt;Write-Progress -Activity "Download Sequences" -Status "Done" -completed &lt;br /&gt;&lt;/blockquote&gt;You need a text file (genes.txt) to test this script:&lt;br /&gt;&lt;blockquote&gt;0&lt;br /&gt;NM_008176&lt;br /&gt;NM_009140&lt;br /&gt;NM_009141&lt;br /&gt;NM_011333&lt;br /&gt;NM_013654&lt;br /&gt;NM_016960&lt;br /&gt;NM_009142&lt;br /&gt;NM_008491&lt;br /&gt;NM_031168&lt;br /&gt;NM_009883&lt;br /&gt;NM_007679&lt;br /&gt;NM_010030&lt;br /&gt;NM_009971&lt;br /&gt;NM_010809&lt;br /&gt;NM_008607&lt;br /&gt;NM_030612&lt;br /&gt;NM_011198&lt;br /&gt;NM_007987&lt;br /&gt;&lt;/blockquote&gt;If you are a biologist, you can see what kind of genes I am intersted in. The first "0" is just to cause an "Not Found" Error. You can run this script like following:&lt;br /&gt;&lt;blockquote&gt;.\efetch.ps1 genes.txt&lt;br /&gt;&lt;/blockquote&gt;Your results is printed to screen as well as "genes.txt.result" file.&lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114904804238664260?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114904804238664260/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/05/download-gene-sequences-using-ncbi.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114904804238664260'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114904804238664260'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/05/download-gene-sequences-using-ncbi.html' title='Download Gene Sequences Using NCBI eFetch Tools'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114800207482034566</id><published>2006-05-18T21:24:00.000-04:00</published><updated>2006-05-18T21:27:54.836-04:00</updated><title type='text'>PowerShell Remoting, Lock Down</title><content type='html'>Any remote shell application is dangerous because you open a door to outside world. So does PowerShell Remoting. Previous version of PowerShell Remoting totally depended on NegotiateStream. You have no control of login process or you can not limit user access.&amp;nbsp; So anyone with a valid local or domain account can login remotely into your computer. As more and more people began to download and install PowerShell Remoting on their computer, I decided to add client access control policy to PowerShell Remoting.&lt;br /&gt;&lt;br /&gt;Firstly, you should limit maximum number of clients which can connect to server simultaneously. This is done by modify registry:&lt;br /&gt;&lt;blockquote&gt;[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PowerShellRemoting\Parameters]&lt;br /&gt;"MaxClient"=dword:0000000a&lt;br /&gt;&lt;/blockquote&gt;Default value is 10. Given 256MB memory is standard configuration for desktop PC, this number is more than enough if you decided to login to your desktop from home network. You can definitely increase this number if you have more clients but remember each runspace will allocate quite a few of memory. So do some experiment and calculation then you can find a reasonable number. &lt;br /&gt;&lt;br /&gt;Secondly, you should limit maxium number of clients which can connect to server simultaneously from Same IP address. This is done by modify registry:&lt;br /&gt;&lt;blockquote&gt;[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PowerShellRemoting\Parameters]&lt;br /&gt;"MaxClientPerIP"=dword:00000002&lt;br /&gt;&lt;/blockquote&gt;Default value is 2. You can also change that but you don't want all your available slots of connection were occupied by clients from same computer.&lt;br /&gt;&lt;br /&gt;Thirdly, you may want to limit which user can login from which IP address. This is done by modify &lt;br /&gt;&lt;b&gt;%Program Files%\PowerShell Remoting\user.xml&lt;/b&gt;&lt;br /&gt;Default installation &lt;font color="#ff0000"&gt;&lt;b&gt;only allow user in Administrators group login from localhost&lt;/b&gt;&lt;/font&gt;. So you have to have your own user.xml before you can login from another IP. If user.xml file parse error occorred when start service, default policy will be loaded. If you can't login, check log file or EventLog for details of parse error. &lt;br /&gt;User.xml file contain information about your user access control list. It has SEVEN tags:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;&lt;b&gt;&amp;lt;NetworkACL&amp;gt;&lt;/b&gt;: container of one or more access control entry (&amp;lt;NetworkACE&amp;gt;)&lt;/li&gt;&lt;li&gt;&lt;b&gt;&amp;lt;NetworkACE&amp;gt;&lt;/b&gt;: access control entry container of &amp;lt;Account&amp;gt;, &amp;lt;Access&amp;gt; and &amp;lt;IPRange&amp;gt;&lt;/li&gt;&lt;li&gt;&lt;b&gt;&amp;lt;Account&amp;gt;&lt;/b&gt;: Valid Group or User&lt;/li&gt;&lt;li&gt;&lt;b&gt;&amp;lt;Access&amp;gt;&lt;/b&gt;:&amp;nbsp; Allow / Deny&lt;/li&gt;&lt;li&gt;&lt;b&gt;&amp;lt;IPRange&amp;gt;&lt;/b&gt;: container of &amp;lt;IP&amp;gt; and &amp;lt;Subnet&amp;gt;&lt;/li&gt;&lt;li&gt;&lt;b&gt;&amp;lt;IP&amp;gt;&lt;/b&gt;: IPAddress. 0.0.0.0 for any IP, 127.0.0.1 for localhost, 192.168.0.2 etc. IPv6 string should be fine, but I have not been able to test it. &lt;/li&gt;&lt;li&gt;&lt;b&gt;&amp;lt;Subnet&amp;gt;&lt;/b&gt;: IPv4 subnet. 192.168.0.0/255.255.255.0 or CIDR like format 192.168.0.0/24.&lt;/li&gt;&lt;/ol&gt;Within &amp;lt;NetworkACE&amp;gt; and &amp;lt;/NetworkACE&amp;gt; tags, order matters. &lt;br /&gt;&lt;ol&gt;&lt;li&gt;&amp;lt;Account&amp;gt;&lt;/li&gt;&lt;li&gt;&amp;lt;Access&amp;gt;&lt;/li&gt;&lt;li&gt;&amp;lt;IPRange&amp;gt;&lt;/li&gt;&lt;/ol&gt;Within &amp;lt;IPRange&amp;gt; and &amp;lt;/IPRange&amp;gt; tags, &amp;lt;IP&amp;gt; and &amp;lt;Subnet&amp;gt; can be used in any order. &lt;br /&gt;As you can probably already figured it out : After user provide credential and got a token (WindowsIdentity), PowerShell Remoting will try to match User/Group and IP range in records of access control list. If no record was found, access is denied. If a records match User/Group and IP range were found, PowerShell Remoting will assess access in following order:&lt;br /&gt;&lt;blockquote&gt;User Deny &amp;gt; User Allow &amp;gt; Group Deny &amp;gt; Group Allow&lt;br /&gt;&lt;/blockquote&gt;For example: if client were a privileged user (Administrators group) from 192.168.0.2, but there were only one record which wanted to deny access of Users group from subnet 192.168.0.0/255.255.255.0. Then access from this client will be denied because any user belongs to Administrators group also belongs to Users group and 192.168.0.2 belongs to subnet 192.168.0.0/255.255.255.0.&lt;br /&gt;&lt;br /&gt;After you logged in and get a PowerShell prompt, you can check $UserACL for serialized access control list.&lt;br /&gt;&lt;br /&gt;Right now, subnet parsing and match could be buggy. So tell me if you found it did not act as expected.&lt;br /&gt;&lt;br /&gt;These changes could make it more difficult to start using PowerShell Remoting. But I believed that you will like them later on. Remember, if you make any changes to previous setting, you will have to restart service to make them take effect.&lt;br /&gt;&lt;blockquote&gt;Stop-Service PowerShellRemoting&lt;br /&gt;Start-Service PowerShellRemoting&lt;br /&gt;&lt;/blockquote&gt;There is also some exciting new feature:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;PowerShell Remoting Client becomes a PSSnapin now. So installation become usier. Just run install.ps1 in client folder and invoke Start-RemoteHost, you are on you way to your remote shell.&lt;/li&gt;&lt;li&gt;Ctrl+C Ctrl+Break support. &lt;br /&gt;&lt;/li&gt;Try&lt;blockquote&gt;dir c:\windows\system32&lt;br /&gt;&lt;/blockquote&gt;And press Ctrl+C to cancel it. If you don't want to handle Ctrl+C, you can set&lt;br /&gt;&lt;blockquote&gt;$RemotingClient.CanHandleCancelKey = $false &lt;br /&gt;&lt;/blockquote&gt;But you probably do not want to do that.&lt;br /&gt;Ctrl+Break will also quit PowerShell Session. So Use it with caution.&lt;br /&gt;&lt;br /&gt;&lt;li&gt;You will find out that information written in log file has been dramatically reduced because I am going to swith to EventLog in later verion.&lt;/li&gt; &lt;/ol&gt;I can actually run PowerShell Remoting Client with in PowerShell Analyzer. But its ReadLine popup window really bothers me.&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114800207482034566?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114800207482034566/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/05/powershell-remoting-lock-down.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114800207482034566'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114800207482034566'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/05/powershell-remoting-lock-down.html' title='PowerShell Remoting, Lock Down'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114798687549458582</id><published>2006-05-18T17:05:00.000-04:00</published><updated>2006-05-18T18:49:34.426-04:00</updated><title type='text'>PowerShell Remoting version 0.2.5.1</title><content type='html'>&lt;a href="http://www.gotdotnet.com/Workspaces/Workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;Version 0.2.5.1&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;&lt;font color="red"&gt;Uninstall old version of PowerShell Remoting before install newer version.&lt;/font&gt;&lt;/span&gt;&lt;br /&gt;&lt;ol&gt;&lt;br /&gt;&lt;li&gt;Support Ctrl+C and Ctrl+Break to cancel current pipeline (UDP datagram, So not 100% reliable)&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Support Maximum Client per IP option (default 2)&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Customized client filter policy (%Program Files%\PowerShell Remoting\user.xml, see sample files for format information)&lt;/li&gt;&lt;br /&gt;   &lt;B&gt;Important&lt;/B&gt;: default installation &lt;font color = "red"&gt;only allow user in Administrators group login from localhost&lt;/font&gt;. So you have to have your own user.xml before you can login from another IP. If user.xml file parse error occorred when start service, default policy will be loaded. Check log file or EventLog for details of parse error. &lt;br /&gt;&lt;br /&gt;&lt;li&gt;$UserACL variable for current client filter policy&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Client is installed as PSSnapin&lt;/li&gt;&lt;br /&gt;&lt;li&gt;New install/uninstall script for both server and client, new start-remotehost.ps1 script&lt;/li&gt;&lt;br /&gt;&lt;li&gt;CanThrowException and CanHandleCancelKey property of client (For developer)&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Change Log file path to %Documents and Settings%\NetworkService\Local Settings\Application Data\PowerShellRemoting.log&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Change Service Name to "PowerShellRemoting"&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Service related Exception is also Logged to Eventlog (EventLog: Application, source: PowershellRemoting)&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Other Bugs fixed&lt;/li&gt;&lt;br /&gt;&lt;/ol&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114798687549458582?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114798687549458582/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/05/powershell-remoting-version-0251.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114798687549458582'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114798687549458582'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/05/powershell-remoting-version-0251.html' title='PowerShell Remoting version 0.2.5.1'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114757504586214835</id><published>2006-05-13T22:47:00.000-04:00</published><updated>2006-05-16T08:42:15.000-04:00</updated><title type='text'>Potential Security Problem of PSSnapin Installation and Execution</title><content type='html'>Windows PowerShell is powerful (hehe, sounds like a bad salesman). To make it even better, user can extent it by &lt;b&gt;PSSnapin&lt;/b&gt;. PSSnapin can contain PSProviders, Cmdlets and other class library. But there is a catch. PSSnapin is arbitrary code which could be bad designed, bugs loaded and somewhat out of your control. If you are not careful when install and execute, PSSnapin can cause serious security problems. Let's look following example:  &lt;br /&gt;&lt;br /&gt;Supposed you have a PSSnapin:&lt;br /&gt;&lt;blockquote&gt;using System;&lt;br /&gt;using System.ComponentModel;&lt;br /&gt;using System.Management.Automation;&lt;br /&gt;namespace TestSnapin&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; [RunInstaller(true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public class MySnapin : PSSnapIn&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Name&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;        {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return "Test"; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Vendor&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return "http://MSHForFun.blogspot.com/"; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Description&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return "Test"; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp; public class Class2&lt;br /&gt;&amp;nbsp;&amp;nbsp;    {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string Who&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return "Good Guy!"; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;You built it by yourself or simply downloaded it from internet. You (&lt;b&gt;An Administrator&lt;/b&gt;) copied it to a folder and ran installutil.exe to install it. Then you tried to use it in PowerShell:&lt;br /&gt;&lt;blockquote&gt;&amp;gt;get-pssnapin -reg&lt;br /&gt;&lt;br /&gt;Name        : Test&lt;br /&gt;PSVersion   : 1.0&lt;br /&gt;Description : Test&lt;br /&gt;&lt;br /&gt; &amp;gt; add-pssnapin test&lt;br /&gt; &amp;gt; $a = new-object TestSnapin.Class2&lt;br /&gt; &amp;gt; $a.Who&lt;br /&gt;&lt;font color="#ff0000"&gt;&lt;b&gt;Good Guy!&lt;/b&gt;&lt;/font&gt;&lt;br /&gt;&lt;/blockquote&gt;Looks perfect, right? But&lt;br /&gt;&lt;ol&gt;&lt;li&gt;The folder where you save your PSSnapin is &lt;b&gt;writeable by any user&lt;/b&gt;, so anyone can change your PSSnapin.&lt;/li&gt;&lt;li&gt;Your PSSnapin assembly is &lt;b&gt;not signed&lt;/b&gt;, so PowerShell will load it without checking its integrity. See the registry key about your PSSnapin&lt;/li&gt;&lt;/ol&gt;&lt;blockquote&gt;Windows Registry Editor Version 5.00&lt;br /&gt;&lt;br /&gt;[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\PowerShell\1\PowerShellSnapIns\Test]&lt;br /&gt;"PowerShellVersion"="1.0"&lt;br /&gt;"Vendor"="http://MSHForFun.blogspot.com/"&lt;br /&gt;"Description"="Test"&lt;br /&gt;"Version"="1.0.0.0"&lt;br /&gt;"ApplicationBase"="D:\\ps1"&lt;br /&gt;"AssemblyName"="Snapin1, Version=1.0.0.0, Culture=neutral, &lt;font color="#ff0000"&gt;&lt;b&gt;PublicKeyToken=null&lt;/b&gt;&lt;/font&gt;"&lt;br /&gt;"ModuleName"="D:\\ps1\\snapin1.dll"&lt;br /&gt;&lt;/blockquote&gt;Suppose there were a malicious user wrote a PSSnapin like yours PSSnapin except Class2: &lt;br /&gt;&lt;blockquote&gt;public class Class2&lt;br /&gt;    {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string Who&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return "Bad Guy!"; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;    }&lt;br /&gt;&lt;/blockquote&gt;He just overwrote your PSSnapin with his DLL. What happened next?&lt;br /&gt;&lt;blockquote&gt;&amp;gt; add-pssnapin test&lt;br /&gt; &amp;gt; $a = new-object TestSnapin.Class2&lt;br /&gt; &amp;gt; $a.Who&lt;br /&gt;&lt;font color="#ff0000"&gt;&lt;b&gt;Bad Guy!&lt;/b&gt;&lt;/font&gt;&lt;br /&gt;&lt;/blockquote&gt;That is to say user can run any code he wanted. In a worst condition, when you (&lt;b&gt;An Administrator&lt;/b&gt;) tried to use this PSSnapin, you were actually &lt;b&gt;tricked into running malicious code as Administrator!&lt;/b&gt;&lt;br /&gt;&lt;br /&gt;So Lessons: &lt;br /&gt;&lt;ol&gt;&lt;li&gt;Keep an eye on your PSSnapin. Never put them in a directory which is writeable by unprivileged user&lt;/li&gt;&lt;Font color="red"&gt;Edit: 2006-05-16 08:36&lt;/font&gt;&lt;br /&gt;"Since snapins are programs that you install, it is wise to apply the tenets and best practices of software installation to them...The potential security problems don't come from PSSnapins -- they come from executing code that you don't trust. " --Lee&lt;br /&gt;&lt;Font color="red"&gt;Edit: 2006-05-16 08:36&lt;/font&gt;&lt;br /&gt;&lt;li&gt;Always use a Signed PSSnapin. If a signed PSSnapin were altered, PowerShell will not load it.&lt;/li&gt;&lt;blockquote&gt;&amp;gt; add-pssnapin test&lt;br /&gt;Add-PSSnapin : Cannot load PSSnapIn test. Encountered following error: PSSnapin&lt;br /&gt; module D:\ps1\snapin1.dll doesn't have required PSSnapin strong name Snapin1,&lt;br /&gt;Version=1.0.0.0, Culture=neutral, PublicKeyToken=3daf9f8a713aaa33.&lt;br /&gt;At line:1 char:13&lt;br /&gt;+ add-pssnapin  &amp;lt;&amp;lt;&amp;lt;&amp;lt; test&lt;br /&gt;&lt;/blockquote&gt;&lt;/ol&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114757504586214835?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114757504586214835/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/05/potential-security-problem-of-pssnapin.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114757504586214835'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114757504586214835'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/05/potential-security-problem-of-pssnapin.html' title='Potential Security Problem of PSSnapin Installation and Execution'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114737974215835506</id><published>2006-05-11T16:19:00.000-04:00</published><updated>2006-05-11T16:35:42.323-04:00</updated><title type='text'>New Shell, New Script Language, Same Old Problem</title><content type='html'>I was reading post on "The Old New Thing" titled "&lt;a href="http://www.leeholmes.com/blog/NothingSolvesEverythingPowerShellAndOtherTechnologies.aspx"&gt;A new scripting language doesn't solve everything&lt;/a&gt;" yesterday. I was just going to write something about this. Lee was one step ahead of me and did a response post titled "&lt;a href="http://blogs.msdn.com/oldnewthing/archive/2006/04/27/585047.aspx"&gt;Nothing solves everything - PowerShell and other technologies&lt;/a&gt;". &lt;br /&gt;&lt;br /&gt;Monad (well, I mean PowerShell) is cool. We have new shell and new script language. But it is still going to be a very long time before we can do everything using cmdlet because not only we need time to write new cmdlets, but also we are limited by what .NET Framwork can do. Most important, monad is NOT supposed to "solve everything". Instead monad is supposed to work cooperatively with "OLD" techniques. So we have to deal with backwards compatibility issue. For example, other scripting language, unmanaged code and legacy program (console application). I will talk about support for console application in monad hosting application today.&lt;br /&gt;&lt;br /&gt;For a local interactive user, powershell.exe provides nice support for "old" console application inherited from cmd.exe. Common user don't even feel much difference between cmd.exe and powershell.exe if they just invoke &lt;br /&gt;&lt;blockquote&gt;ping localhost&lt;br /&gt;&lt;/blockquote&gt;For a programmer, there is a difference lying underneath the surface. Monad using &lt;b&gt;PSHostUserinterface&lt;/b&gt; and &lt;b&gt;PSHostRawUserinterface&lt;/b&gt; to get user input and display results if user invokes cmdlets. To support legacy console application, powershell.exe actually &lt;b&gt;create a new process (outside of pipeline) and redirects stdin/stdout/stderr of legacy console application to its own console&lt;/b&gt;.&lt;br /&gt;&lt;br /&gt;PowerShell.exe works fine for two reasons:&lt;br /&gt;1. PowerShell.exe itself is a console application. &lt;br /&gt;2. PowerShell.exe does NOT care whether the legacy console application runs in a different process or not. (cmdlet runs in-process)&lt;br /&gt;&lt;br /&gt;It becomes a nightmare if you are going to write a hosting application. Considering what will happen when user invokes console application inside your hosting application like "netsh.exe" which requires user input/output and you did not redirect input and output.&lt;br /&gt;1. Legacy console application start a new process which is out of your control&lt;br /&gt;2. If your hosting application is not a console application (like PowerShell Analyzer), legacy console application start a new Console window which is out of your control. "You can loose output or hang waiting for input that never comes." -- William Stacey [MVP]&lt;br /&gt;3. For a remoting host application (like my PowerShell Remoting), it is even worse because the new console window is on another computer, there is no way for remote user move their cursor to the console window and provide input.&lt;br /&gt;&lt;br /&gt;It is NOT a trivial work to solve this problem. My "&lt;a href="http://mshforfun.blogspot.com/2006/03/powershell-remoting-beta-and-future.html"&gt;PowerShell Remoting&lt;/a&gt;" does not solve this issue (A NotSupportException will be thrown if user invoked legacy console application). &lt;a href="http://karlprosser.edify.us/coder/"&gt;Karl Prosser's PowerShell Analyzer&lt;/a&gt;&amp;nbsp; does not solve this problem. If you follow the disscussion in newsgroup: &lt;a href="http://groups.google.com/group/microsoft.public.windows.server.scripting/browse_thread/thread/144cd7a350850e37/1dc331d47ca6c510"&gt;Redirect msh.exe in/out&lt;/a&gt;&amp;nbsp; you will find more people are struggling with this issue. &lt;br /&gt;&lt;br /&gt;So here comes the question: &lt;span style="font-weight:bold;"&gt;Should this issue been taken care of by internal host or external hosting application?&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;I think the answer is both YES and NO.&lt;br /&gt;1. &lt;b&gt;NO:&lt;/b&gt; The Design of Monad internal host is to focus on process scripting language, work with objects and piplines. External host is supposed to take care of application logic and user interface.&lt;br /&gt;2. &lt;b&gt;YES:&lt;/b&gt; legacy console application is a PROBLEM for &lt;span style="font-weight:bold;"&gt;ALL&lt;/span&gt; monad hosting application. So monad should provide more support for it.&lt;br /&gt;&lt;br /&gt;For me, a perfect solution would be that all legacy console application use PSHostUserinterface and PSHostRawUserinterface for &lt;span style="font-weight:bold;"&gt;ALL&lt;/span&gt; output/input (There are protential big problem behind this). Maybe improvement for PSHostUserinterface and PSHostRawUserinterface's definition is needed. NotifyBeginApplication() and NotifyEndApplication() is not good enough. &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114737974215835506?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114737974215835506/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/05/new-shell-new-script-language-same-old.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114737974215835506'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114737974215835506'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/05/new-shell-new-script-language-same-old.html' title='New Shell, New Script Language, Same Old Problem'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114721032183873270</id><published>2006-05-09T17:29:00.000-04:00</published><updated>2006-05-12T23:02:12.010-04:00</updated><title type='text'>PowerShell Remoting version 0.1.1.7</title><content type='html'>&lt;b&gt;What's New&lt;/b&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.gotdotnet.com/Workspaces/Workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;Version 0.1.1.7&lt;/a&gt;&lt;br /&gt;1. Recompiled for new Windows PowerShell RC1 (&lt;b&gt;Refresh version&lt;/b&gt;) &lt;br /&gt;2. Using "&lt;b&gt;Thread Pooling&lt;/b&gt;" method to schedule multiple Host threads. So Sever can potentially &lt;br /&gt;accept more connections. (Old version uses one thread per connection method). &amp;nbsp;&lt;br /&gt;3. Using a separate thread actively &lt;b&gt;reclaim resources&lt;/b&gt; from broken connection and dead host.&lt;br /&gt;4. &lt;b&gt;Clean exit&lt;/b&gt; when stop service: Disconnect all clients and dispose all running hosts.&lt;br /&gt;5. &lt;b&gt;Gracefully disconnect &lt;/b&gt;client when server reach maximum client capacity.&lt;br /&gt;6. Fix: Nested Prompt &lt;b&gt;stack error&lt;/b&gt; when multiple clients connected. &lt;br /&gt;7. Fix: Server unable to exit when &lt;b&gt;connection closed unexpectedly by client&lt;/b&gt;. &lt;br /&gt;8. Fix: "SetShouldExit" method re-throw "&lt;b&gt;SocketException&lt;/b&gt;" Error&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114721032183873270?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114721032183873270/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/05/powershell-remoting-version-0117.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114721032183873270'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114721032183873270'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/05/powershell-remoting-version-0117.html' title='PowerShell Remoting version 0.1.1.7'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114686331822560082</id><published>2006-05-05T17:06:00.000-04:00</published><updated>2006-05-07T00:49:22.686-04:00</updated><title type='text'>PowerShell Remoting version 0.1.0.317</title><content type='html'>Version 0.1.0.317&lt;br /&gt;1. NestedPrompt (suspend host)&lt;br /&gt;2. Multiple line input mode&lt;br /&gt;3. Use local UI to get login credential&lt;br /&gt;4. Save RawUI state on start, and Reset RawUI state on exit.&lt;br /&gt;5. $CurrentUser Variable (WindowsIdentity Object represent current&lt;br /&gt;   login user)&lt;br /&gt;6. Load user profile in following order&lt;br /&gt;1) "\Documents and settings\All users\PsConfiguration\profile.ps1"&lt;br /&gt;2) "\Documents and settings\All users\PsConfiguration\PowerShellRemoting_profile.ps1"&lt;br /&gt;3) "My Documents\PsConfiguration\profile.ps1"&lt;br /&gt;4) "My Documents\PsConfiguration\PowerShellRemoting_profile.ps1"&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client1.2.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client1.2.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client2.0.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client2.0.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client3.0.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client3.0.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client4.0.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client4.0.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114686331822560082?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114686331822560082/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/05/powershell-remoting-version-010317.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114686331822560082'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114686331822560082'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/05/powershell-remoting-version-010317.html' title='PowerShell Remoting version 0.1.0.317'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114645978595619960</id><published>2006-05-01T01:00:00.000-04:00</published><updated>2006-10-05T21:16:03.703-04:00</updated><title type='text'>Perfect Prompt for Windows PowerShell</title><content type='html'>&lt;b&gt;What Can Tweaking Your Prompt Do For You?&lt;/b&gt;&lt;br /&gt;&lt;br /&gt;&lt;i&gt;&lt;b&gt;Windows PowerShell&lt;/b&gt;&lt;/i&gt; have a default prompt in one color (usually gray) that tells you your current working directory. This is OK, but you can do much more with the prompt. &lt;br /&gt;1. All sorts of information can be displayed (machine name, host name, user name, time &amp;amp; date ...)&lt;br /&gt;2. The prompt can use colors&lt;br /&gt;3. You can also manipulate the windows title to dispaly more information. &lt;br /&gt;4. Other RawUI operation is allowed (move cursor)&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Why Bother?&lt;/b&gt;&lt;br /&gt;&lt;br /&gt;Beyond looking cool, it's often useful to keep track of system information. &lt;br /&gt;1. Get your current working directory (how many files in current directory)&lt;br /&gt;2. Current system time, how many process is running&lt;br /&gt;2. If you use my &lt;a href="http://mshforfun.blogspot.com/2006/01/dreaming-of-su-in-msh.html"&gt;su.msh&lt;/a&gt;, you would like to know you current windows identity&lt;br /&gt;3. If you use my &lt;a href="http://mshforfun.blogspot.com/2006/03/powershell-remoting-beta-and-future.html"&gt;powershell remoting&lt;/a&gt;, different color helps distingish between local host and remote host.&lt;br /&gt;4. Colorizing your prompt is the ability to quickly spot the prompt when you use scroll console. &lt;br /&gt;&lt;br /&gt;&lt;b&gt;First step: Profile and prompt function&lt;/b&gt;&lt;br /&gt;&lt;br /&gt;Windows PowerShell use Profile to customize user environment. For more detail, about profile&lt;br /&gt;The Story Behind the Naming and Location of PowerShell Profiles:&lt;br /&gt;&lt;a href="http://www.leeholmes.com/blog/TheStoryBehindTheNamingAndLocationOfPowerShellProfiles.aspx"&gt;http://www.leeholmes.com/blog/TheStoryBehindTheNamingAndLocationOfPowerShellProfiles.aspx&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;1. You can have different prompt for different shell (Maybe you use makeshell.exe generated you own shell)&lt;br /&gt;2. If you have different prompt function defined in multiple profile, the last one excuted take effect&lt;br /&gt;Remember the excution order is&lt;br /&gt;&lt;blockquote&gt;&lt;OL&gt;&lt;LI&gt;"All users" profile is loaded from "&amp;lt;Installation Directory&amp;gt;\profile.ps1" &lt;br /&gt;&lt;LI&gt;"All users," host-specific profile is loaded from "&amp;lt;Installation Directory&amp;gt;\Microsoft.PowerShell_profile.ps1" &lt;br /&gt;&lt;LI&gt;Current user profile is loaded from "&amp;lt;My Documents&amp;gt;\WindowsPowerShell\profile.ps1" &lt;br /&gt;&lt;LI&gt;Current User, host-specific profile is loaded from "&amp;lt;My Documents&amp;gt;\WindowsPowerShell\Microsoft.PowerShell_profile.ps1"&lt;/LI&gt;&lt;/OL&gt;&lt;br /&gt;&lt;/blockquote&gt;&lt;font color="red"&gt;Edit 09-29-2006&lt;BR&gt;&lt;br /&gt;Windows PowerShell RC2 changed profile location to &lt;br /&gt;&lt;BR&gt;&amp;lt;My documents&amp;gt;\WindowsPowerShell&lt;/font&gt;&lt;br /&gt;Now you can customize you prompt in you profile (say &amp;lt;my document&amp;gt;\psconfigurtion\profile.ps1)&lt;br /&gt;this is typical prompt function looks like:&lt;br /&gt;&lt;blockquote&gt;function prompt&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; "PS " + $(get-location) + "&amp;gt; "&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;You can do whatever you want in prompt function. But remember &lt;br /&gt;1) Always return a [string], otherwise Windows PowerShell will use default "PS&amp;gt; " prompt. &lt;br /&gt;2) Try to limit your prompt in one (short) line &lt;br /&gt;3) Host will evaluate prompt frequently, so don't do crazy stuff to slow down your work.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Colorized prompt&lt;/b&gt;&lt;br /&gt;&lt;blockquote&gt;function prompt&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Write-Host ("PS " + $(get-location) +"&amp;gt;") -nonewline -foregroundcolor Magenta&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return " "&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;Random color&lt;/b&gt;&lt;br /&gt;&lt;blockquote&gt;function prompt&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $random = new-object random&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $color=[System.ConsoleColor]$random.next(1,16)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Write-Host ("PS " + $(get-location) +"&amp;gt;") -nonewline -foregroundcolor $color&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return " "&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;Cursor Movement&lt;/b&gt;&lt;br /&gt;Display current&amp;nbsp; time at the end of prompt line (this will mess up you console buffer)&lt;br /&gt;&lt;blockquote&gt;function prompt&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $oldposition = $host.ui.rawui.CursorPosition&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Endline = $oldposition&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Endline.X+=60&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $host.ui.rawui.CursorPosition = $Endline&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Write-Host $(get-date).Tostring("yyyy-MM-dd HH:mm:ss")&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $host.ui.rawui.CursorPosition = $oldposition&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Write-Host ("PS " + $(get-location) +"&amp;gt;") -nonewline -foregroundcolor Magenta &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return " "&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;Use Window Title&lt;/b&gt;&lt;br /&gt;Show current user, host, current line number&lt;br /&gt;&lt;blockquote&gt;$global:CurrentUser = [System.Security.Principal.WindowsIdentity]::GetCurrent()&lt;br /&gt;function prompt&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $host.ui.rawui.WindowTitle = $CurrentUser.Name + " " + $Host.Name + " " + $Host.Version + " Line: " + $host.UI.RawUI.CursorPosition.Y&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Write-Host ("PS " + $(get-location) +"&amp;gt;") -nonewline -foregroundcolor Magenta &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return " "&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;Make some noise&lt;/b&gt;&lt;br /&gt;if your command&amp;nbsp; take very long time to run, beep when it is done.&lt;br /&gt;&lt;blockquote&gt;function prompt&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Write-Host ("PS " + $(get-location) +"&amp;gt;") -nonewline -foregroundcolor Magenta &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return "`a "&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;More information&lt;/b&gt;&lt;br /&gt;Count number of files(or items) in current path and number of process running &lt;br /&gt;&lt;blockquote&gt;function prompt&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $host.ui.rawui.WindowTitle = "Files: " + (get-childitem).count + " Process: " + (get-process).count&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Write-Host ("PS " + $(get-location) +"&amp;gt;") -nonewline -foregroundcolor Magenta &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return " "&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;Something for readers:&lt;/b&gt;&lt;br /&gt;1. laptop battery is low ! (&lt;Font color=red&gt;Edit 2006-07-21: Already done by &lt;a href="http://pcmusings.spaces.msn.com/Blog/cns!42B71883C19FDDAE!294.entry"&gt;Musings of a PC&lt;/a&gt;&lt;/font&gt;)&lt;br /&gt;2. You got new mail !&lt;br /&gt;3. LAN cable disconnected !&lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;br /&gt;Reference:&lt;br /&gt;&lt;a href="http://www.tldp.org/HOWTO/Bash-Prompt-HOWTO/"&gt;http://www.tldp.org/HOWTO/Bash-Prompt-HOWTO/&lt;/a&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/powershell" rel="tag"&gt;powershell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114645978595619960?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114645978595619960/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/05/perfect-prompt-for-windows-powershell.html#comment-form' title='21 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114645978595619960'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114645978595619960'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/05/perfect-prompt-for-windows-powershell.html' title='Perfect Prompt for Windows PowerShell'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>21</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114606614909177044</id><published>2006-04-26T11:36:00.000-04:00</published><updated>2006-04-28T22:51:39.986-04:00</updated><title type='text'>PowerShell, Change ... is Good ... but Painful</title><content type='html'>"&lt;i&gt;&lt;b&gt;Monad&lt;/b&gt;&lt;/i&gt;" has evolved into "&lt;i&gt;&lt;b&gt;Windows PowerShell&lt;/b&gt;&lt;/i&gt;”. Don’t tell me your feeling about this name. That’s one of the problems working on a pre-release product. Just to make you fell better, it means we are really close to final release.&lt;p&gt;There is a bunch of improvement for console user:&lt;p&gt;1.&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Tab completion gets better now. &lt;p&gt;Did anyone know where is the API mentioned in release note: &lt;i&gt;We added support for parameters and variables tab completion. This was done by having the host call a PowerShell function TabExpansion that takes two parameters – the line being entered and the last token on that line&lt;/i&gt;.&lt;p&gt;2. Some cmdlet Parameters alias changed  &lt;p&gt;For example: *-Process Changed -ProcessName to -Name alias -ProcessName, add alias ProcessId to –Id &lt;p&gt;This makes me feel much better when working with *-process cmdlet.&lt;p&gt;&lt;b&gt;Here comes the pain:&lt;/b&gt;&lt;/p&gt;  &lt;p&gt;1.&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Change your old script file extention: *.msh - &amp;gt; *.ps1&lt;p&gt;2.&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Check into individual script (especially you profile.msh) see if you use any old cmdlet names: for example, combine-path -&amp;gt; join-path&lt;p &gt;3.&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Change you %my documents%\msh\profile.msh to %my documents%\PSconfiguration\profile.ps1 &lt;p&gt; &lt;p&gt;&lt;b&gt;If you previously wrote some cmdlets or hosting application, you are going to deal with some mess here:&lt;/b&gt;&lt;P&gt;1. Be careful about name changes:&lt;p&gt;CmdletAttribute &lt;br /&gt;VerbNounCommand &lt;br /&gt;&lt;br /&gt;MshHostRawUserInterface &lt;br /&gt;PSHostRawUserInterface &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;MshCredential &lt;br /&gt;PSCredential &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;MshCredentialTypes &lt;br /&gt;PSCredentialTypes &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;MshCredentialUIOptions &lt;br /&gt;PSCredentialUIOptions &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;MshInvalidCastException &lt;br /&gt;PSInvalidCastException &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Some hidden changes: &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;FieldDescription.AssemblyFullName &lt;br /&gt;FieldDescription.ParameterAssemblyFullName &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;FieldDescription.TypeFullName &lt;br /&gt;FieldDescription.ParameterTypeFullName &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;FieldDescription.TypeName &lt;br /&gt;FieldDescription.ParameterTypeName &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;BufferCell.Type &lt;br /&gt;BufferCell.BufferCellType &lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;b&gt;If you are using my “Monad Remoting”&lt;/b&gt;&lt;p&gt;&lt;font color="#ff0000"&gt;&lt;b&gt;Uninstall “Monad Remoting” before upgrade to “PowerShell”&lt;/b&gt;&lt;/font&gt;&lt;br /&gt;You’ve been warned!&lt;/p&gt;    &lt;p&gt;To use “&lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;PowerShell Remoting&lt;/a&gt;”, you have to change you client script.&lt;br /&gt;To build your own client, be careful about name change. &lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client.3.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client.3.jpg" border="0" alt="" /&gt;&lt;/a&gt; &lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114606614909177044?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114606614909177044/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/04/powershell-change-is-good-but-painful.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114606614909177044'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114606614909177044'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/04/powershell-change-is-good-but-painful.html' title='PowerShell, Change ... is Good ... but Painful'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114592689109566856</id><published>2006-04-24T20:52:00.000-04:00</published><updated>2006-05-05T11:05:14.696-04:00</updated><title type='text'>Build Your Own Client for Monad Remoting</title><content type='html'>New version of Monad Remoting with a client class library suitable for building you own client. Available at &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;MSH For Fun Workspace at gotdotnet&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;B&gt;&lt;font color="red"&gt;Uninstall your old Server before upgrade!&lt;/font&gt;&lt;/B&gt;&lt;br /&gt;&lt;br /&gt;My DELL laptop was down again. This time, it was hard drive. I lost two weeks' work. (Ouch! If anyone want to donate a hard drive to me for backup, please contact me. Hehe. ) But I am not giving up. After one month's hard work, I was able to present you the new version of Monad Remoting. &lt;br /&gt;&lt;br /&gt;We have a better server: more compatible with ConsoleHost and many bug fixed. But most dramatic changes were made at client side. Now you can build your own cleint application using client class library :&lt;br /&gt;&lt;br /&gt;1. To build your own client, you need to initialize an instance of &lt;b&gt;ClientMshHost&lt;/b&gt; (Add reference &lt;b&gt;MonadRemoting.ClientMshHost.dll,&lt;/b&gt; namespace &lt;b&gt;MonadRemoting&lt;/b&gt;), which served as &lt;b&gt;&lt;font color="#ff0000"&gt;proxy&lt;/font&gt;&lt;/b&gt; between Monad Remoting server user interface (&lt;b&gt;remote UI&lt;/b&gt;) and Local userinterface (&lt;b&gt;Local UI&lt;/b&gt;). Although with similar public properties, this "Host" is not derived from MshHost thus can not be used to open a runspace. &lt;br /&gt;&lt;br /&gt;2. ClientMshHost has only two public method &lt;b&gt;Start()&lt;/b&gt; (to connect server and run) and &lt;B&gt;SetShouldExit(int)&lt;/b&gt; (to force client to quit) . Let ClientMshHost do all the hard work: connect to server, authenticate &amp;amp; encrypt, open runspace and run script. Whenever a user interface API was invoked at Server, parameters were sent to ClientMshHost. ClientMshHost will invoke same user interface API at Local UI: display information or get user input, return data back to server. ClientMshHost tries not to throw any exceptions, instead it use Local UI to display all server error and local error.&lt;br /&gt;&lt;br /&gt;3. The constructor of ClientMshHost requires a &lt;b&gt;IPEndPoint &lt;/b&gt;(to connect Remote UI) and a &lt;b&gt;MshHostUserinterface&lt;/b&gt; (to connect LocalUI).&lt;br /&gt;&lt;blockquote&gt;public ClientMshHost(IPEndPoint host, MshHostUserInterface UI){}&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;MshHostRawUserinterface&lt;/b&gt; within MshHostUserinterface is NOT mandatory but is supported by ClientMshHost. Minimum requirement is to implement a MshHostUserinterface which overridden&lt;br /&gt;&lt;blockquote&gt;public abstract string ReadLine();&lt;br /&gt;public abstract SecureString ReadLineAsSecureString();&lt;br /&gt;public abstract void Write(string value);&lt;br /&gt;public abstract void Write(ConsoleColor foregroundColor, ConsoleColor backgroundColor, string value);&lt;br /&gt;public abstract void WriteDebugLine(string message);&lt;br /&gt;public abstract void WriteErrorLine(string value);&lt;br /&gt;public virtual void WriteLine();&lt;br /&gt;public abstract void WriteLine(string value);&lt;br /&gt;public virtual void WriteLine(ConsoleColor foregroundColor, ConsoleColor backgroundColor, string value);&lt;br /&gt;public abstract void WriteVerboseLine(string message);&lt;br /&gt;public abstract void WriteWarningLine(string message);&lt;br /&gt;&lt;/blockquote&gt;Note: To simplify server and client implementation, following API in local UI were ignored (instead normal Read/Write API will be invoked):&lt;br /&gt;&lt;blockquote&gt;public abstract Dictionary&amp;lt;string, MshObject&amp;gt; Prompt(string caption, string message, Collection&amp;lt;FieldDescription&amp;gt; descriptions);&lt;br /&gt;public abstract int PromptForChoice(string caption, string message, Collection&amp;lt;ChoiceDescription&amp;gt; choices, int defaultChoice);&lt;br /&gt;public abstract MshCredential PromptForCredential(string caption, string message, string userName, string targetName);&lt;br /&gt;public abstract MshCredential PromptForCredential(string caption, string message, string userName, string targetName, MshCredentialTypes allowedCredentialTypes, MshCredentialUIOptions options);&lt;br /&gt;&lt;/blockquote&gt; There are great advantages of this design: &lt;br /&gt;1. There is no need to implement my own console client. &lt;font color="#ff0000"&gt;Don't invent wheels! &lt;/font&gt;Msh.exe already exposed a great MshHostUserinterface (ConsoleHostUserInterface) as &lt;b&gt;$host.UI&lt;/b&gt; variable. So just run a simple script, we are able to "steal" ConsoleHostUserInterface for remoting (Or I should say,unleash the power of $host.UI). I already add following script into my profile.msh.&lt;br /&gt;&lt;blockquote&gt;function start-remotehost {&lt;br /&gt;Param ([string] $IPAddress = "127.0.0.1", [int] $Port = 8080)&lt;br /&gt;&lt;br /&gt;# Make sure you change path to where you saved MonadRemoting.ClientMshHost.dll &lt;br /&gt;[void][System.Reflection.Assembly]::LoadFile("D:\msh\MonadRemoting.ClientMshHost.dll")&lt;br /&gt;&lt;br /&gt;&amp;nbsp;$RemoteIP = [System.Net.IPAddress]::Parse($IPAddress)&lt;br /&gt;&amp;nbsp;$RemoteEP = new-object&amp;nbsp; System.Net.IPEndPoint ($RemoteIP, $Port)&lt;br /&gt;&amp;nbsp;$RemotingClient = new-object&lt;br /&gt;&amp;nbsp;MonadRemoting.ClientMshHost($RemoteEP,$host.ui)&lt;br /&gt;&amp;nbsp;$RemotingClient.Start()&lt;br /&gt;&amp;nbsp;$RemotingClient = $null&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;2. We enjoy all the benefits of &lt;b&gt;ConsoleHostUserInterface&lt;/b&gt; and whenever Monad was upgraded, our Monad Remoting local UI was automatically upgraded. Actually, because it use 100% naive msh.exe UI, it is difficult to find out you are in local shell or remote shell. You can always invoke&lt;blockquote&gt;$host&lt;br /&gt;&lt;/blockquote&gt;If you saw ConsoleHost, you were in &lt;b&gt;local shell&lt;/b&gt;&lt;br /&gt;&lt;blockquote&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : ConsoleHost&lt;br /&gt;Version&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 1.0.7487.0&lt;br /&gt;InstanceId&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : ae801745-7671-4a46-9501-6f120bae8a81&lt;br /&gt;UI&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : System.Management.Automation.Internal.Host.InternalHostUserI&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; nterface&lt;br /&gt;...&lt;br /&gt;&lt;/blockquote&gt;If you saw ServerMshHost, you were in &lt;b&gt;remote shell&lt;/b&gt;.&lt;br /&gt;&lt;blockquote&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : ServerMshHost&lt;br /&gt;Version&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 0.1.0.283&lt;br /&gt;InstanceId&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 84574e63-2b39-4438-b8cc-bb13bd7af932&lt;br /&gt;UI&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : System.Management.Automation.Internal.Host.InternalHostUserI&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; nterface&lt;br /&gt;...&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client.0.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client.0.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;3. You will never leave you msh.exe console window and start another program for remote access. You can call start-remoteHost to gain remote access within msh.exe. When you are done, type &lt;blockquote&gt;exit&lt;/blockquote&gt; and return to your local shell.  You want connect to Remote host again? Just call start-remoteHost again. Actually, I am now using this client as a &lt;B&gt;&lt;font color="red"&gt;in-process su command&lt;/font&gt;&lt;/B&gt;. I was thinking of building this client as a &lt;B&gt;MshSnapin&lt;/B&gt; someday. &lt;br /&gt;&lt;br /&gt;4. The ClientMshHost dose not care what kind of outter application it is in. It works for console application like msh.exe, also works for Winform base GUI application like &lt;a href="http://www.karlprosser.com/coder/?page_id=14"&gt;Karl Prosser's Msh Analyzer&lt;/a&gt;. Hopefully, soon I can use Msh analyzer as my Monad remoting client (Its Rich UI is really cool)&lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114592689109566856?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114592689109566856/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/04/build-your-own-client-for-monad.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114592689109566856'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114592689109566856'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/04/build-your-own-client-for-monad.html' title='Build Your Own Client for Monad Remoting'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114455926987543692</id><published>2006-04-09T01:03:00.000-04:00</published><updated>2006-05-05T11:05:37.240-04:00</updated><title type='text'>MshObject, the Magic Therein</title><content type='html'>From &lt;a href="http://blogs.msdn.com/arulk/default.aspx"&gt;Arul Kumaravel's WebLog&lt;/a&gt;: "Monad is the only scripting platform that provides access to .Net, WMI, COM in a well-integrated manner."&lt;br /&gt;&lt;br /&gt;How? It is MshObject which does all the tricks. MshObject serve as an adapter to  .Net, WMI and COM objects. For more details, read &lt;a href="http://windowssdk.msdn.microsoft.com/library/en-us/monad_prog/html/ced30e23-10af-4700-8933-49873bd84d58.asp?frame=true#mshobjectconcepts"&gt;MSH Object Concepts.&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Here are members of System.Management.Automation.MshObject:&lt;br /&gt;&lt;blockquote&gt;public class MshObject : IFormattable&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // Methods&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; static MshObject();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public MshObject();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public MshObject(object obj);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public static MshObject AsMshObject(object obj);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public virtual MshObject Copy();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string ToString();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string ToString(string format, IFormatProvider formatProvider);&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // Properties&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public object BaseObject { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public object ImmediateBaseObject { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public MshMemberInfoCollection Members { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public MshMemberInfoCollection Methods { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public MshMemberInfoCollection Properties { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public Collection&amp;lt;string&amp;gt; TypeNames { get; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;MshObject is hidden under the surface of Msh. You might not notice its exsitance unless you write a cmdlet which deal with MshObject directly. I&amp;nbsp; prevously working on  Serialization of MshObject in my &lt;a href="http://mshforfun.blogspot.com/2006/03/monad-remoting-beta-and-future.html"&gt;Monad Remoting project&lt;/a&gt;. I wrote a small cmdlet to track Mshobject within MSH.exe&lt;br /&gt;&lt;blockquote&gt;using System;&lt;br /&gt;using System.Collections.Generic;&lt;br /&gt;using System.Text;&lt;br /&gt;using System.Management.Automation;&lt;br /&gt;&lt;br /&gt;namespace MshCx&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Cmdlet("get", "mshobject")]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public class GetMshobject: Cmdlet&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private MshObject[] inputObjects = null;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Mandatory = false,ValueFromPipeline = true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public MshObject[] InputObjects&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return inputObjects; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { inputObjects = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; protected override void ProcessRecord()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (inputObjects != null)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; StringBuilder sb = new StringBuilder();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; foreach (MshObject Item in inputObjects)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine("MshObject: ");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine("\t" + Item.ToString());&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine("BaseObject: ");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine("\t"+ Item.BaseObject.ToString() + " (" + Item.BaseObject.GetType().FullName + ")");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine("ImmediateBaseObject: ");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine("\t" + Item.ImmediateBaseObject.ToString() + " (" + Item.ImmediateBaseObject.GetType().FullName + ")");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine("TypeNames: ");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; foreach (string Type in Item.TypeNames)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine("\t"+ Type);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; sb.AppendLine("=============================================================");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteObject(sb.ToString());&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;It is really intersting to see how export-clixml and import-clixml works:&lt;br /&gt;&lt;blockquote&gt;&amp;gt; $file= (get-childitem)[0]&lt;br /&gt;&amp;gt; $file &lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Directory: Microsoft.Management.Automation.Core\FileSystem::D:\msh&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Mode&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; LastWriteTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Length Name&lt;br /&gt;----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; -------------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ------ ----&lt;br /&gt;-a---&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 2006-4-3&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 22:27&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 350 1.txt&lt;br /&gt;&lt;br /&gt;&amp;gt; $file | get-member&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp; TypeName: System.IO.FileInfo&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; MemberType&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Definition&lt;br /&gt;----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ----------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ----------&lt;br /&gt;AppendText&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.StreamWriter AppendText()&lt;br /&gt;CopyTo&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileInfo CopyTo(String de...&lt;br /&gt;Create&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileStream Create()&lt;br /&gt;CreateObjRef&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Runtime.Remoting.ObjRef Crea...&lt;br /&gt;CreateText&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.StreamWriter CreateText()&lt;br /&gt;Decrypt&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void Decrypt()&lt;br /&gt;Delete&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void Delete()&lt;br /&gt;Encrypt&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void Encrypt()&lt;br /&gt;Equals&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean Equals(Object obj)&lt;br /&gt;get_Attributes&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileAttributes get_Attrib...&lt;br /&gt;get_CreationTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime get_CreationTime()&lt;br /&gt;get_CreationTimeUtc&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime get_CreationTimeUtc()&lt;br /&gt;get_Directory&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.DirectoryInfo get_Directo...&lt;br /&gt;get_DirectoryName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String get_DirectoryName()&lt;br /&gt;get_Exists&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean get_Exists()&lt;br /&gt;get_Extension&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String get_Extension()&lt;br /&gt;get_FullName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String get_FullName()&lt;br /&gt;get_IsReadOnly&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean get_IsReadOnly()&lt;br /&gt;get_LastAccessTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime get_LastAccessTime()&lt;br /&gt;get_LastAccessTimeUtc&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime get_LastAccessTimeU...&lt;br /&gt;get_LastWriteTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime get_LastWriteTime()&lt;br /&gt;get_LastWriteTimeUtc&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime get_LastWriteTimeUtc()&lt;br /&gt;get_Length&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int64 get_Length()&lt;br /&gt;get_Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String get_Name()&lt;br /&gt;GetAccessControl&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Security.AccessControl.FileS...&lt;br /&gt;GetHashCode&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int32 GetHashCode()&lt;br /&gt;GetLifetimeService&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Object GetLifetimeService()&lt;br /&gt;GetObjectData&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void GetObjectData(Serializa...&lt;br /&gt;GetType&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Type GetType()&lt;br /&gt;InitializeLifetimeService Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Object InitializeLifetimeSer...&lt;br /&gt;MoveTo&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void MoveTo(String destFileN...&lt;br /&gt;Open&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileStream Open(FileMode ...&lt;br /&gt;OpenRead&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileStream OpenRead()&lt;br /&gt;OpenText&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.StreamReader OpenText()&lt;br /&gt;OpenWrite&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileStream OpenWrite()&lt;br /&gt;Refresh&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void Refresh()&lt;br /&gt;Replace&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileInfo Replace(String d...&lt;br /&gt;set_Attributes&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_Attributes(FileAttr...&lt;br /&gt;set_CreationTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_CreationTime(DateTi...&lt;br /&gt;set_CreationTimeUtc&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_CreationTimeUtc(Dat...&lt;br /&gt;set_IsReadOnly&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_IsReadOnly(Boolean ...&lt;br /&gt;set_LastAccessTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_LastAccessTime(Date...&lt;br /&gt;set_LastAccessTimeUtc&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_LastAccessTimeUtc(D...&lt;br /&gt;set_LastWriteTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_LastWriteTime(DateT...&lt;br /&gt;set_LastWriteTimeUtc&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_LastWriteTimeUtc(Da...&lt;br /&gt;SetAccessControl&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void SetAccessControl(FileSe...&lt;br /&gt;ToString&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String ToString()&lt;br /&gt;MshChildName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty&amp;nbsp;&amp;nbsp; System.String MshChildName=1.txt&lt;br /&gt;MshDrive&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty&amp;nbsp;&amp;nbsp; System.Management.Automation.DriveI...&lt;br /&gt;MshIsContainer&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty&amp;nbsp;&amp;nbsp; System.Boolean MshIsContainer=False&lt;br /&gt;MshParentPath&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty&amp;nbsp;&amp;nbsp; System.String MshParentPath=Microso...&lt;br /&gt;MshPath&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty&amp;nbsp;&amp;nbsp; System.String MshPath=Microsoft.Man...&lt;br /&gt;MshProvider&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty&amp;nbsp;&amp;nbsp; System.Management.Automation.Provid...&lt;br /&gt;Attributes&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileAttributes Attributes...&lt;br /&gt;CreationTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime CreationTime {get;s...&lt;br /&gt;CreationTimeUtc&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime CreationTimeUtc {ge...&lt;br /&gt;Directory&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.DirectoryInfo Directory {...&lt;br /&gt;DirectoryName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String DirectoryName {get;}&lt;br /&gt;Exists&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean Exists {get;}&lt;br /&gt;Extension&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String Extension {get;}&lt;br /&gt;FullName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String FullName {get;}&lt;br /&gt;IsReadOnly&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean IsReadOnly {get;set;}&lt;br /&gt;LastAccessTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime LastAccessTime {get...&lt;br /&gt;LastAccessTimeUtc&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime LastAccessTimeUtc {...&lt;br /&gt;LastWriteTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime LastWriteTime {get;...&lt;br /&gt;LastWriteTimeUtc&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime LastWriteTimeUtc {g...&lt;br /&gt;Length&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int64 Length {get;}&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String Name {get;}&lt;br /&gt;Mode&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ScriptProperty System.Object Mode {get=$catr = "";&lt;br /&gt;&amp;gt; $file | get-mshobject&lt;br /&gt;&lt;br /&gt;MshObject:&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 1.txt&lt;br /&gt;BaseObject:&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 1.txt (System.IO.FileInfo)&lt;br /&gt;ImmediateBaseObject:&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 1.txt (System.IO.FileInfo)&lt;br /&gt;TypeNames:&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileInfo&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.IO.FileSystemInfo&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.MarshalByRefObject&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Object&lt;br /&gt;=============================================================&lt;br /&gt;&amp;gt; $file |export-clixml abc.xml&lt;br /&gt;&lt;br /&gt;&amp;gt; $file = import-clixml abc.xml&lt;br /&gt;&amp;gt; $file&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Directory: Microsoft.Management.Automation.Core\FileSystem::D:\msh&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Mode&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; LastWriteTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Length Name&lt;br /&gt;----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; -------------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ------ ----&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 2006-4-3&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 22:27&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 350 1.txt&lt;br /&gt;&lt;br /&gt;&amp;gt; $file | get-member&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp; TypeName: Deserialized.System.IO.FileInfo&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; MemberType&amp;nbsp;&amp;nbsp; Definition&lt;br /&gt;----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ----------&amp;nbsp;&amp;nbsp; ----------&lt;br /&gt;MshChildName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty System.String MshChildName=1.txt&lt;br /&gt;MshDrive&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty System.Management.Automation.MshObject MshDri...&lt;br /&gt;MshIsContainer&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty System.Boolean MshIsContainer=False&lt;br /&gt;MshParentPath&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty System.String MshParentPath=Microsoft.Managem...&lt;br /&gt;MshPath&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty System.String MshPath=Microsoft.Management.Au...&lt;br /&gt;MshProvider&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty System.Management.Automation.MshObject MshPro...&lt;br /&gt;Attributes&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String {get;set;}&lt;br /&gt;CreationTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime {get;set;}&lt;br /&gt;CreationTimeUtc&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime {get;set;}&lt;br /&gt;Directory&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String {get;set;}&lt;br /&gt;DirectoryName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String {get;set;}&lt;br /&gt;Exists&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean {get;set;}&lt;br /&gt;Extension&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String {get;set;}&lt;br /&gt;FullName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String {get;set;}&lt;br /&gt;IsReadOnly&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean {get;set;}&lt;br /&gt;LastAccessTime&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime {get;set;}&lt;br /&gt;LastAccessTimeUtc Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime {get;set;}&lt;br /&gt;LastWriteTime&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime {get;set;}&lt;br /&gt;LastWriteTimeUtc&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.DateTime {get;set;}&lt;br /&gt;Length&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int64 {get;set;}&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String {get;set;}&lt;br /&gt;&lt;br /&gt;&amp;gt; $file | get-mshobject&lt;br /&gt;&lt;br /&gt;MshObject:&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; @{MshPath=Microsoft.Management.Automation.Core\FileSystem::D:\msh\1.txt;&lt;br /&gt;&amp;nbsp;MshPa&lt;br /&gt;rentPath=Microsoft.Management.Automation.Core\FileSystem::D:\msh; MshChildName=&lt;br /&gt;1.txt; MshDrive=; MshProvider=; MshIsContainer=False; Name=1.txt; Length=350; D&lt;br /&gt;irectoryName=D:\msh; Directory=D:\msh; IsReadOnly=False; Exists=True; FullName=&lt;br /&gt;D:\msh\1.txt; Extension=.txt; CreationTime=2006-4-3 22:27:16; CreationTimeUtc=2&lt;br /&gt;006-4-4 2:27:16; LastAccessTime=2006-4-3 22:27:16; LastAccessTimeUtc=2006-4-4 2&lt;br /&gt;:27:16; LastWriteTime=2006-4-3 22:27:16; LastWriteTimeUtc=2006-4-4 2:27:16; Att&lt;br /&gt;ributes=Archive}&lt;br /&gt;BaseObject:&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; (System.Management.Automation.MshCustomObject)&lt;br /&gt;ImmediateBaseObject:&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; (System.Management.Automation.MshCustomObject)&lt;br /&gt;TypeNames:&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Deserialized.System.IO.FileInfo&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Deserialized.System.IO.FileSystemInfo&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Deserialized.System.MarshalByRefObject&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Deserialized.System.Object&lt;br /&gt;=============================================================&lt;br /&gt;&lt;br /&gt;&lt;/blockquote&gt;If you look carefully, you will notice:&lt;br /&gt;1. export-clixml write &lt;b&gt;MshObject.Properties&lt;/b&gt; into a xml file and import-clixml reconstruct a MshObject.&lt;br /&gt;2. Although they looks the same, something changed&amp;nbsp; after serializtion and deserializtion:&lt;br /&gt;Before: A &lt;b&gt;FileInfo&lt;/b&gt; object is wrapped within MshObject&lt;br /&gt;After:&amp;nbsp;&amp;nbsp;&amp;nbsp; A &lt;b&gt;MshCustomObject&lt;/b&gt; is wrapped within MshObject. All &lt;b&gt;Methods are lost&lt;/b&gt;. &lt;br /&gt;3. Deserialized &lt;b&gt;MshCustomObject&lt;/b&gt; is a Hash table.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Have Fun.&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114455926987543692?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114455926987543692/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/04/mshobject-magic-therein.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114455926987543692'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114455926987543692'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/04/mshobject-magic-therein.html' title='MshObject, the Magic Therein'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114383256894350753</id><published>2006-03-31T14:14:00.000-05:00</published><updated>2006-06-30T10:30:55.793-04:00</updated><title type='text'>PowerShell Remoting - Beta and future</title><content type='html'>Release of &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea" target="_blank"&gt;"PowerShell Remoting", 0.2.7.1 Beta version&lt;/a&gt;.&lt;br /&gt;Version 0.2.7.1&lt;br /&gt;&lt;OL&gt;&lt;br /&gt;&lt;LI&gt;New GUI client manager: Save/delete server information &amp; connection option, generate connection script automatically, launch powershell remoting client directly.&lt;br /&gt;&lt;LI&gt;Add option to reject connection if user found invalid remote X509 certificate.&lt;br /&gt;&lt;LI&gt;Bug fix: Null login credential (press Cancel in CredUI window) cause server crash &lt;br /&gt;&lt;LI&gt;Bug fix: other minor bugs&lt;/OL&gt;&lt;br /&gt;Version 0.2.6.0&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Write Server Information &amp;amp; Error to EventLog (Source: PowerShellRemoting).  Log file will no longer be used by newer version.&lt;/li&gt;&lt;br&gt;&lt;li&gt;SSL support using SSLStream.&lt;/li&gt;&lt;br&gt;&lt;font color="#ff0000"&gt;Warning: SSL is for advanced user.&lt;/font&gt; &lt;br&gt;If you want to provide SSL support to server, you should&lt;br&gt;&lt;ul&gt; &lt;br&gt;&lt;li&gt;Get X509 certificate for server. For testing purpose, you can use makecert.exe (included in .NET framework SDK) &lt;br&gt;&lt;/li&gt;&lt;li&gt;Install X509 certificate at StoreLocation: LocalMachine, StoreName: My (personal). &lt;br&gt;&lt;/li&gt;&lt;li&gt;Grand "NetworkService" account read access to X509 certificate associated private key file. &lt;br&gt;&lt;/li&gt;&lt;li&gt;Set [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PowerShellRemoting\Parameters\ X509] to thumbprint of X509 Certificate.&lt;br&gt;&lt;br&gt;There is pretty good walkthrough at &lt;a href="http://blogs.technet.com/jhoward/archive/2005/02/02/365323.aspx"&gt;John Howard's blog&lt;/a&gt;.&lt;/li&gt;&lt;/ul&gt;&lt;br&gt;&lt;li&gt;X509 Option &lt;/li&gt;&lt;br&gt;[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PowerShellRemoting\Parameters]&lt;br&gt;"X509"="0"&lt;br&gt;&lt;br&gt;&lt;li&gt;DebugHost Option (Default 0: false)&lt;/li&gt;&lt;br&gt;[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PowerShellRemoting\Parameters]&lt;br&gt;"DebugHost"=dword:00000000 &lt;br&gt;&lt;br&gt;&lt;li&gt;Bug fix: Write-Progress throw null object Exception.&lt;/li&gt;&lt;/ol&gt;&lt;span style="font-weight: bold;"&gt;Check out the help.chm in release package for details.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Version 0.2.5.1 &lt;br /&gt;1. Support Ctrl+C and Ctrl+Break to cancel current pipeline (UDP datagram, So not 100% reliable)&lt;br /&gt;2. Support Maximum Client per IP option (default 2)&lt;br /&gt;3. Customized client filter policy (%Program Files%\PowerShell Remoting\user.xml, see sample files for format information)&lt;br /&gt;   Important: default installation only allow user in Administrators group login from localhost. So you have to have your own user.xml before you can login from another IP. If user.xml file parse error occorred when start service, default policy will be loaded. Check log file or EventLog for details of parse error. &lt;br /&gt;4. $UserACL variable for current client filter policy&lt;br /&gt;5. Client is installed as PSSnapin&lt;br /&gt;6. New install/uninstall script for both server and client, new start-remotehost.ps1 script&lt;br /&gt;7. CanThrowException and CanHandleCancelKey property of client (For developer)&lt;br /&gt;8. Change Log file path to %Documents and Settings%\NetworkService\Local Settings\Application Data\PowerShellRemoting.log&lt;br /&gt;9. Change Service Name to "PowerShellRemoting"&lt;br /&gt;10. Service related Exception is also Logged to Eventlog (EventLog: Application, source: PowershellRemoting)&lt;br /&gt;11. Other Bugs fixed&lt;br /&gt;&lt;br /&gt;Version 0.1.1.7 &lt;br /&gt;1. Recompiled for new Windows PowerShell RC1 (Refresh version) &lt;br /&gt;2. Using "Thread Pooling" method to schedule multiple Host threads. So Sever can potentially accept more connections. (Old version uses one thread per connection method).  &lt;br /&gt;3. Using a separate thread actively reclaim resources from broken connection and dead host. &lt;br /&gt;4. Clean exit when stop service: Disconnect all clients and dispose all running hosts. &lt;br /&gt;5. Gracefully disconnect client when server reach maximum client capacity. &lt;br /&gt;6. Fix: Nested Prompt stack error when multiple clients connected. &lt;br /&gt;7. Fix: Server unable to exit when connection closed unexpectedly by client. &lt;br /&gt;8. Fix: "SetShouldExit" method re-throw "SocketException" Error &lt;br /&gt;&lt;br /&gt;Version 0.1.0.318&lt;br /&gt;1. Fix "All User" profile Path &lt;br /&gt;1) "\Documents and settings\All users\Documents\PsConfiguration\profile.ps1" &lt;br /&gt;2) "\Documents and settings\All users\Documents\PsConfiguration\PowerShellRemoting_profile.ps1" &lt;br /&gt;&lt;br /&gt;Version 0.1.0.317&lt;br /&gt;1. NestedPrompt (suspend host)&lt;br /&gt;2. Multiple line input mode&lt;br /&gt;3. Use local UI to get login credential&lt;br /&gt;4. Save RawUI state on start, and Reset RawUI state on exit.&lt;br /&gt;5. $CurrentUser Variable (WindowsIdentity Object represent current&lt;br /&gt;   login user)&lt;br /&gt;6. Load user profile in following order&lt;br /&gt;1) "\Documents and settings\All users\PsConfiguration\profile.ps1"&lt;br /&gt;2) "\Documents and settings\All users\PsConfiguration\PowerShellRemoting_profile.ps1"&lt;br /&gt;3) "My Documents\PsConfiguration\profile.ps1"&lt;br /&gt;4) "My Documents\PsConfiguration\PowerShellRemoting_profile.ps1"&lt;br /&gt;&lt;br /&gt;Version 0.1.0.311&lt;br /&gt;1. Solve Server cause CPU overload problem&lt;br /&gt;2. Solve Port or MaxClient change not take effect problem&lt;br /&gt;3. Except for PSHostUserInterface.Prompt, all other UI/RawUI &lt;br /&gt;   API were connect to local UI/RawUI API&lt;br /&gt;4. improved Client exception report &lt;br /&gt;&lt;br /&gt;Version 0.1.0.301&lt;br /&gt;1. Recompile for new Windows PowerShell RC1&lt;br /&gt;2. Client class libary to build your own client&lt;br /&gt;3. Console client use naive PowerShell.exe user interface&lt;br /&gt;4. Support for all RawUI API &lt;br /&gt;5. Bug fix for server&lt;br /&gt;&lt;br /&gt;Version 0.1.0.128&lt;br /&gt;1. Multiple connection (Maximum 10 connection)&lt;br /&gt;2. New log file format&lt;br /&gt;3. Hide some common exception on Client&lt;br /&gt;4. Some bug fix &lt;br /&gt;&lt;br /&gt;This software is distributed under BSD license. See license.txt for details.&lt;br /&gt;&lt;br /&gt;I. What is "PowerShell Remoting"&lt;br /&gt;&lt;br /&gt;PowerShell Remoting is a light-weighted server-client application which &lt;br /&gt;provides secure remote access to Windows PowerShelll (codename Monad). &lt;br /&gt;It contains two components:&lt;br /&gt;&lt;br /&gt;Server: A Windows Service (Service Name "PowerShell Remoting") running &lt;br /&gt;under NetworkService account. It will listen at certain TCP port, accept &lt;br /&gt;income connection, authenticate client and provide PowerShell hosting &lt;br /&gt;environment.&lt;br /&gt;&lt;br /&gt;Client: A Class libary. It severs as a proxy between sever user interface &lt;br /&gt;and client user interface. It will connect to server, provide client &lt;br /&gt;credential for authentication, get user input and display results.&lt;br /&gt;&lt;br /&gt;This software is distributed under BSD license. See license.txt for &lt;br /&gt;details.&lt;br /&gt;&lt;br /&gt;II. System requirement.&lt;br /&gt;1. Microsoft .NET framework v2.0.50727 (Server &amp; Client)&lt;br /&gt;2. PowerShell RC1 or Higher (Server only)&lt;br /&gt;3. Windows XP/2003 (For server); Windows 2000/XP/2003 (For client)&lt;br /&gt;4. 256MB Memory, 1M hard drive space.&lt;br /&gt;&lt;br /&gt;III. Features&lt;br /&gt;1. Client authentication &amp; protection&lt;br /&gt;1) All communication between server and client is encrypted and signed.&lt;br /&gt;Depend on server environment, authentication method could be NTLM or &lt;br /&gt;Kerberos.&lt;br /&gt;&lt;br /&gt;2) Multipul connection from client. (default Port 8080, Maximum 10 connection)&lt;br /&gt;Can be changed by modify registry.&lt;br /&gt;&lt;br /&gt;2. Support PSHostUserInterface &amp; PSHostRawUserInterface&lt;br /&gt;1) PSHostUserInterface will be passed to constructor of client&lt;br /&gt;2) PSHostRawUserInterface is not mandatory but is supported&lt;br /&gt;&lt;br /&gt;Note : Not supported at this version&lt;br /&gt;1) Tab completion&lt;br /&gt;2) start-transcript&lt;br /&gt;&lt;br /&gt;Note. Known problems&lt;br /&gt;1) Outputs of legacy program are not redirected to client&lt;br /&gt;&lt;br /&gt;IV Installation and usage&lt;br /&gt;# Server&lt;br /&gt;1. Please use provided install.ps1 (install service) and uninstall.ps1 &lt;br /&gt;(uninstall service) to install/uninstall server component.&lt;br /&gt;&lt;br /&gt;2. Default installation, server will listen to all available IP &lt;br /&gt;(IPAddress.Any) listen at port 8080 and maximum client number is 10.&lt;br /&gt;Those can be changed by modify registry&lt;br /&gt;[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\PowerShell Remoting&lt;br /&gt;\Parameters]&lt;br /&gt;"Port"=dword:00001f90&lt;br /&gt;"MaxClient"=dword:0000000a&lt;br /&gt;&lt;br /&gt;3. Log file was "Hard Coded" to&lt;br /&gt;C:\Documents and Settings\NetworkService\PowerShellRemoting.log&lt;br /&gt;&lt;br /&gt;4. Default installed as Manual start service.  &lt;br /&gt;&lt;br /&gt;# Client&lt;br /&gt;1. Client application do not need to be installed, just copy it to client &lt;br /&gt;PC and execute "start-remotehost.ps1". (Some modification is needed)&lt;br /&gt;&lt;br /&gt;2. argument:&lt;br /&gt;start-remotehost &lt;IPAddress&gt; &lt;Port&gt;&lt;br /&gt;Where &lt;Port&gt; is IP address which server is listening &lt;br /&gt;(For example: 127.0.0.1- for localhost; 192.168.0.2, et, al.)&lt;br /&gt;Where &lt;Port&gt; is port number which server is listening &lt;br /&gt;(default 8080) &lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/achitect.0.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/achitect.0.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client1.3.jpg"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://photos1.blogger.com/blogger/5412/2034/320/client1.3.jpg" alt="" border="0"&gt;&lt;/a&gt;&lt;br /&gt;If you have any other suggestions, please drop a few lines in comment.   &lt;br /&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114383256894350753?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114383256894350753/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/powershell-remoting-beta-and-future.html#comment-form' title='7 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114383256894350753'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114383256894350753'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/powershell-remoting-beta-and-future.html' title='PowerShell Remoting - Beta and future'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>7</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114343980592519804</id><published>2006-03-27T01:05:00.000-05:00</published><updated>2006-03-27T11:03:03.810-05:00</updated><title type='text'>Monad Remoting - Windows Service</title><content type='html'>Just upload a new version of "&lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea" target="_blank"&gt;Monad Remoting&lt;/a&gt;". Now it is a windows service with a bunch of new features and recommanded for upgrading.&lt;br /&gt;&lt;br /&gt;New feature:&lt;br /&gt;1. Running as windows service under &lt;b&gt;NetworkService&lt;/b&gt; account (Service Name "Monad Remoting").&lt;br /&gt;&lt;br /&gt;2. Receiving &lt;b&gt;customized NetworkCredential&lt;/b&gt; for logon. (Yes, I mean really logon) But only accept one connection at a time. &lt;br /&gt; &lt;br /&gt;3. &lt;b&gt;&lt;font color="#ff0000"&gt;Impersonation&lt;/font&gt;&lt;/b&gt; as remote NetworkCredential. You can either login as an unprivileged user or an Administrator. Try my faverate &lt;a href="http://mshforfun.blogspot.com/2006/01/clone-of-idwhoami-in-msh.html"&gt;id.msh&lt;/a&gt; to find out your current identity. &lt;br /&gt;&lt;br /&gt;4. &lt;b&gt;Log file&lt;/b&gt; was "Hard Coded" to &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; C:\Documents and Settings\NetworkService\MonadRemoting.log&lt;br /&gt;&lt;br /&gt;5. Automatic &lt;b&gt;install service&lt;/b&gt; (install.msh) and &lt;b&gt;uninstall service&lt;/b&gt; (uninstall.msh). You 'd better install service using my install.msh because it creates required registry key.&lt;br /&gt;&lt;br /&gt;6. Default installed as  &lt;b&gt;Manual&lt;/b&gt; start service. You can change it to Automatic in MMC service snapin. You have to start service before first connection. &lt;br /&gt;&lt;blockquote&gt;Start-service "Monad Remoting"&lt;/blockquote&gt;&lt;br /&gt;7. Default listen at &lt;b&gt;port 8080&lt;/b&gt;, can be changed by modify registry&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Monad Remoting\Port]&lt;br /&gt;&lt;br /&gt;8: Default listen to &lt;b&gt;all available IP&lt;/b&gt; (IPAddress.Any)&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client1.0.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client1.0.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;Have Fun&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114343980592519804?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114343980592519804/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/monad-remoting-windows-service.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114343980592519804'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114343980592519804'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/monad-remoting-windows-service.html' title='Monad Remoting - Windows Service'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114308670712757895</id><published>2006-03-22T22:18:00.000-05:00</published><updated>2006-03-22T23:05:07.143-05:00</updated><title type='text'>Monad Remoting - Now Can Read SecureString From Remote Client</title><content type='html'>Implementation of &lt;b&gt;ReadLineAsSecureString()&lt;/b&gt; in MshHostUserInterface.&lt;br /&gt;&lt;br /&gt;Just upload a new version of "&lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea" target="_blank"&gt;Monad Remoting&lt;/a&gt;". It can read SecureString from remote client console now.&lt;br /&gt;&lt;br /&gt;SecureString will not be kept secret if you store its content in a normal string first. That is to say, we have to read it from console and store them &lt;b&gt;directly as SecureString&lt;/b&gt;. But before sent them to remote server, we have to decrypt it to byte[ ]. NegotiateStream will encrypt (decrypted) byte[ ] before write to NetworkStream. At server side, we have to get the byte[ ] and restore it to a SecureString.&lt;br /&gt;&lt;br /&gt;Although I tried to minimize exposure and clear my footprint behind me, there are still potential security problems. &lt;b&gt;So use it at your own risk&lt;/b&gt;. I post the code here, in case someone want to take a close look at those steps I mentioned here.&lt;br /&gt;&lt;blockquote&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; do&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; keyinfo = Console.ReadKey(true);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ((keyinfo.Modifiers &amp;amp; ConsoleModifiers.Alt) != 0 || (keyinfo.Modifiers &amp;amp; ConsoleModifiers.Control) != 0) continue;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (keyinfo.Key == ConsoleKey.Enter)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Console.WriteLine();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; break;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (password.Length == 512)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Console.Write("\r\nRead 512 (Maxium) Characters!");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; break;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (keyinfo.Key == ConsoleKey.Backspace)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; password.RemoveAt(password.Length - 1);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Console.Write('\b');&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Console.Write(' ');&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Console.Write('\b');&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; continue;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; password.AppendChar(keyinfo.KeyChar);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Console.Write('*');&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; while (keyinfo.Key != ConsoleKey.Enter);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (password.Length &amp;gt; 0)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Plantext = GetByteArrayFromSecurString(password);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; authStream.Write(Plantext, 0, Plantext.Length);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Array.Clear(Plantext, 0, Plantext.Length);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&lt;/blockquote&gt;At this point, you can now enjoy the get-credential, new-securestring cmdlets.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;I really wish we could have a &lt;b&gt;in-process&lt;/b&gt; &lt;b&gt;&lt;font color="#ff0000"&gt;su command&lt;/font&gt;&lt;/b&gt;, because the trick of &lt;br /&gt;&lt;blockquote&gt;[System.Diagnostics.Process]::Start()&lt;br /&gt;&lt;/blockquote&gt; will not work for remote client. Well, we have to expect that at next version of monad.&lt;br /&gt;&lt;br /&gt;Have Fun.&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114308670712757895?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114308670712757895/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/monad-remoting-now-can-read.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114308670712757895'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114308670712757895'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/monad-remoting-now-can-read.html' title='Monad Remoting - Now Can Read SecureString From Remote Client'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114305547088647959</id><published>2006-03-22T14:05:00.000-05:00</published><updated>2006-03-22T14:58:35.153-05:00</updated><title type='text'>Script to Resize Remote Client Console Window</title><content type='html'>There is an intersting msh script from &lt;a href="http://oka326.blogspot.com/" target="_blank"&gt;Web ChangeLog&lt;/a&gt; blog to demonstrate RawUI functionality of &lt;a href="http://mshforfun.blogspot.com/2006/03/monad-remoting-updated-version.html"&gt;my Monad Remoting tools&lt;/a&gt;. &lt;br /&gt;&lt;br /&gt;&lt;a href="http://oka326.blogspot.com/2006/03/msh-remote-scripting-host.html" target="_blank"&gt;MSH: Remote scripting host&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Interstingly, if you run this script in msh.exe, you will probobly get some exception. But it works fine for my Monad Remoting tools. &lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;Exception setting "WindowSize": "Window cannot be wider than the screen buffer.&lt;br /&gt;Parameter name: value.Width Actual value was 85."&lt;br /&gt;At D:\msh\script\resizewin.msh:7 char:18&lt;/blockquote&gt;&lt;br /&gt;Actually, This is a bug of my tools. I simply applied all RawUI operation directly to client console and but did not check screen buffer. &lt;br /&gt;&lt;br /&gt;Have Fun!&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114305547088647959?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114305547088647959/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/script-to-resize-remote-client-console.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114305547088647959'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114305547088647959'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/script-to-resize-remote-client-console.html' title='Script to Resize Remote Client Console Window'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114291124620943600</id><published>2006-03-20T22:12:00.000-05:00</published><updated>2006-03-21T10:52:57.530-05:00</updated><title type='text'>Monad Remoting (updated version)</title><content type='html'>Just upload a new version of Monad Remoting for testing. Download at &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea" target="_blank"&gt;gotdotnet&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Feature:&lt;br /&gt;&lt;br /&gt;# Automatic authentication &lt;br /&gt;1) Client credential is automaticly provided to server for authentication. &lt;br /&gt;2) All communication between server and client is entrypted and signed.&lt;br /&gt;&lt;br /&gt;# Basic MshHostUserInterface.&lt;br /&gt;1) Load User Profile at server when connected (new)&lt;br /&gt;2) Evaluation for Prompt function (new)&lt;br /&gt;3) Read and write from console&lt;br /&gt;4) Colorized output&lt;br /&gt;5) Prompt for undefined parameters (new)&lt;br /&gt;6) Prompt for choice (new)&lt;br /&gt;&lt;br /&gt;# Not supported at this version&lt;br /&gt;1) Read Securestring&lt;br /&gt;2) ReadKey&lt;br /&gt;&lt;br /&gt;# known problems&lt;br /&gt;1) Outputs of legacy program are not redirected to client&lt;br /&gt;&lt;br /&gt;Have Fun.&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114291124620943600?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114291124620943600/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/monad-remoting-updated-version.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114291124620943600'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114291124620943600'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/monad-remoting-updated-version.html' title='Monad Remoting (updated version)'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114264119698753355</id><published>2006-03-17T19:16:00.000-05:00</published><updated>2006-03-20T22:23:00.373-05:00</updated><title type='text'>Securely Extend Msh Host User Interface over Network</title><content type='html'>&lt;font color="red"&gt;Added at 20th Mar, 22:20&lt;/font&gt;&lt;br /&gt;There is a followup post &lt;a href="http://mshforfun.blogspot.com/2006/03/monad-remoting-updated-version.html"&gt;here&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Securely extend Msh Host User Interface over network using NegotiateStream.&lt;br /&gt;&lt;br /&gt;If you follow my previous post, you will find out that I changed my strategy. There is no need to sent Mshobjects to remote client. We just need to implement a customized MshHostUserInterface which get input and write result to remote client. Monad is designed to be extended in this way, so it only took me a couple of days to get a usable solution. You can download testing binary at &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea" target="_blank"&gt;gotdotnet&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Server&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/server.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/server.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;Client&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/client.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/client.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;The underline idea is to implement all APIs in MshHostUserInterface and MshHostRawUserInterface. It was much easier than I originally thought. But&amp;nbsp; I still had  some problems with &lt;br /&gt;&lt;blockquote&gt;public override Dictionary&lt;string, mshobject=""&gt; Prompt(string caption, string message, Collection&lt;FieldDescription&gt; descriptions)&amp;nbsp;&amp;nbsp; { }&lt;br /&gt;&lt;br /&gt;public override int PromptForChoice(string caption, string message, Collection&lt;ChoiceDescription&gt; choices, int defaultChoice) { }&lt;br /&gt;&lt;br /&gt;public override MshCredential PromptForCredential(string caption, string message, string userName, string targetName)&amp;nbsp; { }&lt;br /&gt;&lt;br /&gt;public override MshCredential PromptForCredential(string caption, string message, string userName, string targetName, MshCredentialTypes allowedCredentialTypes, MshCredentialUIOptions options)&amp;nbsp;&amp;nbsp; { }&lt;br /&gt;&lt;br /&gt;public override SecureString ReadLineAsSecureString()&amp;nbsp;&amp;nbsp; { }&lt;br /&gt;&lt;/ChoiceDescription&gt;&lt;/FieldDescription&gt;&lt;/string,&gt;&lt;/blockquote&gt;in &lt;b&gt;MshHostUserInterface&lt;/b&gt; and&lt;br /&gt;&lt;blockquote&gt;public override KeyInfo ReadKey(ReadKeyOptions options) { }&lt;br /&gt;&lt;br /&gt;public override void ScrollBufferContents(Rectangle source, Coordinates destination, Rectangle clip, BufferCell fill)&amp;nbsp;&amp;nbsp; { }&lt;br /&gt;&lt;br /&gt;public override void SetBufferContents(Coordinates origin, BufferCell[,] contents)&amp;nbsp; { }&lt;br /&gt;&lt;br /&gt;public override void SetBufferContents(Rectangle rectangle, BufferCell fill)&amp;nbsp;&amp;nbsp; { }&lt;br /&gt;&lt;/blockquote&gt;in &lt;b&gt;MshHostRawUserInterface&lt;/b&gt;.&lt;br /&gt;&lt;br /&gt;That is to say: all sercurestring-related, credential-related, scroll console-related cmdlet are not working. But it is really fun to run some test on remote machine. Try out yourself by downloading the testing binary at &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"  target="_blank"&gt;gotdotnet&lt;/a&gt;. &lt;br /&gt;&lt;br /&gt;Monad Rocks!&lt;br /&gt;&lt;br /&gt;Have Fun!&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114264119698753355?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114264119698753355/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/securely-extend-msh-host-user.html#comment-form' title='5 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114264119698753355'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114264119698753355'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/securely-extend-msh-host-user.html' title='Securely Extend Msh Host User Interface over Network'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>5</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114236943207686439</id><published>2006-03-14T15:24:00.000-05:00</published><updated>2006-03-15T10:54:22.036-05:00</updated><title type='text'>Separation of Monad Engine and User Interface</title><content type='html'>Research on &lt;b&gt;MshHost&lt;/b&gt; &amp;amp; &lt;b&gt;MshHostUserInterface&lt;/b&gt; abstract class.&lt;br /&gt;&lt;br /&gt;The &lt;b&gt;msh.exe&lt;/b&gt; is actully a console program hosting monad engine. In another word: monad engine does not worry about user interface, it is host environment's job.&amp;nbsp; My &lt;a href="http://mshforfun.blogspot.com/2006/03/securely-extend-monad-pipline-over_13.html"&gt;Remote MSH server&lt;/a&gt; is not INTERACTIVE (For example: remote user will not be prompted to input credentials when invoking "get-credential" at server) because I use &lt;b&gt;DefaultHost&lt;/b&gt; which does not Implement &lt;b&gt;MshHostUserInterface&lt;/b&gt;.&amp;nbsp; &lt;br /&gt;&lt;br /&gt;OK, OK, it is to fast, let's start from Create a Runspace:&lt;br /&gt;System.Management.Automation.Runspaces.RunspaceFactory.CreateRunspace()&lt;br /&gt;&lt;blockquote&gt;public static Runspace CreateRunspace()&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Runspace runspace1;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; using (IDisposable disposable1 = RunspaceFactory._tracer.TraceMethod())&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; runspace1 = RunspaceFactory.CreateRunspace(new DefaultHost(Thread.CurrentThread.CurrentCulture, Thread.CurrentThread.CurrentUICulture));&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return runspace1;&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;So it acually create a &lt;b&gt;Runspace&lt;/b&gt; using &lt;b&gt;DefaultHost&lt;/b&gt;&lt;br /&gt;Microsoft.Management.Automation.Internal.DefaultHost is a implement  of &lt;b&gt;MshHost&lt;/b&gt; abstract class.&lt;br /&gt;&lt;blockquote&gt;internal class DefaultHost : MshHost&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // Methods&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; static DefaultHost();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; internal DefaultHost(CultureInfo currentCulture, CultureInfo currentUICulture);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override void EnterNestedPrompt();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override void ExitNestedPrompt();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override void NotifyBeginApplication();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override void NotifyEndApplication();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override void SetShouldExit(int exitCode);&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // Properties&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override CultureInfo CurrentCulture { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override CultureInfo CurrentUICulture { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override Guid InstanceId { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Name { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override MshHostUserInterface UI { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override Version Version { get; }&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // Fields&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private CultureInfo currentCulture;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private CultureInfo currentUICulture;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private Guid id;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [TraceSource("DefaultHost", "DefaultHost subclass of S.M.A.MshHost Tracer")]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private static MshTraceSource tracer;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private Version ver;&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;Let's take a look at System.Management.Automation.Host.MshHost&lt;br /&gt;&lt;blockquote&gt;public abstract class MshHost&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // Methods&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; protected MshHost();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void EnterNestedPrompt();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void ExitNestedPrompt();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void NotifyBeginApplication();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void NotifyEndApplication();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void SetShouldExit(int exitCode);&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // Properties&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract CultureInfo CurrentCulture { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract CultureInfo CurrentUICulture { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract Guid InstanceId { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract string Name { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public virtual MshObject PrivateData { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract MshHostUserInterface UI { get; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract Version Version { get; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;b&gt;MshHostUserInterface&lt;/b&gt; is the object which actully deals with user interface:&lt;br /&gt;&lt;blockquote&gt;public abstract class MshHostUserInterface&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // Methods&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; protected MshHostUserInterface();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract Dictionary&amp;lt;string, MshObject&amp;gt; Prompt(string caption, string message, Collection&amp;lt;FieldDescription&amp;gt; descriptions);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract int PromptForChoice(string caption, string message, Collection&amp;lt;ChoiceDescription&amp;gt; choices, int defaultChoice);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract MshCredential PromptForCredential(string caption, string message, string userName, string targetName);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract MshCredential PromptForCredential(string caption, string message, string userName, string targetName, MshCredentialTypes allowedCredentialTypes, MshCredentialUIOptions options);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract string ReadLine();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract SecureString ReadLineAsSecureString();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void Write(string value);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void Write(ConsoleColor foregroundColor, ConsoleColor backgroundColor, string value);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void WriteDebugLine(string message);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void WriteErrorLine(string value);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public virtual void WriteLine();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void WriteLine(string value);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public virtual void WriteLine(ConsoleColor foregroundColor, ConsoleColor backgroundColor, string value);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void WriteProgress(long sourceId, ProgressRecord record);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void WriteVerboseLine(string message);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract void WriteWarningLine(string message);&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // Properties&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public abstract MshHostRawUserInterface RawUI { get; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;But when we check the public property &lt;b&gt;UI&lt;/b&gt; in DefaultHost:&lt;br /&gt;&lt;blockquote&gt;public override MshHostUserInterface UI&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; MshHostUserInterface interface1;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; using (IDisposable disposable1 = DefaultHost.tracer.TraceProperty())&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; interface1 = null;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return interface1;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;So, it is a null object.&lt;br /&gt;&lt;br /&gt;If we want a REAL interactive remote shell, we have to implement our own &lt;b&gt;MshHost&lt;/b&gt; and &lt;b&gt;MshHostUserInterface&lt;/b&gt; (and maybe &lt;b&gt;MshHostRawUserInterface&lt;/b&gt;). MshHostUserInterface will be responsible to write results to and get input from remote client. I bet this is the way Microsoft monad team will be using to provide remote access (maybe in version 2 of msh). &lt;br /&gt;&lt;br /&gt;For me, it is too much work (and I would not compete with monad team). I really wish someone can show a example of implementation of &lt;b&gt;MshHost&lt;/b&gt; and &lt;b&gt;MshHostUserInterface.&lt;/b&gt; Maybe monad team would like to share their&amp;nbsp; source code of msh.exe&lt;br /&gt;&lt;br /&gt;Hehe, You know I am joking, right?&lt;br /&gt;&lt;br /&gt;&lt;font color=red&gt;Added on Mar 15th 10:50am&lt;/font&gt;&lt;br /&gt;I just find out that &lt;a href="http://windowssdk.msdn.microsoft.com/library/default.asp?url=/library/en-us/Monad_Prog/html/f3aaf667-af84-4ea8-a5ad-d454d0d700b8.asp"&gt;Microsoft Command Shell (MSH) Programmer's Guide&lt;/a&gt; are online now! It has exact information I needed. &lt;br /&gt;&lt;br /&gt;Have Fun!&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114236943207686439?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114236943207686439/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/separation-of-monad-engine-and-user.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114236943207686439'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114236943207686439'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/separation-of-monad-engine-and-user.html' title='Separation of Monad Engine and User Interface'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114222857266726116</id><published>2006-03-13T00:42:00.000-05:00</published><updated>2006-03-14T16:16:26.493-05:00</updated><title type='text'>Securely Extend Monad Pipline over Network (2)</title><content type='html'>I have uploaded a testing binary package. You can download it from &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;gotdotnet&lt;/a&gt;. If you have any suggestions or bug reports, please drop a few lines as comment.&lt;br/&gt;&lt;br/&gt;Usage:&lt;br/&gt;&lt;br/&gt;1. Start MonadServiceHost.exe at Host Windows box with Monad installed (beta 3.1 for my testing):&lt;br/&gt;&lt;blockquote&gt;MonadServiceHost.exe 8888&lt;br/&gt;&lt;/blockquote&gt;Where "8888" is the port number you want server to listen. (Remember to allow accecc to local port 8888 in you firewall setting).&lt;br/&gt;&lt;br/&gt;2. Start MSH.exe at client Windows box&lt;br/&gt;&lt;blockquote&gt;MSH.exe&lt;br/&gt;&lt;/blockquote&gt;3. Load MonadServiceClient.dll from within client MSH.exe&lt;br/&gt;&lt;blockquote&gt;[System.Reflection.Assembly]::LoadFile("D:\MonadServiceClient.dll")&lt;br/&gt;&lt;/blockquote&gt;where "D:\MonadServiceClient.dll" full path to MonadServiceClient.dll&lt;br/&gt;&lt;br/&gt;4. Initialize a client object&lt;br/&gt;&lt;blockquote&gt;$client = new-object MonadServiceClient.ClientLib (8888,"192.168.0.2")&lt;br/&gt;&lt;/blockquote&gt;where "192.168.0.2" is the IP Address of Server, "8888" is port to connect .&lt;br/&gt;&lt;br/&gt;5. Check out Method you can use&lt;br/&gt;&lt;blockquote&gt;$client | get-member&lt;br/&gt;&lt;/blockquote&gt;6. Connect client to remote server&lt;br/&gt;&lt;blockquote&gt;$client.Connect()&lt;br/&gt;&lt;/blockquote&gt;7. Using client to communicate with server&lt;br/&gt;&lt;blockquote&gt;# Ping Server&lt;br/&gt;$client.Ping()&lt;br/&gt;&lt;br/&gt;# Invoke remote command &lt;br/&gt;$client.Invoke("get-process")&lt;br/&gt;$client.Invoke("set-location HKLM:")&lt;br/&gt;&lt;br/&gt;# run remote script&lt;br/&gt;$client.Invoke("D:\msh\id.msh")&lt;br/&gt;&lt;br/&gt;# Redirect output to a file if return a lot of objects.&lt;br/&gt;&lt;/blockquote&gt;7. Disconnect client&lt;br/&gt;&lt;blockquote&gt;$client.Close()&lt;br/&gt;&lt;/blockquote&gt;8. If something went wrong and you lost connection , just reconnect client&lt;br/&gt;&lt;blockquote&gt;$client.Connect()&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;Have Fun!&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114222857266726116?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114222857266726116/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/securely-extend-monad-pipline-over_13.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114222857266726116'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114222857266726116'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/securely-extend-monad-pipline-over_13.html' title='Securely Extend Monad Pipline over Network (2)'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114194023844721383</id><published>2006-03-09T16:31:00.000-05:00</published><updated>2006-03-09T22:41:24.706-05:00</updated><title type='text'>Securely Extend Monad Pipline over Network (1)</title><content type='html'>Prototype (or a toy) of a light-weighted server, which host monad and interact with remote client via secured TCP channel.&amp;nbsp;  &lt;br /&gt;&lt;br /&gt;There are a lot of questions been asked in newsgroup about using Monad securely from remote computer. Ideally, we should have something like &lt;b&gt;sshd&lt;/b&gt; in linux. But unlike traditional text based shell, Monad deal with &lt;b&gt;.Net object&lt;/b&gt; using &lt;b&gt;pipeline&lt;/b&gt;. Sshd did not have buildin functionality to work with .Net object.&amp;nbsp; So it make sense to host monad in a &lt;b&gt;ASP.NET&lt;/b&gt; application and send object over &lt;b&gt;soap&lt;/b&gt; protocal. &lt;br /&gt;&lt;br /&gt;But what if you don't want a &lt;b&gt;CPU-intensive&lt;/b&gt; program or don't want to rely on &lt;b&gt;IIS web server&lt;/b&gt;? Maybe you just want to access your desktop via a laptop on the same home network. I still remember in the "old time"  I can use NetCat.exe binding a shell and gain remote access instantly. "&lt;font color="red"&gt;Simple is beautiful&lt;/font&gt;", isn't it?  That's why I write this tiny "toy" (File size: Server 24kb, client 20kb).&lt;br /&gt;&lt;br /&gt;Design:&lt;br /&gt;1. Server is a console program which &lt;b&gt;hosts Monad Runspace&lt;/b&gt;, authenticates client using &lt;b&gt;NegotiateStream&lt;/b&gt; and &lt;b&gt;impersonates&lt;/b&gt; client using remote credential.&lt;br /&gt;2. Client is class libary which sents out msh command to server.&lt;br /&gt;3. Server gets command input, &lt;b&gt;invoke monad pipline&lt;/b&gt; and get output objects.&lt;br /&gt;4. Server &lt;b&gt;serializes &lt;/b&gt;object and send them to client over secure tcp channel.&lt;br /&gt;5. Client &lt;b&gt;de-serializes&lt;/b&gt; object and emit them to client side interactive MSH for reuse. &lt;br /&gt;&lt;br /&gt;Some thoughts:&lt;br /&gt;1. &lt;b&gt;Simple text-base control commands &lt;/b&gt;were used to control server and client. For example: Server sent a "SendObject" command to client; Client sent back an "OK" command and prepared to receive &lt;b&gt;object&lt;/b&gt;; Server then sent serialized objects, Client de-serialized objects and sent back an "OK" command to finish this sequence.    &lt;br /&gt;2.  Serialization and de-serialization of &lt;b&gt;MshObject&lt;/b&gt; is the most difficult part. I still did not make it fully work. Serialization of every member in MshObject is not needed because some fields are session-dependent. We just need most important informations about the object so that we can &lt;b&gt;operated those objects at server side&lt;/b&gt;.&lt;br /&gt;3. Instead of creating a new instance of monad runspace for each invoke, remote session state should be maintained by server for each client. So client can use variable generated by previous command.&lt;br /&gt;&lt;br /&gt;At this moment&lt;br /&gt;1. Authentication and network are working fine.&lt;br /&gt;2. Server can only accept one client at a time.(I will swith to asynchronous method later)&lt;br /&gt;2. Client maintain connection status and can be controled by msh script.   &lt;br /&gt;2. It is barely usable as a interactive remote shell. for example, start remote service, kill remote process, run remote script (this is really cool).&lt;br /&gt;3. Can NOT sent &lt;span style="font-weight:bold;"&gt;real&lt;/span&gt; object between server and client. Only important object information were transfered to client.&lt;br /&gt;&lt;br /&gt;I will post binary and source code when it became more mature. See a screenshot of server console and client output below:&lt;br /&gt;&lt;br /&gt;Host:&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/host.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/host.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Client output:&lt;br /&gt;&lt;blockquote&gt;&amp;gt;[System.Reflection.Assembly]::LoadFile("D:\msh\MonadServiceClient.dll")&lt;br /&gt;&lt;br /&gt;GAC&amp;nbsp;&amp;nbsp;&amp;nbsp; Version&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Location&lt;br /&gt;---&amp;nbsp;&amp;nbsp;&amp;nbsp; -------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; --------&lt;br /&gt;False&amp;nbsp; v2.0.50727&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; D:\msh\MonadServiceClient.dll&lt;br /&gt;&lt;br /&gt;&amp;gt; $client = new-object MonadServiceClient.ClientLib (8080,"127.0.0.1")&lt;br /&gt;&amp;gt; $client.Connect()&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;IsConnected&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : True&lt;br /&gt;IsAuthenticated&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : True&lt;br /&gt;IsMutuallyAuthenticated : False&lt;br /&gt;IsEncrypted&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : True&lt;br /&gt;IsSigned&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : True&lt;br /&gt;RemoteIdentity&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : System.Security.Principal.GenericIdentity&lt;br /&gt;Welcome&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : MSHForFun.MonadHostService Ready!&lt;br /&gt;ConnectStartAt&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 2006-3-9 15:33:54&lt;br /&gt;ConnectEndAt&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 0001-1-1 0:00:00&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&amp;gt; $client.Invoke("set-location d:\msh")&lt;br /&gt;OK: Null object in pipline&lt;br /&gt;&lt;br /&gt;&amp;gt; $client.Invoke("get-location")&lt;br /&gt;D:\msh&lt;br /&gt;Drive:System.Management.Automation.DriveInfo Drive {get;}&lt;br /&gt;Provider:System.Management.Automation.ProviderInfo Provider {get;}&lt;br /&gt;ProviderPath:System.String ProviderPath {get;}&lt;br /&gt;Path:System.String Path {get;}&lt;br /&gt;&lt;br /&gt;&amp;gt; $client.Invoke("(get-process explorer).Id")&lt;br /&gt;1644&lt;br /&gt;&lt;br /&gt;&amp;gt; $client.ping()&lt;br /&gt;Success&lt;br /&gt;&lt;br /&gt;&amp;gt; $client.close()&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;IsConnected&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;IsAuthenticated&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;IsMutuallyAuthenticated : False&lt;br /&gt;IsEncrypted&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;IsSigned&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;RemoteIdentity&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; :&lt;br /&gt;Welcome&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; :&lt;br /&gt;ConnectStartAt&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 2006-3-9 15:38:46&lt;br /&gt;ConnectEndAt&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 2006-3-9 15:41:43&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;Have Fun!&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114194023844721383?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114194023844721383/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/securely-extend-monad-pipline-over.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114194023844721383'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114194023844721383'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/securely-extend-monad-pipline-over.html' title='Securely Extend Monad Pipline over Network (1)'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114192092244510501</id><published>2006-03-09T11:04:00.000-05:00</published><updated>2006-03-09T11:15:22.456-05:00</updated><title type='text'>Switch to BSD License</title><content type='html'>&lt;p&gt;License is a sensitivie issue. Any comments on certain licence will cause a "war" in newsgroup. I am not a lawyer and I do not want to get into trouble either. I wrote all those codes just for fun and I do want to get more feed back for my project.  So I take &lt;a href="http://www.leeholmes.com/blog/PermaLink,guid,f9176068-1928-4ed2-90de-dec33e90ab07.aspx"&gt;Lee Holmes' advice&lt;/a&gt;.&lt;br /&gt;&lt;/p&gt;&lt;p&gt;My &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea"&gt;MSHForFun.Security mshsnapin&lt;/a&gt; are now under BSD license.&lt;br /&gt;&lt;/p&gt;&lt;p&gt;Have Fun!&lt;br /&gt;&lt;/p&gt;&lt;p&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt;    &lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114192092244510501?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114192092244510501/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/switch-to-bsd-license.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114192092244510501'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114192092244510501'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/switch-to-bsd-license.html' title='Switch to BSD License'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114127596528267350</id><published>2006-03-01T23:10:00.000-05:00</published><updated>2006-05-05T11:08:17.176-04:00</updated><title type='text'>Release of MSHForFun.Security MshSnapin v0.1</title><content type='html'>Finally, I finished my &lt;b&gt;MSHForFun.Security MshSnapin&lt;/b&gt; v0.1. Source code and binary files can be downloaded from &lt;a href="http://www.gotdotnet.com/workspaces/workspace.aspx?id=ce09cdaf-7da2-4f1c-bed3-f8cb35de5aea" target="_blank"&gt;GotDotNet&lt;/a&gt; under BSD license (Sorry, you need an Internet explorer to visit gotdotnet.com. Firefox seemed to not willing to take .Net passport). Contain four cmdlets at this moment:&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : &lt;b&gt;add-processowner&lt;/b&gt;&lt;br /&gt;Definition&amp;nbsp;&amp;nbsp;&amp;nbsp; : add-processowner [-ProcessArray] Process[] [-Verbose] [-Debug]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [-ErrorAction ActionPreference] [-ErrorVariable String] [-OutVa&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; riable String] [-OutBuffer Int32] [-WhatIf] [-Confirm]&lt;br /&gt;Wrapper of OpenProcessToken Win32 API. It takes Process (output of get-process cmdlet) as input and adds process owner information (System.Security.Pricipal.WindowsIdentity) as NoteProperty. &lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : &lt;b&gt;Get-Privilege&lt;/b&gt;&lt;br /&gt;Definition&amp;nbsp;&amp;nbsp;&amp;nbsp; : Get-Privilege [[-Identity] WindowsIdentity] [-Verbose] [-Debug]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [-ErrorAction ActionPreference] [-ErrorVariable String] [-OutV&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ariable String] [-OutBuffer Int32] [-WhatIf] [-Confirm]&lt;br /&gt;Wrapper of GetTokenInformation Win32 API. It takes System.Security.Pricipal.WindowsIdentity object as input and returns MSHForFun.Security.TokenPrivilegeCollection object. If used without parameter, it returns current process (msh.exe) token privileges.&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : &lt;b&gt;get-windowsidentity&lt;/b&gt;&lt;br /&gt;Definition&amp;nbsp;&amp;nbsp;&amp;nbsp; : get-windowsidentity [[-Credential] MshCredential] [-Verbose] [-&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Debug] [-ErrorAction ActionPreference] [-ErrorVariable String]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [-OutVariable String] [-OutBuffer Int32] [-WhatIf] [-Confirm]&lt;br /&gt;Wapper of LogonUser() Win32API. It takes MshCredential object as input and returns System.Security.Pricipal.WindowsIdentity object. If used without parameter, it returns System.Security.Pricipal.WindowsIdentity object represented current user.&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : &lt;b&gt;start-process&lt;/b&gt;&lt;br /&gt;Definition&amp;nbsp;&amp;nbsp;&amp;nbsp; : start-process [-FileName] String [-Credential MshCredential] [-&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Arguments String] [-LoadUserProfile] [-UseShellExecute] [-Worki&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ngDirectory String] [-CreateNoWindow] [-ErrorDialog] [-ErrorDia&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; logParentHandle IntPtr] [-RedirectStandardError] [-RedirectStan&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; dardInput] [-RedirectStandardOutput] [-StandardErrorEncoding En&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; coding] [-StandardOutputEncoding Encoding] [-Verb String] [-Win&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; dowStyle ProcessWindowStyle] [-Verbose] [-Debug] [-ErrorAction&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ActionPreference] [-ErrorVariable String] [-OutVariable String]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [-OutBuffer Int32] [-WhatIf] [-Confirm]&lt;br /&gt;Wrapper of System.Diagnostics.Process.Start() Methods. It takes MshCredential object as input and start a process using that credential. (Runas in MSH).&lt;br /&gt;&lt;br /&gt;What's new?&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Wrap token handle into &lt;b&gt;SafeTokenHandle&lt;/b&gt;, which is derived from Microsoft.Win32. SafeHandles. SafeHandleZeroOrMinusOneIsInvalid (try to prevent handle leakage and provides protection for handle recycling security attacks)&lt;/li&gt;&lt;li&gt;&lt;b&gt;&lt;font color="#ff0000"&gt;Get-Privilege&lt;/font&gt;&lt;/b&gt; cmdlet&lt;/li&gt;&lt;li&gt;Make sure all &lt;b&gt;Exceptions&lt;/b&gt; were properly handled&amp;nbsp; and using &lt;b&gt;WriteWarning&lt;/b&gt; instead of WriteError,&amp;nbsp; if we known errors will happen frequently (Add-Processowner) &lt;/li&gt;&lt;li&gt;Rewrite C# code, correct errors and clean comments.&lt;/li&gt;&lt;/ol&gt;Something intersting about Get-Privilege cmdlet:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;&lt;b&gt;System.Security.Pricipal.WindowsIdentity&lt;/b&gt; contains all important information inside a token except &lt;b&gt;token privileges&lt;/b&gt;, so I took the challenge to write a  Get-Privilege cmdlet.&lt;/li&gt;&lt;li&gt;Mashalling memory block (&lt;b&gt;struct TOKEN_PRIVILEGE&lt;/b&gt;) using C# is killing me. I will not do it again.&lt;/li&gt;&lt;li&gt;MSHForFun.Security.TokenPrivilege contian 2 public property: &lt;b&gt;Name&lt;/b&gt; and &lt;b&gt;Status&lt;/b&gt;&lt;/li&gt;&lt;li&gt;MSHForFun.Security.TokenPrivilegeCollection is derived from &lt;b&gt;System.Collection.CollectionBase&lt;/b&gt;.&lt;/li&gt;&lt;li&gt;Get-Privilege cmdlet is used for &lt;b&gt;dump token privilege only&lt;/b&gt;. &lt;/li&gt;&lt;/ol&gt;Some examples of using these cmdlets:&lt;br /&gt;&lt;blockquote&gt;&lt;b&gt;&amp;gt;&lt;/b&gt;get-privilege (get-windowsidentity (get-credential)) &lt;br /&gt;&lt;br /&gt;Cmdlet get-credential at command pipeline position 1&lt;br /&gt;Supply values for the following parameters:&lt;br /&gt;Credential&lt;br /&gt;User: Administrator&lt;br /&gt;Password for user Administrator: *******&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Status&lt;br /&gt;----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ------&lt;br /&gt;SeChangeNotifyPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeSecurityPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeBackupPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeRestorePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeSystemtimePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeShutdownPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeRemoteShutdownPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeTakeOwnershipPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeDebugPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeSystemEnvironmentPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeSystemProfilePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeProfileSingleProcessPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeIncreaseBasePriorityPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeLoadDriverPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeCreatePagefilePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeIncreaseQuotaPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeUndockPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeManageVolumePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeCreateGlobalPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeImpersonatePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;&lt;br /&gt;&amp;gt; get-privilege (get-process -Id 3768 | add-processowner).Processowner&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Status&lt;br /&gt;----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ------&lt;br /&gt;SeChangeNotifyPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeSecurityPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeBackupPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeRestorePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeSystemtimePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeShutdownPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeRemoteShutdownPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeTakeOwnershipPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeDebugPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled&lt;br /&gt;SeSystemEnvironmentPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeSystemProfilePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeProfileSingleProcessPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeIncreaseBasePriorityPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeLoadDriverPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeCreatePagefilePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeIncreaseQuotaPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeUndockPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeManageVolumePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Removed&lt;br /&gt;SeCreateGlobalPrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;SeImpersonatePrivilege&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Enabled | Enabled By Default&lt;br /&gt;&lt;br /&gt;&lt;b&gt;&amp;gt;&lt;/b&gt;get-process | add-processowner&lt;br /&gt;&lt;br /&gt;Handles&amp;nbsp; NPM(K)&amp;nbsp;&amp;nbsp;&amp;nbsp; PM(K)&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WS(K) VS(M)&amp;nbsp;&amp;nbsp; CPU(s)&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Id ProcessName&lt;br /&gt;-------&amp;nbsp; ------&amp;nbsp;&amp;nbsp;&amp;nbsp; -----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ----- -----&amp;nbsp;&amp;nbsp; ------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; -- -----------&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 71&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 3&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 1548&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 5304&amp;nbsp;&amp;nbsp;&amp;nbsp; 38&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 0.80&amp;nbsp;&amp;nbsp;&amp;nbsp; 864 acrotray&lt;br /&gt;&lt;font color="#ffcc33"&gt;&lt;b&gt;WARNING: Failed to openy process token (Access Denied): alg&lt;/b&gt;&lt;/font&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; 105&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 5&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 1224&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 3604&amp;nbsp;&amp;nbsp;&amp;nbsp; 35&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 2832 alg&lt;br /&gt;....&lt;br /&gt;(clipped)&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;&amp;gt;&lt;/b&gt;Start-process -Credential (get-credential) -FileName control.exe -Arguments timedate.cpl&lt;br /&gt;&lt;br /&gt;Cmdlet get-credential at command pipeline position 1&lt;br /&gt;Supply values for the following parameters:&lt;br /&gt;Credential&lt;br /&gt;User: Administrator&lt;br /&gt;Password for user Administrator: *******&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Handles&amp;nbsp; NPM(K)&amp;nbsp;&amp;nbsp;&amp;nbsp; PM(K)&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WS(K) VS(M)&amp;nbsp;&amp;nbsp; CPU(s)&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Id ProcessName&lt;br /&gt;-------&amp;nbsp; ------&amp;nbsp;&amp;nbsp;&amp;nbsp; -----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ----- -----&amp;nbsp;&amp;nbsp; ------&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; -- -----------&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 0&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 0&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 64&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 60&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 1&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 0.00&amp;nbsp;&amp;nbsp; 2220 control&lt;br /&gt;&lt;/blockquote&gt; &lt;br /&gt;&lt;br /&gt;PS. some Non-MSH stuff:&lt;br /&gt;Check out the "Brrreeeport" game on &lt;a href="http://scobleizer.wordpress.com/2006/02/13/blogcode-helps-you-find-blogs-similar-to/" target="_blank"&gt;the Scobleizer blog&lt;/a&gt;.&lt;br /&gt;Check out results on &lt;br /&gt;1. &lt;a href="http://www.technorati.com/search/brrreeeport" target="_blank"&gt;Technorati&lt;/a&gt; &lt;br /&gt;2. &lt;a href="http://search.msn.com/results.aspx?FORM=TOOLBR&amp;amp;q=brrreeeport" target="_blank"&gt;MSN Search&lt;/a&gt;&lt;br /&gt;3. &lt;a href="http://www.google.com/search?hl=en&amp;amp;q=brrreeeport&amp;amp;btnG=Google+Search" target="_blank"&gt;Google&lt;/a&gt; &lt;br /&gt;4. &lt;a href="http://search.yahoo.com/search?p=brrreeeport&amp;amp;sm=Yahoo%21+Search&amp;amp;fr=FP-tab-web-t&amp;amp;toggle=1&amp;amp;cop=&amp;amp;ei=UTF-8" target="_blank"&gt;Yahoo&lt;/a&gt;  &lt;br /&gt;&lt;br /&gt;Have fun!&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114127596528267350?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114127596528267350/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/03/release-of-mshforfunsecurity-mshsnapin.html#comment-form' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114127596528267350'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114127596528267350'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/03/release-of-mshforfunsecurity-mshsnapin.html' title='Release of MSHForFun.Security MshSnapin v0.1'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114012417804888854</id><published>2006-02-16T15:22:00.000-05:00</published><updated>2006-05-05T11:08:48.310-04:00</updated><title type='text'>Groups Command in MSH: Get-WindowsIdentity cmdlet</title><content type='html'>&lt;font color="#ff0000"&gt;(Added on Mar 6th)&lt;/Font&gt; There is a follow up post on this topic &lt;a href="http://mshforfun.blogspot.com/2006/03/release-of-mshforfunsecurity-mshsnapin.html"&gt;here&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;In Linux Bash shell, there is a handy&amp;nbsp; &lt;b&gt;groups&lt;/b&gt; command, which takes a username as input and return user associated groups. To get similar functionality,&amp;nbsp; I wrote the &lt;b&gt;Get-WindowsIdentity&lt;/b&gt; cmdlet, which take&amp;nbsp; a MshCredential as input, call LogonUser Win32 API and return a System.Security. Principal.WindowsIdentity object. The bad news, you got to have a username and &lt;font color="#ff0000"&gt;password&lt;/font&gt;. Example:&lt;br /&gt;&lt;blockquote&gt;&amp;gt;get-WindowsIdentity (get-credential)&lt;br /&gt;&lt;br /&gt;AuthenticationType : MICROSOFT_AUTHENTICATION_PACKAGE_V1_0&lt;br /&gt;ImpersonationLevel : None&lt;br /&gt;IsAuthenticated&amp;nbsp;&amp;nbsp;&amp;nbsp; : True&lt;br /&gt;IsGuest&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;IsSystem&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;IsAnonymous&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : False&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : Domain\Administrator&lt;br /&gt;Owner&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : S-1-5-21-XXXXXXXXX-XXXXXXX-XXXX-XX&lt;br /&gt;User&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : S-1-5-21-XXXXXXXXX-XXXXXXX-XXXX-XX&lt;br /&gt;Groups&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : {S-1-5-21-XXXXXXXXX-XXXXXXX-XXXX-XX, , , , , , , }&lt;br /&gt;Token&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : XXXX&lt;br /&gt;&lt;/blockquote&gt;This cmdlet is designed for WindowsXP SP2. In Windows 2000, user required to have &lt;span style="font-weight:bold;"&gt;SeTcbPrivilege&lt;/span&gt;,a.k.a Act as part of the operating system, to call LogonUser. The reference (at the end of the post), provide a workaround to not call LongonUser: Use &lt;b&gt;NegotiateStream&lt;/b&gt;. But it did not work for me.&lt;br /&gt;&lt;br /&gt;If you are using windows server 2003 and want to check a domain account, don't use this cmdlet. Just do something like this:&lt;br /&gt;&lt;blockquote&gt;&amp;gt;$id = new-object System.Security.Principal.WindowsIdentity("Domain\User")&lt;br /&gt;&lt;/blockquote&gt;This cmdlet could be useful if you are trying&lt;br /&gt;1. To find out a specific user (you known his/her password) belongs to which groups &lt;br /&gt;&lt;br /&gt;2. To check a user's password without login as that user or using runas/&lt;a href="http://mshforfun.blogspot.com/2006/01/dreaming-of-su-in-msh.html"&gt;su.msh&lt;/a&gt;. If you input wrong password, you will get an error:&lt;br /&gt;&lt;blockquote&gt;get Get-WindowsIdentity : Win32 API (LogonUser) Error: 1326 &lt;br /&gt;&lt;/blockquote&gt;  &lt;br /&gt;&lt;br /&gt;C# code:&lt;br /&gt;&lt;blockquote&gt;using System;&lt;br /&gt;using System.Security.Principal;&lt;br /&gt;using System.Management.Automation;&lt;br /&gt;using System.Net;&lt;br /&gt;using System.Runtime.InteropServices;&lt;br /&gt;&lt;br /&gt;namespace MSHForFun.Security&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public class LogonUserHelper&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [DllImport("advapi32.dll", SetLastError = true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; static extern bool LogonUser(&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; string principal,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; string authority,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; string password,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; LogonTypes logonType,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; LogonProviders logonProvider,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; out IntPtr token);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [DllImport("kernel32.dll", SetLastError = true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; static extern bool CloseHandle(IntPtr handle);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; enum LogonTypes : uint&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Interactive = 2,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Network,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Batch,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Service,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NetworkCleartext = 8,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NewCredentials&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; enum LogonProviders : uint&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Default = 0, // default for platform (use this!)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WinNT35,&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // sends smoke signals to authority&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WinNT40,&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // uses NTLM&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WinNT50&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // negotiates Kerb or NTLM&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public static WindowsIdentity LogonUser(MshCredential UserCre)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; IntPtr token = IntPtr.Zero;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NetworkCredential Cre = UserCre.GetNetworkCredential();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; bool result = LogonUser(&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Cre.UserName, "", Cre.Password,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; LogonTypes.Network,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; LogonProviders.Default,&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; out token);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WindowsIdentity id;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (result)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; id = new WindowsIdentity(token);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; CloseHandle(token);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; else&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; throw new Exception("Win32 API (LogonUser) Error: " + Marshal.GetLastWin32Error().ToString());&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return id;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// Get User WindowsIdentity &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Cmdlet("Get", "WindowsIdentity", SupportsShouldProcess = true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public class GetWindowsIdentityCmd : Cmdlet&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; #region Parameters&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private MshCredential userCre = null;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Process Arrary to work with&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Mandatory = true, Position = 0)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public MshCredential UserCredential&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return userCre; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { userCre = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; #endregion&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// Call LogonUser Return a WindowsIdentity Object&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; protected override void ProcessRecord()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (ShouldProcess("Get WindowsIdentity of User: " + userCre.UserName))&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteObject(LogonUserHelper.LogonUser(userCre));&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;Reference: http://pluralsight.com/wiki/default.aspx/Keith.GuideBook/HowToGetATokenForAUser.html&lt;br /&gt;&lt;br /&gt;Have fun!&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114012417804888854?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114012417804888854/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/02/groups-command-in-msh-get.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114012417804888854'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114012417804888854'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/02/groups-command-in-msh-get.html' title='Groups Command in MSH: Get-WindowsIdentity cmdlet'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-114006890442553529</id><published>2006-02-16T00:43:00.000-05:00</published><updated>2006-05-05T11:09:18.086-04:00</updated><title type='text'>Add-ProcessOwner cmdlet (update)</title><content type='html'>&lt;font color="#ff0000"&gt;(Added on Mar 6th)&lt;/Font&gt; There is a follow up post on this topic &lt;a href="http://mshforfun.blogspot.com/2006/03/release-of-mshforfunsecurity-mshsnapin.html"&gt;here&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Rewrite Add-ProcessOwner cmdlet and build into a MshSnapin. Most intersting thing here: Wrap an object into &lt;b&gt;MshObject&lt;/b&gt;, add a &lt;b&gt;MshNoteProperty&lt;/b&gt;.&lt;br /&gt;&lt;br /&gt;MshObject Constructor:&lt;br /&gt;&lt;blockquote&gt;System.Management.Automation.MshObject..ctor(Object)&lt;br /&gt;&lt;/blockquote&gt;MshNoteProperty Constructor:&lt;br /&gt;&lt;blockquote&gt;System.Management.Automation.MshNoteProperty..ctor(String, Object)&lt;br /&gt;&lt;/blockquote&gt;Example to use this cmdlet:&lt;br /&gt;&lt;blockquote&gt;&amp;gt;$ps=get-process | add-processowner&lt;br /&gt;&amp;gt;$ps | get-member&lt;br /&gt;&lt;br /&gt;TypeName: System.Diagnostics.Process&lt;br /&gt;&lt;br /&gt;&amp;gt;$ps[0].ProcessOwner | get-member&lt;br /&gt;&lt;br /&gt;System.Security.Principal.WindowsIdentity&lt;br /&gt;# &lt;font color="#ff0000"&gt;Some processOwner could be null due to security policy&lt;/font&gt;&lt;br /&gt;&lt;/blockquote&gt;&lt;blockquote&gt;//Add-ProcessOwner.cs&lt;br /&gt;using System;&lt;br /&gt;using System.Security.Principal;&lt;br /&gt;using System.Diagnostics;&lt;br /&gt;using System.Management.Automation;&lt;br /&gt;using System.Runtime.InteropServices;&lt;br /&gt;&lt;br /&gt;namespace MSHForFun.Security&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// Add Process Owner infomation as NoteProperty&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Cmdlet("add", "processowner", SupportsShouldProcess = true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public class AddProcessOwnerCmd : Cmdlet&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; #region Parameters&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private Process[] allProcess = null;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// Arrary of Process to query&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Mandatory = true, Position = 0, ValueFromPipeline = true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public Process[] ProcessArray&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return allProcess; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { allProcess = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; #endregion&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private SafeTokenHandle processToken = new SafeTokenHandle(IntPtr.Zero);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private MshObject psex;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private MshNoteProperty info;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private WindowsIdentity id;&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// Get WindowsIdentity for each process&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; protected override void ProcessRecord()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; foreach (Process ps in allProcess)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (ShouldProcess(ps.ProcessName))&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; psex = new MshObject(ps);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; try&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (Win32Helper.OpenProcessToken(ps.Handle, TokenAccessLevels.Query, ref processToken))&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (processToken.IsInvalid)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteWarning("Invalid process token: " + ps.ProcessName);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; info = new MshNoteProperty("ProcessOwner", null);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; psex.Properties.Add(info);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; else&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; id = processToken.GetWindowsIdenty();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteVerbose("Successfully get process owner information: " + ps.ProcessName);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; info = new MshNoteProperty("ProcessOwner", id);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; psex.Properties.Add(info);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; else&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteWarning("Unable to query process token (privilege not held): " + ps.ProcessName);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; info = new MshNoteProperty("ProcessOwner", null);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; psex.Properties.Add(info);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; catch&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteWarning("Unable to query process token (privilege not held): " + ps.ProcessName);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; info = new MshNoteProperty("ProcessOwner", null);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; psex.Properties.Add(info);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteObject(psex);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;For MshSnapin&lt;br /&gt;&lt;blockquote&gt;//MshSnapin.cs&lt;br /&gt;using System;&lt;br /&gt;using System.Collections.Generic;&lt;br /&gt;using System.Text;&lt;br /&gt;using System.Management.Automation;&lt;br /&gt;using System.Configuration.Install;&lt;br /&gt;using System.ComponentModel;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;namespace MSHForFun.Security&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt; Defines the properties of MonadSecurity snapin&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; [RunInstaller(true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public class MonadSecurity : MshSnapIn&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Creates an instance of MonadSecurity Snapin class.&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public MonadSecurity() : base()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ///&amp;lt;summary&amp;gt;The snapin name which is used for registration&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Name&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return "MSHForFun.Security";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Gets vendor of the snapin.&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Vendor&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return "http://mshforfun.blogspot.com/";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Gets description of the snapin. &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Description&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return "Cmdlets for windows security related jobs";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-114006890442553529?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/114006890442553529/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/02/add-processowner-cmdlet-update.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114006890442553529'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/114006890442553529'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/02/add-processowner-cmdlet-update.html' title='Add-ProcessOwner cmdlet (update)'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113989801844510285</id><published>2006-02-14T01:20:00.000-05:00</published><updated>2006-02-14T11:26:31.793-05:00</updated><title type='text'>Peek into process token: Add-ProcessOwner cmdlet</title><content type='html'>Take a look at process tab in windws task manager. You will find all process followed by a &lt;strong&gt;user name &lt;/strong&gt;who start the process. Although Monad’s buildin cmdlet &lt;strong&gt;get-process &lt;/strong&gt;also return information of processes running on current windows box, due to the limitation of &lt;strong&gt;System.Diagnostics.Process &lt;/strong&gt;object, results does not contain process owner information.&lt;br/&gt;&lt;br/&gt;In order to get process token, I have to call Win32API – &lt;font color="#ff0000"&gt;OpenProcessToken&lt;/font&gt;, which return a &lt;strong&gt;System.IntPtr &lt;/strong&gt;type token. This token can be used to construct a &lt;strong&gt;System.Security. Principal.WindowsIdentity &lt;/strong&gt;object. (It is first time I use P/Invoke. Please tell me if I did anything wrong.)&lt;br/&gt;&lt;br/&gt;Using &lt;strong&gt;add-member &lt;/strong&gt;cmdlet, I add this WindowsIdentity object to System.Diagnostics.Process object as NoteProperty. To use it:&lt;br/&gt;&lt;blockquote&gt;&amp;gt;$ps= Get-process –ProcessName exporler | Add-ProcessOwner.msh&lt;br/&gt;&amp;gt;$ps | get-member&lt;br/&gt;…&lt;br/&gt;WaitForExit&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp System.Boolean WaitForExit(Int...&lt;br/&gt;WaitForInputIdle&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean WaitForInputIdl...&lt;br/&gt;__NounName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; NoteProperty&amp;nbsp;&amp;nbsp; System.String __NounName=Process&lt;br/&gt;&lt;font color="#ff0000"&gt;ProcessOwner&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;NoteProperty&amp;nbsp;&amp;nbsp; System.Security.Principal.Wind...&lt;/font&gt;&lt;br/&gt;…&lt;br/&gt;&amp;gt;$ps.ProcessOwner&lt;br/&gt;&lt;br/&gt;AuthenticationType : NTLM&lt;br/&gt;ImpersonationLevel : None&lt;br/&gt;IsAuthenticated&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;:&lt;br/&gt;IsGuest&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;: False&lt;br/&gt;IsSystem&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : False&lt;br/&gt;IsAnonymous&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;: False&lt;br/&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : Domain\tony&lt;br/&gt;Owner&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;: S-1-5-21-854245398-XXXXXXXXXX-XXXXXX-XXX&lt;br/&gt;User&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : S-1-5-21-854245398--XXXXXXXXXX-XXXXXX-XXX&lt;br/&gt;Groups&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : {S-1-5-21-854245398--XXXXXXXXXX, , , , , }&lt;br/&gt;Token&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;: XXXX&lt;/blockquote&gt;&lt;br/&gt;It is pretty sad that due to local security policy, I can not get owner of processes runing as &lt;strong&gt;System &lt;/strong&gt;or &lt;strong&gt;Network service &lt;/strong&gt;(which are those most intersting process). I might have to mount myself as a system service first than call OpenProcessToken. Well, that is to complicated for me.&lt;br/&gt;&lt;br/&gt;&lt;blockquote&gt;using System;&lt;br/&gt;using System.Runtime.InteropServices;&lt;br/&gt;using System.Security.Principal;&lt;br/&gt;using System.Collections;&lt;br/&gt;using System.Diagnostics;&lt;br/&gt;&lt;br/&gt;namespace Monad.Security&lt;br/&gt;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public class OpenProcessTokenHelper&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;[Flags]&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;enum TOKEN_ACCESS : uint&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_ASSIGN_PRIMARY = 0x0001,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_DUPLICATE = 0x0002,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_IMPERSONATE = 0x0004,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_QUERY = 0x0008,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_QUERY_SOURCE = 0x0010,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_ADJUST_PRIVILEGES = 0x0020,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_ADJUST_GROUPS = 0x0040,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_ADJUST_DEFAULT = 0x0080,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_ADJUST_SESSIONID = 0x0100,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_READ = 0x00020000 | TOKEN_QUERY,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_WRITE = 0x00020000 | TOKEN_ADJUST_PRIVILEGES | TOKEN_ADJUST_GROUPS | TOKEN_ADJUST_DEFAULT,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TOKEN_EXECUTE = 0x00020000,&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;};&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;[DllImport("Advapi32.dll", SetLastError = true)]&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;extern static int OpenProcessToken(IntPtr processHandle, TOKEN_ACCESS desiredAccess, out IntPtr tokenHandle);&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;[DllImport("kernel32.dll", SetLastError = true)]&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;extern static bool CloseHandle(IntPtr handle);&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public static WindowsIdentity GetProcessesIdentities(Process process)&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;try&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;IntPtr token = IntPtr.Zero;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;if (OpenProcessToken(process.Handle, TOKEN_ACCESS.TOKEN_QUERY, out token) == 0)&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;throw new ApplicationException("Can't open process token for: " + process.ProcessName);&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;WindowsIdentity id = new WindowsIdentity(token);&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;CloseHandle(token);&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;return (id);&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;catch (Exception ex)&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;throw new ApplicationException("Open process token error", ex);&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;}&lt;/blockquote&gt;&lt;br/&gt;&lt;blockquote&gt;#################################################&lt;br/&gt;## Add-ProcessOwner.msh&lt;br/&gt;## Add System.Security.Principal.WindowsIdentity object&lt;br/&gt;## to System.Diagnostics.Process object as NoteProperty &lt;br/&gt;## using P/invoke OpenProcessToken Win32API&lt;br/&gt;##&lt;br/&gt;## from &lt;a href="http://mshforfun.blogspot.com/"&gt;http://mshforfun.blogspot.com/&lt;/a&gt;&lt;br/&gt;################################################&lt;br/&gt;begin&lt;br/&gt;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;[void][Reflection.Assembly]::LoadFile("D:\msh\OpenProcessTokenHelper.dll")&lt;br/&gt;}&lt;br/&gt;process&lt;br/&gt;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;if ($_)&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; # Only working with process object&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($_ -isnot [System.Diagnostics.Process]) {continue}&amp;nbsp;&amp;nbsp;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; else&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; # Get WindowsIdentityObject&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $id=[Monad.Security.OpenProcessTokenHelper]::GetProcessesIdentities($_) &lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; add-member -InputObject $_ -Type NoteProperty -Name "ProcessOwner" -Value $id -ErrorAction "SilentlyContinue"&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br/&gt;}&lt;/blockquote&gt;&lt;br /&gt;Reference: http://www.sellsbrothers.com/askthewonk/secure/default.aspx?content=howcanigetthesecurityprin.htm&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113989801844510285?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113989801844510285/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/02/peek-into-process-token-add.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113989801844510285'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113989801844510285'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/02/peek-into-process-token-add.html' title='Peek into process token: Add-ProcessOwner cmdlet'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113983749180311588</id><published>2006-02-13T08:29:00.000-05:00</published><updated>2006-02-13T08:31:31.803-05:00</updated><title type='text'>Page load Activities increased!</title><content type='html'>My laptop was down for two days. When it came back, I was surprised to find out that visits to my blog increased dramatically. All visitors were referred from &lt;a href="http://blogs.msdn.com/monad/archive/2006/02/11/530215.aspx"&gt;monad team blog&lt;/a&gt; and &lt;a href="http://www.leeholmes.com/blog/CachingCredentialsForAdministrativeTasks.aspx"&gt;Lee Holmes' blog&lt;/a&gt;. Thanks you, guys! &lt;br /&gt;&lt;br /&gt;Although only small changes were made, their scripts delivered whole new user experience or better security compared to my (ugly) script. As you may have noticed, my daytime job is research scientist on immunology. I set up this blog for biology oriented readers and never thought IT professionals would be major readers. So please forgive my amateurish and feel free to comment on any errors or bad ideas in my posts. &lt;br /&gt;&lt;br /&gt;PS,I need to mention is that Blastn is program for DNA sequence analysis. So input should match [ATGCN], otherwise you will get an error.&lt;br /&gt;&lt;br /&gt;Have Fun.&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113983749180311588?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113983749180311588/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/02/page-load-activities-increased.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113983749180311588'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113983749180311588'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/02/page-load-activities-increased.html' title='Page load Activities increased!'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113937740551315343</id><published>2006-02-08T00:40:00.000-05:00</published><updated>2006-05-05T11:09:48.733-04:00</updated><title type='text'>Tired of Typing Administrator’s Password Repeatedly?</title><content type='html'>An example of how to use &lt;b&gt;new- SecureString&lt;/b&gt;, &lt;b&gt;export-SecureString&lt;/b&gt; and&lt;b&gt; import-SecureString&lt;/b&gt;.&lt;br /&gt;&lt;br /&gt;If you read my &lt;a href="http://mshforfun.blogspot.com/2006/02/survival-as-non-administrator-monad.html"&gt;previous blog entry&lt;/a&gt; and were convinced to logon as non-privilege user, you must have discovered the beauty and power of runas.exe or our &lt;a href="http://mshforfun.blogspot.com/2006/01/dreaming-of-su-in-msh.html"&gt;su.msh&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;But being the only user of that laptop, isn't it annoying to type Administrator's password again and again just for some routing jobs?&amp;nbsp; Why can't we just incorporate the Administrator's Password in our msh script? &lt;br /&gt;Yes, we can. We are not dumb enough to put plain text password in our script. We have to store our password in an encrypted form. Monad beta3 contain three cmdlets to operate SecureString:&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : export-SecureString&lt;br /&gt;Definition : export-SecureString [-SecureString] SecureString [[-SecureKey] Sec&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ureString] [-Verbose] [-Debug] [-ErrorAction ActionPreference] [-E&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; rrorVariable String] [-OutVariable String] [-OutBuffer Int32]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; export-SecureString [-SecureString] SecureString [-Key Byte[]] [-V&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; erbose] [-Debug] [-ErrorAction ActionPreference] [-ErrorVariable S&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; tring] [-OutVariable String] [-OutBuffer Int32]&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : import-SecureString&lt;br /&gt;Definition : import-SecureString [-String] String [[-SecureKey] SecureString] [&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; -Verbose] [-Debug] [-ErrorAction ActionPreference] [-ErrorVariable&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; String] [-OutVariable String] [-OutBuffer Int32]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; import-SecureString [-String] String [-Key Byte[]] [-Verbose] [-De&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; bug] [-ErrorAction ActionPreference] [-ErrorVariable String] [-Out&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Variable String] [-OutBuffer Int32]&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : new-SecureString&lt;br /&gt;Definition : new-SecureString [-Verbose] [-Debug] [-ErrorAction ActionPreferenc&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; e] [-ErrorVariable String] [-OutVariable String] [-OutBuffer Int32]&lt;br /&gt;&lt;br /&gt;Using export-SecureString, we can export a securestring (Administrator's Password) to a safe, persistable format (encrypted Administrator's Password). When needed, we can use import-SecureString to decrypt the output of export-securestring and restore it to a securestring.&lt;br /&gt;&lt;blockquote&gt;&amp;gt; export-SecureString (new-SecureString)|out-file Admin.pass&lt;br /&gt;Enter secret: ******&lt;br /&gt;&lt;br /&gt;&amp;gt; get-content Admin.pass&lt;br /&gt;01000000d08c9ddf0115d1118c7a00c04fc297eb0100000091700afb9271384c8d9d0f5fc5bbcad&lt;br /&gt;d0000000002000000000003660000a8000000100000003ab5cb17d04880206425514877334d5600&lt;br /&gt;…&lt;br /&gt;(Clipped)&lt;br /&gt;&lt;/blockquote&gt;Now we can write a script like following:&lt;br /&gt;&lt;blockquote&gt;##########################################&lt;br /&gt;# Defrag.msh&lt;br /&gt;# Start Disk Defragmenter as Administrator&lt;br /&gt;# From http://mshforfun.blogspot.com/&lt;br /&gt;# This script is provided AS IS&lt;br /&gt;# Use it at your own risk&lt;br /&gt;##########################################&lt;br /&gt;$Password=import-SecureString (get-content D:\msh\Admin.pass)&lt;br /&gt;$Windir=(get-childitem Env:windir).Value&lt;br /&gt;$StartInfo = new-object System.Diagnostics.ProcessStartInfo&lt;br /&gt;$StartInfo.UserName = "Admin"&lt;br /&gt;$StartInfo.Password = $Password&lt;br /&gt;$StartInfo.FileName = $Windir + "\system32\mmc.exe"&lt;br /&gt;$StartInfo.Arguments = $Windir + "\system32\dfrg.msc"&lt;br /&gt;$StartInfo.WorkingDirectory = $Windir + "\system32"&lt;br /&gt;$StartInfo.LoadUserProfile = $true&lt;br /&gt;$StartInfo.UseShellExecute = $false&lt;br /&gt;[System.Diagnostics.Process]::Start($StartInfo)&lt;br /&gt;&lt;/blockquote&gt;Tada! No more prompts for password!&lt;br /&gt;&lt;br /&gt;Something needed to mention:&lt;br /&gt;1. Although I don't know the &lt;b&gt;default key&lt;/b&gt; which export-SecureString used to encrypt password, I am pretty sure this key is &lt;b&gt;account-specific&lt;/b&gt; and &lt;b&gt;domain-specific&lt;/b&gt;. That is to say, another user on the same computer can not use import-SecureString to decrypt export-SecureString output.&amp;nbsp; Even a user with same account name can't decrypt it if he/she is on another computer (domain). If an unauthorized user tried to import-SecureString, he/she will get an error: &lt;br /&gt;&lt;blockquote&gt;import-SecureString : Key not valid for use in specified state. &lt;br /&gt;&lt;/blockquote&gt;But that does not rule out bruce attack. So make sure to apply &lt;b&gt;restricted access rule&lt;/b&gt; to you password file. It should be only readable by &lt;b&gt;&lt;font color="#ff0000"&gt;yourself&lt;/font&gt; &lt;/b&gt;and &lt;b&gt;&lt;font color="#ff0000"&gt;Administrators group&lt;/font&gt;&lt;/b&gt;.&lt;br /&gt;&lt;br /&gt;2. Export-SecureString can take a key (a SecureString or byte[]) to encrypt SecureString. Import-SecureString will require the same key to decrypt. (Then we would have to type another password - the encrypt key) This method will output an encrypted password which can be used by another user. But this feature is yet not available in version beta 3. You will get an error:&lt;br /&gt;&lt;blockquote&gt;&amp;gt; $key=new-securestring&lt;br /&gt;Enter secret: *****&lt;br /&gt;&amp;gt; export-securestring (new-securestring) -SecureKey $key&lt;br /&gt;Enter secret: ******&lt;br /&gt;export-SecureString : Cannot process argument because the value of argument "key" is invalid.&lt;br /&gt;&lt;/blockquote&gt;&lt;font color="#ff0000"&gt;Added on 14th, Feb 2006&lt;/font&gt;&lt;br /&gt;This is not a bug:&lt;br /&gt;From Lee Holmes--When you use an encryption key on export-secureString, it must be of a length supported by the encryption algorithm. That is 128,192, or 256 bytes -- which is 8, 12, or 16 unicode characters if you type them. I'll file a doc bug to make this more clear.&lt;br /&gt;&lt;font color="#ff0000"&gt;Added on 14th, Feb 2006&lt;/font&gt;&lt;br /&gt;3. Sign your script, and apply the &lt;font color="#ff0000"&gt;&lt;b&gt;AllSigned&lt;/b&gt;&lt;/font&gt; execution policy to prevent the script was tampered by malicious user.&lt;br /&gt;&lt;br /&gt;4. DO NOT try to grant access to another user using this method. As you can see, if a non-privilege user got the content of Admin.pass (if Admin.pass properly encrypted for this specific user), he can do anything as an Administrator!&amp;nbsp; &lt;br /&gt;&lt;br /&gt;There are more in depth discuss about Cryptograpy in MSH on MoW's Blog: &lt;a href="http://mow001.blogspot.com/2005/11/get-credential-and-decrypting.html"&gt;here&lt;/a&gt; and &lt;a href="http://mow001.blogspot.com/2005/11/more-on-cryptograpy-and-msh.html"&gt;here&lt;/a&gt; &lt;br /&gt;&lt;br /&gt;Have Fun!&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113937740551315343?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113937740551315343/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/02/tired-of-typing-administrators.html#comment-form' title='13 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113937740551315343'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113937740551315343'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/02/tired-of-typing-administrators.html' title='Tired of Typing Administrator’s Password Repeatedly?'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>13</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113903305845510493</id><published>2006-02-04T00:56:00.000-05:00</published><updated>2006-05-05T11:10:13.836-04:00</updated><title type='text'>Give Monad a Voice: out-voice cmdlet</title><content type='html'>This script will get objects from &lt;b&gt;pipline&lt;/b&gt; and output as voice using &lt;b&gt;Text To Speech (TTS) engine&lt;/b&gt;. If set $SaveToWav to $true, it  will output to a serial of WAV files.&lt;br /&gt;&lt;br /&gt;WindowsXP shipped with both speech recognition and Text To Speech Engine. TTS engine  (&lt;span style="font-weight: bold;"&gt;sapi.dll&lt;/span&gt;) takes text as input and output that text as spoken audio. Although WinFX will contain the fully managed API for speech, at this moment, I have to use (ugly) com interop. To make things easier, I generate a managed API libaray (SpeechLib.dll) using &lt;span style="font-weight: bold;"&gt;tlbimp.exe&lt;/span&gt;, a tool in .NET 2.0 SDK.&lt;br /&gt;&lt;blockquote&gt;set-alias tlbimp "C:\Program Files\Microsoft.NET\SDK\v2.0\bin\tlbimp.exe"&lt;br /&gt;tlbimp "C:\Program Files\Common Files\Microsoft Shared\Speech\sapi.dll" `&lt;br /&gt; /out:SpeechLib.dll /namespace:SpeechLib&lt;br /&gt;&lt;/blockquote&gt;You will see some warnings talking about type error. Just ignore them because we will not use those problemetic class today. Then we can load the libray, initialize a &lt;span style="font-style: italic;"&gt;SpeechLib.SpVoiceClass&lt;/span&gt; object and call &lt;span style="font-style: italic;"&gt;Speak&lt;/span&gt; method.&lt;br /&gt;&lt;blockquote&gt;[Reflection.Assembly]::LoadFile("D:\msh\SpeechLib.dll")&lt;br /&gt;$SpVoice = new-object SpeechLib.SpVoiceClass&lt;br /&gt;$SpVoice.Speak("Hello", [SpeechLib.SpeechVoiceSpeakFlags]::SVSFDefault)&lt;br /&gt;&lt;/blockquote&gt;After using this cmdlet for a while, I found out that call &lt;span style="font-style: italic;"&gt;Speak&lt;/span&gt; method asynchronously is a good idea. While listen to your voice output (which could be lengthy and boring), you can still get a prompt and working with MSH.&lt;br /&gt;&lt;blockquote&gt;$SpVoice.Speak("Hello", [SpeechLib.SpeechVoiceSpeakFlags]::SVSFlagsAsync)&lt;br /&gt;&lt;/blockquote&gt;To get a .wav filename, I used &lt;span style="font-style: italic;"&gt;System.Windows.Forms.SaveFileDialog&lt;/span&gt; object&lt;br /&gt;&lt;blockquote&gt;$SaveFileD = new-object System.Windows.Forms.SaveFileDialog&lt;br /&gt;$SaveFileD.Filter = "All files (*.*)|*.*|wav files (*.wav)|*.wav";&lt;br /&gt;$SaveFileD.Title = "Save to a wave file";&lt;br /&gt;$SaveFileD.FilterIndex = 2;&lt;br /&gt;$SaveFileD.RestoreDirectory = true;&lt;br /&gt;if ($SaveFileD.ShowDialog() -eq [System.Windows.Forms.DialogResult]::OK)&lt;br /&gt;{&lt;br /&gt;      $FileName = $SaveFileD.FileName&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;To save to wav file, I use &lt;span style="font-style: italic;"&gt;SpeechLib.SpFileStreamClass&lt;/span&gt;&lt;br /&gt;&lt;blockquote&gt;$WaveFile = new-object SpeechLib.SpFileStreamClass&lt;br /&gt;$WaveFile.Open($FileNameS, [SpeechLib.SpeechStreamFileMode]::SSFMCreateForWrite, $false)&lt;br /&gt;$SpVoice.AudioOutputStream = $WaveFile&lt;br /&gt;$SpVoice.Speak($StringToSay, [SpeechLib.SpeechVoiceSpeakFlags]::SVSFlagsAsync)&lt;br /&gt;$SpVoice.WaitUntilDone([System.Threading.Timeout]::Infinite)&lt;br /&gt;$WaveFile.Close()&lt;br /&gt;&lt;/blockquote&gt;I use &lt;b&gt;$_&lt;/b&gt; to get object from pipline and use &lt;span style="font-weight: bold;"&gt;out-string&lt;/span&gt; cmdlet  to convert them to System.String object .&lt;br /&gt;&lt;blockquote&gt;$StringToSay = $_ | out-string&lt;br /&gt;&lt;/blockquote&gt;If you want to try it, do something like&lt;br /&gt;&lt;blockquote&gt;dir| select-object Name -first 4 | .\out-voice.msh&lt;br /&gt;get-eventlog Application -Newest 4 | .\out-voice.msh $true&lt;br /&gt;&lt;/blockquote&gt;Make sure the speaker on your computer is poweron and enabled. Make sure you use &lt;b&gt;select&lt;/b&gt; to format your results first. Otherwise you won't know what your computer are talking about. There is no guarantee that it would be fun. As I said before it could be lengthy and boring.&lt;br /&gt;&lt;blockquote&gt;###############################################################&lt;br /&gt;#&lt;br /&gt;# out-voice.msh&lt;br /&gt;# This script takes objects from pipline and output as voice using TTS engine.&lt;br /&gt;# If set $SaveToWav to $true, output to WAV file(s).&lt;br /&gt;#&lt;br /&gt;# Usage: "Hello", "Welcome to monad world" | out-voice &lt;br /&gt;#&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; "Hello", "Welcome to monad world" | out-voice $true&lt;br /&gt;#&lt;br /&gt;# from Tony http://mshforfun.blogspot.com/ &lt;br /&gt;#&lt;br /&gt;################################################################&lt;br /&gt;&lt;br /&gt;param ( [bool] $SaveToWav = $false )&lt;br /&gt;begin&lt;br /&gt;{&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; [void][Reflection.Assembly]::LoadFile("D:\msh\SpeechLib.dll")&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $SpVoice = new-object SpeechLib.SpVoiceClass&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $count = 0&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($SaveToWav)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [void] [Reflection.Assembly]::Load("System.Windows.Forms, Version=2.0.0.0, `&lt;br /&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; Culture=neutral, PublicKeyToken=b77a5c561934e089")&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $SaveFileD = new-object System.Windows.Forms.SaveFileDialog&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $SaveFileD.Filter = "All files (*.*)|*.*|wav files (*.wav)|*.wav";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $SaveFileD.Title = "Save to a wave file";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $SaveFileD.FilterIndex = 2;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $SaveFileD.RestoreDirectory = true;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($SaveFileD.ShowDialog() -eq [System.Windows.Forms.DialogResult]::OK) &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; $FileName = $SaveFileD.FileName&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; else&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; "Must Specify a wav file"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;&amp;nbsp;&amp;nbsp; break&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;process&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($_)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $count++&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $StringToSay = $_ | out-string&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; "$count: $StringToSay"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($SaveToWav)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $FileNameS = $FileName.Replace(".wav", $count.Tostring()+".wav")&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $WaveFile = new-object SpeechLib.SpFileStreamClass&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $WaveFile.Open($FileNameS, `&lt;br /&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; [SpeechLib.SpeechStreamFileMode]::SSFMCreateForWrite, $false)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $SpVoice.AudioOutputStream = $WaveFile&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [void]$SpVoice.Speak($StringToSay, `&lt;br /&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; [SpeechLib.SpeechVoiceSpeakFlags]::SVSFlagsAsync)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [void]$SpVoice.WaitUntilDone([System.Threading.Timeout]::Infinite)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $WaveFile.Close()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; else&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [void]$SpVoice.Speak($StringToSay, `&lt;br /&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; [SpeechLib.SpeechVoiceSpeakFlags]::SVSFlagsAsync)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; else&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; "null object"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;end&lt;br /&gt;{&lt;br /&gt;&amp;nbsp; "Number of objects successfully output: $count"&lt;br /&gt;}&lt;br /&gt;##############################################&lt;br /&gt;&lt;/blockquote&gt;Reference: &lt;a href="http://msdn.microsoft.com/coding4fun/inthebox/tts-hw/default.aspx"&gt;Code4Fun&lt;/a&gt;, &lt;a href="http://www.c-sharpcorner.com/Speech/TTSAppsInCSGAG.asp"&gt;C# Corner&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Have Fun!&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113903305845510493?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113903305845510493/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/02/give-monad-voice-out-voice-cmdlet.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113903305845510493'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113903305845510493'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/02/give-monad-voice-out-voice-cmdlet.html' title='Give Monad a Voice: out-voice cmdlet'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113892477761575493</id><published>2006-02-02T18:52:00.000-05:00</published><updated>2006-05-05T11:10:44.446-04:00</updated><title type='text'>Survival as a Non-Administrator: A Monad view</title><content type='html'>&lt;b&gt;&lt;span style="color:red;"&gt;DON'T ROOT AROUND!&lt;/span&gt;&lt;/b&gt;&lt;br /&gt;&lt;br /&gt;Remember the security rule NO.1  in unix world? It is also 100% rule NO.1 in windows world. Do you get some worms, viruses, spywares or adware in you windows box? You should blame yourself first if you logged in as an Adminstrator EVERYTIME EVERYDAY. It is you who let those malware bypass all windows security check and write themselves directly in system folder and registry. Do you really need Administrator privilege to read Emails or surf the internet? Or do you really need Administrator privilege to compile your code? If you want to write secure code, login as a limited user and find out how you code works. Don't rely on testing afterwards.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Reality check:&lt;/b&gt; &lt;ul&gt;&lt;li&gt;&lt;a href="http://blogs.msdn.com/uac/"&gt;Although Windows Vista is supposed to provide better user experence for limited user account,&lt;/a&gt; frankly speaking, using windows 2000 / xp / 2003 as limited user account is not easy and intuitive as Mac OS X or Linux . Default user in windows xp is a Administrator! &lt;/li&gt;&lt;li&gt;Being an Administrator for so long, you have indulged yourself by that power. After "eating your own dog food", it isn't really that fun to be a non-privilege user. You found yourself trapped in a "jungle" and can't breathe.&lt;/li&gt;&lt;/ul&gt; But calm down man! Don't point to that logout button so soon! There are plenty of ways to regain your power without logout. You can control your computer as Administrator and return back to your non-Administrator environment after you are done.&lt;br /&gt;&lt;br /&gt;Since this is a blog about MSH, I am going to talk about some solutions in MSH.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;1. -Credential Parameter&lt;/b&gt;&lt;br /&gt;It is good to see that (although still in beta stage) monad designers kept "running at least privilege" in mind. For example, they plan to implemetation -Credential parameter for file/registry provider. There are some buildin cmdlet using -Credential parameter. For example those Item cmdlet:&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : clear-item&lt;br /&gt;Definition : clear-item [-Path] String[] [-Force] [-Filter String] [-Include St&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ring[]] [-Exclude String[]] [-Credential MshCredential] [-Verbose]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [-Debug] [-ErrorAction ActionPreference] [-ErrorVariable String]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [-OutVariable String] [-OutBuffer Int32] [-WhatIf] [-Confirm]&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : copy-item&lt;br /&gt;Definition : copy-item [-Path] String[] [[-Destination] String] [-Container] [-&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Force] [-Filter String] [-Include String[]] [-Exclude String[]] [-&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Recurse] [-PassThru] [-Credential MshCredential] [-Verbose] [-Debu&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; g] [-ErrorAction ActionPreference] [-ErrorVariable String] [-OutVa&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; riable String] [-OutBuffer Int32] [-WhatIf] [-Confirm]&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : get-item&lt;br /&gt;Definition : get-item [-Path] String[] [-Filter String] [-Include String[]] [-E&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; xclude String[]] [-Force] [-Credential MshCredential] [-Verbose] [&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; -Debug] [-ErrorAction ActionPreference] [-ErrorVariable String] [-&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; OutVariable String] [-OutBuffer Int32]&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : invoke-item&lt;br /&gt;Definition : invoke-item [-Path] String[] [-Filter String] [-Include String[]]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [-Exclude String[]] [-Credential MshCredential] [-Verbose] [-Debug&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ] [-ErrorAction ActionPreference] [-ErrorVariable String] [-OutVar&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; iable String] [-OutBuffer Int32] [-WhatIf] [-Confirm]&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : move-item&lt;br /&gt;Definition : move-item [-Path] String[] [[-Destination] String] [-Force] [-Filt&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; er String] [-Include String[]] [-Exclude String[]] [-PassThru] [-C&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; redential MshCredential] [-Verbose] [-Debug] [-ErrorAction ActionP&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; reference] [-ErrorVariable String] [-OutVariable String] [-OutBuff&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; er Int32] [-WhatIf] [-Confirm]&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : new-item&lt;br /&gt;Definition : new-item [-Path] String[] [-Type String] [-Value Object] [-Force]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [-Credential MshCredential] [-Verbose] [-Debug] [-ErrorAction Acti&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; onPreference] [-ErrorVariable String] [-OutVariable String] [-OutB&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; uffer Int32] [-WhatIf] [-Confirm]&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : remove-item&lt;br /&gt;Definition : remove-item [-Path] String[] [-Filter String] [-Include String[]]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [-Exclude String[]] [-Recurse] [-Force] [-Credential MshCredential&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ] [-Verbose] [-Debug] [-ErrorAction ActionPreference] [-ErrorVaria&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ble String] [-OutVariable String] [-OutBuffer Int32] [-WhatIf] [-C&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; onfirm]&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : rename-item&lt;br /&gt;Definition : rename-item [-Path] String [-Name] String [-Force] [-PassThru] [-C&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; redential MshCredential] [-Verbose] [-Debug] [-ErrorAction ActionP&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; reference] [-ErrorVariable String] [-OutVariable String] [-OutBuff&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; er Int32] [-WhatIf] [-Confirm]&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : set-item&lt;br /&gt;Definition : set-item [-Path] String[] [[-Value] Object] [-Force] [-PassThru] [&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; -Filter String] [-Include String[]] [-Exclude String[]] [-Credenti&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; al MshCredential] [-Verbose] [-Debug] [-ErrorAction ActionPreferen&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ce] [-ErrorVariable String] [-OutVariable String] [-OutBuffer Int3&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; 2] [-WhatIf] [-Confirm]&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Unfortunately, if you try to use them now, you will get an error. &lt;br /&gt;&lt;br /&gt;invoke-item : Dynamic parameters for the Cmdlet cannot be retrieved. Invocation of MakePath on the 'FileSystem' provider failed for path ''. Cannot call method. The provider does not support the use of credentials.&lt;br /&gt;&lt;br /&gt;According to&lt;font color="#000000"&gt;&lt;b&gt; &lt;a href="http://groups.google.com/group/microsoft.public.windows.server.scripting/browse_frm/thread/9a3acd1644a14369"&gt;Abhishek Agrawal [MSFT]&lt;/a&gt; :&lt;/b&gt;&lt;/font&gt; "FileSystem and Registry provider do not supprt Credential parameter for V1. We plan to address this in V2. For now you will need to start an elevated MSH window using runas.exe (or Process.Start api) and carry out the required operations there. "&lt;br /&gt;&lt;br /&gt;So you have to wait new version of monad which can utilize the -credential parameter for FileSystem and Registry provider.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;2. System.Diagnostics.Process.Start() method&lt;/b&gt;&lt;br /&gt;.NET framework 2.0 provide three new overloads of System.Diagnostics.Process.Start() method which (might use CreateProcessAsUser Win32 API to) start a process as different user:&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;public static Process Start ( ProcessStartInfo &lt;i&gt;startInfo&lt;/i&gt;)&lt;br /&gt;public static Process Start ( string &lt;i&gt;fileName&lt;/i&gt;, string &lt;i&gt;userName&lt;/i&gt;, SecureString &lt;i&gt;password&lt;/i&gt;, string &lt;i&gt;domain&lt;/i&gt;)&lt;br /&gt;public static Process Start (string &lt;i&gt;fileNam&lt;/i&gt;e, string &lt;i&gt;arguments&lt;/i&gt;, string &lt;i&gt;userName&lt;/i&gt;, SecureString &lt;i&gt;password&lt;/i&gt;, string &lt;i&gt;domain&lt;/i&gt;)&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;They take string type username and &lt;b&gt;SecureString&lt;/b&gt; type password. (ProcessStartInfo.Password is a &lt;b&gt;SecureString&lt;/b&gt;) SecureString is a new creature in .NET 2.0. How we can get an instance of SecureString? Using &lt;b&gt;get-credential&lt;/b&gt; cmdlet we can easily and securely package username and password and then pass them to System.Diagnostics.Process.Start() method. See &lt;a href="http://mshforfun.blogspot.com/2006/01/dreaming-of-su-in-msh.html"&gt;my previous blog entry&lt;/a&gt; for details.&lt;br /&gt;&lt;br /&gt;Armed with this tool, we can do almost anything in MSH command line. For example, set file system access control rule, kill a process, modify registry or start a service.&lt;br /&gt;&lt;br /&gt;Remember you need to type: &lt;blockquote&gt;exit&lt;/blockquote&gt;to stop this msh.exe process. You don't want to leave a shell with Administrator privilege to someone else, do you?&lt;br /&gt;&lt;br /&gt;&lt;b&gt;3. Have to use GUI?&lt;/b&gt;&lt;br /&gt;Well, I have to admit that sometimes command line is just not good enough. For example, you want to &lt;span style="font-weight: bold;"&gt;disable wireless network connection&lt;/span&gt;. There is no way to use &lt;b&gt;runas.exe&lt;/b&gt; or do &lt;b&gt;shift-click&lt;/b&gt; tricks. Even if you started msh.exe as an Administrator, invoking &lt;span style="font-weight: bold;"&gt;ncpa.cpl&lt;/span&gt; will not give you "Network Connections" in control panel. The only choice is to use other command line tools like: devcon.exe (from &lt;a href="http://support.microsoft.com/default.aspx?scid=kb;EN-US;Q311272"&gt;microsoft&lt;/a&gt;) or network.exe (from &lt;a href="http://www.wingnutsoftware.com/utility.html"&gt;Wingnut Software&lt;/a&gt;) &lt;span style="font-weight: bold;"&gt;If you know how to do this in MSH script, please tell me, please!&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;ps:&lt;/b&gt; I found this &lt;a href="http://sqljunkies.com/weblog/donkiely/archive/2004/07/29/3680.aspx"&gt;funny story&lt;/a&gt;. The author had same problem as mine.&lt;br /&gt;&lt;br /&gt;But there is always a work around: With help of monad, we can easily get a GUI shell(explorer.exe) as Administrator. &lt;br /&gt;&lt;br /&gt;1) using &lt;a href="http://mshforfun.blogspot.com/2006/01/dreaming-of-su-in-msh.html"&gt;su.msh&lt;/a&gt; to get a msh prompt as Adminstrator&lt;br /&gt;2) run following commands&lt;br /&gt;&lt;blockquote&gt;stop-process -ProcessName explorer&lt;br /&gt;explorer.exe&lt;br /&gt;&lt;/blockquote&gt;Welcome to Administrator's Explorer! Go to control panel and disable wireless network connection as you wish. But remember:&lt;br /&gt;&lt;br /&gt;a) Explorer.exe will reload itself quickly after been killed, so you better write those command in msh script.&lt;br /&gt;&lt;br /&gt;b) After you finish your work, you need to return to your original explorer environment. You can't kill the explorer.exe process within &lt;b&gt;task manager&lt;/b&gt; because you are a limited user (remember?). Instead, you can&lt;br /&gt;&lt;blockquote&gt;stop-process -ProcessName explorer&lt;br /&gt;&lt;/blockquote&gt;in the &lt;span style="font-weight: bold;"&gt;msh as Adminstrator&lt;/span&gt;&lt;br /&gt;What? you have already closed that window? Run &lt;a href="http://mshforfun.blogspot.com/2006/01/dreaming-of-su-in-msh.html"&gt;su.msh&lt;/a&gt; again!&lt;br /&gt;then you either wait explorer.exe to reload itself or start explorer (Do this as a non-Administrator!) by&lt;br /&gt;&lt;blockquote&gt;explorer.exe&lt;/blockquote&gt;&lt;br /&gt;&lt;font color="#ff0000"&gt;Added on 26th, Feb 2006&lt;/font&gt;&lt;br /&gt;You can change registry to start exporler.exe in seperate process (so there is no need to kill your original explorer.exe process):&lt;br /&gt;First, run &lt;a href="http://mshforfun.blogspot.com/2006/01/dreaming-of-su-in-msh.html"&gt;su.msh&lt;/a&gt;&lt;BR /&gt;Then modify registry:&lt;br /&gt;&lt;blockquote&gt;set-property HKCU:\Software\Microsoft\Windows\CurrentVersion\Explorer\Advanced -property SeparateProcess -value 1 -force&lt;/blockquote&gt;&lt;br /&gt;Without reboot, we can now start new explorer.exe windows as Administrator:&lt;br /&gt;&lt;blockquote&gt;explorer.exe&lt;/blockquote&gt;&lt;br /&gt;You can even use &lt;span style="font-weight:bold;"&gt;System.Diagnostics.Process.Start()&lt;/span&gt; method to start a explorer.exe process from your msh runing as limited user.&lt;br /&gt;&lt;font color="#ff0000"&gt;Added on 26th, Feb 2006&lt;/font&gt;&lt;br /&gt;&lt;br /&gt;Have Fun!&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113892477761575493?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113892477761575493/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/02/survival-as-non-administrator-monad.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113892477761575493'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113892477761575493'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/02/survival-as-non-administrator-monad.html' title='Survival as a Non-Administrator: A Monad view'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113834286346763497</id><published>2006-01-27T01:16:00.000-05:00</published><updated>2006-05-05T11:11:36.626-04:00</updated><title type='text'>Dreaming of SU in MSH?</title><content type='html'>&lt;font color="#ff0000"&gt;(Added on Mar 6th)&lt;/Font&gt; There is a follow up post on this topic &lt;a href="http://mshforfun.blogspot.com/2006/03/release-of-mshforfunsecurity-mshsnapin.html"&gt;here&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Shame on myself! I should do more research before posting a blog entry. MoW already had a &lt;a href="http://mow001.blogspot.com/2005/10/runas-with-loading-profile-script-in.html"&gt;similar script&lt;/a&gt; a couple of months ago.&lt;/span&gt; &lt;br /&gt;&lt;br /&gt;Want to run a MSH script as another windows user? You got it now! I am not talking about Runas.exe. It is a MSH script to start new msh.exe process with a differnt windows identity. Just like su.exe in Linux.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;###########################################&lt;br /&gt;# File Name: su.msh&lt;br /&gt;# Launch a new msh.exe with someone else's identity&lt;br /&gt;# from tony http://mshforfun.blogspot.com/&lt;br /&gt;###########################################&lt;br /&gt;$SuAccount = get-credential&lt;br /&gt;$StartInfo = new-object System.Diagnostics.ProcessStartInfo&lt;br /&gt;$StartInfo.FileName = "msh.exe"&lt;br /&gt;$StartInfo.UserName = $SuAccount.UserName&lt;br /&gt;$StartInfo.Password = $SuAccount.Password&lt;br /&gt;$StartInfo.LoadUserProfile = $true&lt;br /&gt;$StartInfo.UseShellExecute = $false&lt;br /&gt;$StartInfo.WorkingDirectory = (get-location).Path&lt;br /&gt;[System.Diagnostics.Process]::Start($StartInfo)&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;span style="color: rgb(255, 0, 0);"&gt;Added on 23rd Feb 2006, 08:40&lt;/span&gt;&lt;br /&gt;Jeffrey Snover Suggested to add the following line: &lt;br /&gt;&lt;blockquote&gt;$StartInfo.Arguments="-noexit -command `$Host.UI.RawUI.WindowTitle=\`"Microsoft Command Shell ($($SuAccount.UserName)) \`""&lt;/blockquote&gt;&lt;span style="color: rgb(255, 0, 0);"&gt;Added on 23rd Feb 2006, 08:40&lt;/span&gt;&lt;br /&gt;&lt;br&gt;&lt;br /&gt;&lt;span style="color: rgb(255, 0, 0);"&gt;Added on 27th Jan 2006, 15:46&lt;/span&gt;&lt;br /&gt;In Monad beta3 version, the default behavior of get-credential was changed to "CredUI". "CredUI returns a username with "\" prepended. When passing that to the Process.Start method, it has intermittent difficulty dealing with that form of a username. " --Lee Holmes&lt;br /&gt;To change it back to CLI, run following script:&lt;br /&gt;&lt;blockquote&gt;new-property HKLM:\SOFTWARE\Microsoft\MSH\1\ShellIds `&lt;br /&gt;-property ConsolePrompting -value "True" -force&lt;/blockquote&gt;&lt;br /&gt;See newsgroup thread &lt;a target="_blank" href="http://groups.google.com/group/microsoft.public.windows.server.scripting/browse_frm/thread/b6dad897d013e6d1/f1dcb95582a8d61b#f1dcb95582a8d61b"&gt;here &lt;/a&gt;for details. Also checkout &lt;a target="_blank" href="http://monadblog.blogspot.com/2006/01/msh-change-default-get-credential.html"&gt;::: MSH ::: Blog Entry&lt;/a&gt; for this issue.&lt;br /&gt;&lt;span style="color: rgb(255, 0, 0);"&gt;/Added on 27th Jan 2006, 15:46&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;So if you were a non-privilege user "testac" , you run &lt;a href="http://mshforfun.blogspot.com/2006/01/clone-of-idwhoami-in-msh.html"&gt;id.msh&lt;/a&gt;:&lt;br /&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;UserSID= S-1-5-21&lt;span style="color: rgb(102, 102, 102);"&gt;-xxxxxxxxx-xxxxxxxxxx-xxxxxxxxxx-xxx&lt;/span&gt; (Domain\testac)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;AuthenticationType= NTLM&lt;/span&gt;&lt;br /&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;ImpersonationLevel= None&lt;br /&gt;Token= xxxx&lt;br /&gt;Groups=&lt;br /&gt;       GroupSID= S-1-5-21&lt;span style="color: rgb(102, 102, 102);"&gt;-xxxxxxxxx-xxxxxxxxxx-xxxxxxxxxx-xxx &lt;/span&gt;(Domain\None)&lt;br /&gt;       GroupSID= S-1-1-0 (Everyone)&lt;br /&gt;       GroupSID= S-1-5-32-545 (BUILTIN\Users)&lt;br /&gt;       GroupSID= S-1-5-4 (NT AUTHORITY\INTERACTIVE)&lt;br /&gt;       GroupSID= S-1-5-11 (NT AUTHORITY\Authenticated Users)&lt;br /&gt;       GroupSID= S-1-2-0 (LOCAL)&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;After &lt;span style="font-weight: bold;"&gt;su&lt;/span&gt; to an Administrator user "tony". Then you run &lt;a href="http://mshforfun.blogspot.com/2006/01/clone-of-idwhoami-in-msh.html"&gt;id.msh&lt;/a&gt; again in new msh.exe window:&lt;br /&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;UserSID= S-1-5-21-xxxxxxxxx-xxxxxxxxxx-xxxxxxxxxx-xxxx (Domain\tony)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;AuthenticationType= MICROSOFT_AUTHENTICATION_PACKAGE_V1_0&lt;br /&gt;&lt;/span&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;ImpersonationLevel= None&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;&lt;br /&gt;Token= xxxx&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;&lt;br /&gt;Groups=&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;      &lt;br /&gt;       GroupSID= S-1-5-21-xxxxxxxxx-xxxxxxxxxx-xxxxxxxxxx-xxx (Domain\None)&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;&lt;br /&gt;       GroupSID= S-1-1-0 (Everyone)&lt;/span&gt;&lt;br /&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-5-32-544 (BUILTIN\Administrators)&lt;/span&gt;&lt;br /&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-5-32-545 (BUILTIN\Users)&lt;/span&gt;&lt;br /&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-5-4 (NT AUTHORITY\INTERACTIVE)&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;&lt;br /&gt;       GroupSID= S-1-5-11 (NT AUTHORITY\Authenticated Users)&lt;/span&gt;&lt;br /&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-2-0 (LOCAL)&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Have Fun!&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113834286346763497?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113834286346763497/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/dreaming-of-su-in-msh.html#comment-form' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113834286346763497'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113834286346763497'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/dreaming-of-su-in-msh.html' title='Dreaming of SU in MSH?'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113816417971762515</id><published>2006-01-24T23:41:00.000-05:00</published><updated>2006-05-05T11:12:15.126-04:00</updated><title type='text'>A Clone of id/whoami in MSH</title><content type='html'>I would like to have something like id/whoami in linux while working with MSH. So I  wrote a simple script.&lt;br /&gt;&lt;blockquote&gt;##############################################&lt;br /&gt;# File Name: id.msh&lt;br /&gt;# Return User and Group information of current logon user&lt;br /&gt;# By Tony http://mshforfun.blogspot.com&lt;br /&gt;##############################################&lt;br /&gt;$me=[System.Security.Principal.WindowsIdentity]::GetCurrent()&lt;br /&gt;"UserSID= " + $me.User + " (" + $me.Name + ")"&lt;br /&gt;"AuthenticationType= " + $me.AuthenticationType&lt;br /&gt;"ImpersonationLevel= " + $me.ImpersonationLevel&lt;br /&gt;"Token= " + $me.Token&lt;br /&gt;"Groups= "&lt;br /&gt;foreach($Group in $me.Groups)&lt;br /&gt;{&lt;br /&gt;     "`tGroupSID= " + $Group + " (" + $Group.Translate([System.Security.Principal.NTAccount]) + ")"&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt; Output looks like:&lt;br /&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;UserSID= S-1-5-21-xxxxxxxxx-xxxxxxxxxx-xxxxxxxxxx-xxxx (Domain\me)&lt;br /&gt;&lt;/span&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;AuthenticationType= NTLM&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;&lt;br /&gt;ImpersonationLevel= None&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;&lt;br /&gt;Token= xxxx&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;&lt;br /&gt;Groups=&lt;br /&gt;&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-5-21-xxxxxxxxx-xxxxxxxxxx-xxxxxxxxxx-xxx (Domain\None)&lt;/span&gt;&lt;br /&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-1-0 (Everyone)&lt;br /&gt;&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-5-32-545 (BUILTIN\Users)&lt;br /&gt;&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-5-4 (NT AUTHORITY\INTERACTIVE)&lt;br /&gt;&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-5-11 (NT AUTHORITY\Authenticated Users)&lt;br /&gt;&lt;/span&gt; &lt;span style="color: rgb(102, 102, 102);"&gt;        GroupSID= S-1-2-0 (LOCAL)&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;Well, write a clone of &lt;span style="font-weight: bold;"&gt;who&lt;/span&gt; would be fun. Any volunteer?&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113816417971762515?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113816417971762515/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/clone-of-idwhoami-in-msh.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113816417971762515'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113816417971762515'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/clone-of-idwhoami-in-msh.html' title='A Clone of id/whoami in MSH'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113742657368119484</id><published>2006-01-16T10:44:00.000-05:00</published><updated>2006-05-05T11:12:37.026-04:00</updated><title type='text'>Combination Rights, Inheritance and Propagation Settings of File System Access Rules</title><content type='html'>A more complexed example of combination rights, inheritance and propagation settings of access rules for directory.&lt;br /&gt;&lt;br /&gt;Yesterday, I happened to find a code example of manipulating ACLs for .NET framework 1.0: &lt;a href="http://www.gotdotnet.com/Community/UserSamples/Details.aspx?SampleGuid=e6098575-dda0-48b8-9abf-e0705af065d9"&gt;ACLs in .NET: A C# library containing wrapper classes for ACL, ACE, Security descriptors, Security Attributes, Access tokens, etc.&lt;/a&gt; It is so complicated to working on platform invokation. As you can see from my previous blog entry &lt;a href="http://mshforfun.blogspot.com/2005/12/play-with-acl-in-msh.html"&gt;Play with ACL in MSH&lt;/a&gt;, &lt;a href="http://mshforfun.blogspot.com/2006/01/play-with-acl-in-msh-continued.html"&gt;Play with ACL in MSH (continued)&lt;/a&gt; and /\/\o\/\/'s blog entry &lt;a href="http://mow001.blogspot.com/2006/01/adding-simple-accesrule-to-file-acl-in.html"&gt;Adding a Simple AccesRule to a file ACL in MSH&lt;/a&gt;, with&amp;nbsp; .NET 2.0 things getting much easier. Today I am going to dig a little deeper and talk about more&amp;nbsp; complex example.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold; color: rgb(255, 0, 0);"&gt;1. &lt;/span&gt;We have to deal with FileSystemRights enumeration when creating a new FileSystemAccessRule object. We can see from following that FileSystemRights contain 23 names:&lt;br /&gt;&lt;blockquote&gt;[system.enum]::getnames([System.Security.AccessControl.FileSystemRights])&lt;br /&gt;&lt;/blockquote&gt;ListDirectory&lt;br /&gt;ReadData&lt;br /&gt;WriteData&lt;br /&gt;CreateFiles&lt;br /&gt;CreateDirectories&lt;br /&gt;AppendData&lt;br /&gt;ReadExtendedAttributes&lt;br /&gt;WriteExtendedAttributes&lt;br /&gt;Traverse&lt;br /&gt;ExecuteFile&lt;br /&gt;DeleteSubdirectoriesAndFiles&lt;br /&gt;ReadAttributes&lt;br /&gt;WriteAttributes&lt;br /&gt;Write&lt;br /&gt;Delete&lt;br /&gt;ReadPermissions&lt;br /&gt;Read&lt;br /&gt;ReadAndExecute&lt;br /&gt;Modify&lt;br /&gt;ChangePermissions&lt;br /&gt;TakeOwnership&lt;br /&gt;Synchronize&lt;br /&gt;FullControl&lt;br /&gt;&lt;br /&gt;FileSystemRights enumeration has a &lt;span style="font-weight: bold;"&gt;FlagsAttribute&lt;/span&gt; attribute that allows a bitwise combination of its member values. In MSH, "&lt;span style="font-weight: bold;"&gt;-bor&lt;/span&gt;" is used as "&lt;span style="font-weight: bold;"&gt;Bitwise OR&lt;/span&gt;" Operator. To better understand that, we can find from following example that "&lt;span style="font-weight: bold;"&gt;Read&lt;/span&gt;" actually means &lt;span style="font-weight: bold;"&gt;ReadData | ReadExtendedAttributes | ReadAttributes |ReadPermissions&lt;/span&gt;.&lt;br /&gt;&lt;blockquote&gt;[int]([System.Security.AccessControl.FileSystemRights]::Read)&lt;br /&gt;&lt;/blockquote&gt;131209&lt;br /&gt;&lt;blockquote&gt;[System.Security.AccessControl.FileSystemRights]::ReadData `&lt;br /&gt;-bor [System.Security.AccessControl.FileSystemRights]::ReadExtendedAttributes `&lt;br /&gt;-bor [System.Security.AccessControl.FileSystemRights]::ReadAttributes `&lt;br /&gt;-bor [System.Security.AccessControl.FileSystemRights]::ReadPermissions &lt;br /&gt;&lt;/blockquote&gt;131209&lt;br /&gt;&lt;br /&gt;&lt;B&gt;Added on 2006-01-17 12:27&lt;/B&gt;&lt;br /&gt;&lt;font color="red"&gt;Marcel Comment:"A comma separated list of values cast can be cast to a flags enum."&lt;/font&gt;&lt;br /&gt;&lt;blockquote&gt;[System.Security.AccessControl.FileSystemRights] "ReadData, ReadExtendedAttributes, ReadAttributes, ReadPermissions"&lt;/blockquote&gt;&lt;br /&gt;Will do same thing! &lt;br /&gt;&lt;br /&gt;So it is easier to use the combination values such as &lt;span style="font-weight: bold;"&gt;FullControl&lt;/span&gt;, &lt;span style="font-weight: bold;"&gt;Read&lt;/span&gt; and &lt;span style="font-weight: bold;"&gt;Write&lt;/span&gt;, rather than specifying each component value separately. But we still can build a custumized value such as "Read OR Write" as below.&lt;br /&gt;&lt;blockquote&gt;$Rights= [System.Security.AccessControl.FileSystemRights]::Read `&lt;br /&gt;-bor [System.Security.AccessControl.FileSystemRights]::Write&lt;br /&gt;&lt;/blockquote&gt;&lt;span style="color: rgb(255, 0, 0); font-weight: bold;"&gt;2. &lt;/span&gt;All of our previous examples were simple because we never deal with  inheritance and propagation settings. If a directroy contain both files and child directory, things get more compicated. Every access rule is either explicit or inherited: inherited rules come from a parent container while explicit rules are added by user later on. So you can only manipulate its explicit rules.&lt;br /&gt;There are two inheritance flags: container inherit (CI), object inherit (OI) and None.&lt;br /&gt;There are two propagation flags: inherit only (IO), no-propagate inherit (NP) and None.&lt;br /&gt;&lt;blockquote&gt;$Inherit=[System.Security.AccessControl.InheritanceFlags]::ContainerInherit `&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; -bor [System.Security.AccessControl.InheritanceFlags]::ObjectInherit&lt;br /&gt;$Prop=[System.Security.AccessControl.PropagationFlags]::InheritOnly&lt;br /&gt;&lt;/blockquote&gt;Now we can construct our access rule and set it to a directory:&lt;br /&gt;&lt;blockquote&gt;# set AccessControlType : Allow / Deny&lt;br /&gt;$Access=[System.Security.AccessControl.AccessControlType]::Allow&lt;br /&gt;# create new access rule&lt;br /&gt;$AccessRule = new-object System.Security.AccessControl.FileSystemAccessRule `&lt;br /&gt;("testac",$Rights,$Inherit,$Prop,$Access)&lt;br /&gt;# validate access rule&lt;br /&gt;$Sid = $AccessRule.IdentityReference.Translate`&lt;br /&gt;([System.Security.Principal.securityidentifier])&lt;br /&gt;$ACL=get-acl D:\msh\tmp&lt;br /&gt;$ACL.AddAccessRule($AccessRule)&lt;br /&gt;set-acl -AclObject $ACL -Path D:\msh\tmp&lt;br /&gt;&lt;br /&gt;&lt;/blockquote&gt;&amp;nbsp;&lt;span style="font-weight: bold; color: rgb(255, 0, 0);"&gt;3. &lt;/span&gt;What if you do &lt;span style="font-weight: bold;"&gt;NOT&lt;/span&gt; want to inherit access rules from you parents?&lt;span style="font-family: monospace;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;blockquote&gt;$ACL=get-acl D:\msh\tmp&lt;br /&gt;$ACL.SetAccessRuleProtection(&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; # changes from parent won't propagate&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $true, &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; # do not keep current inheritance settings&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $false ); &lt;br /&gt;set-acl -AclObject $ACL -Path D:\msh\tmp&lt;br /&gt;&lt;/blockquote&gt;Reference: &lt;a href="http://msdn.microsoft.com/msdnmag/issues/04/11/AccessControlinNET/default.aspx"&gt;Manage Access to Windows Objects with ACLs and the .NET Framework &lt;/a&gt;&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113742657368119484?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113742657368119484/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/combination-rights-inheritance-and.html#comment-form' title='5 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113742657368119484'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113742657368119484'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/combination-rights-inheritance-and.html' title='Combination Rights, Inheritance and Propagation Settings of File System Access Rules'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>5</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113718906267830978</id><published>2006-01-13T16:51:00.000-05:00</published><updated>2006-01-13T22:38:54.216-05:00</updated><title type='text'>Use Search-Entrez Cmdlet and Format Results</title><content type='html'>&lt;div xmlns="http://www.w3.org/1999/xhtml"&gt;In my previous blog entry &lt;a href="http://mshforfun.blogspot.com/2006/01/author-monad-cmdlet-as-web-service.html"&gt;Author a Monad Cmdlet as Web Service Client&lt;/a&gt;, I created a cmdlet &lt;span style="font-weight: bold;"&gt;Search-Entrez&lt;/span&gt;. Let's see what we can do with this cmdlet.&lt;br/&gt;&lt;blockquote&gt;get-command search-entrez | format-list&lt;br/&gt;&lt;/blockquote&gt;Name : search-entrez&lt;br/&gt;CommandType : Cmdlet&lt;br/&gt;Definition : search-entrez [-Database] String [-Keywords] String [[-MaxRecor&lt;br/&gt; d] String] [[-Email] String] [[-Field] String] [[-RelativeDate]&lt;br/&gt; String] [[-MinimumDate] String] [[-MaximumDate] String] [[-Dat&lt;br/&gt; eType] String] [-Verbose] [-Debug] [-ErrorAction ActionPreferen&lt;br/&gt; ce] [-ErrorVariable String] [-OutVariable String] [-OutBuffer I&lt;br/&gt; nt32] [-WhatIf] [-Confirm]&lt;br/&gt;&lt;br/&gt;Path :&lt;br/&gt;AssemblyInfo :&lt;br/&gt;DLL : D:\msh\Entrez-mshsnapin.dll&lt;br/&gt;HelpFile : Entrez-mshsnapin.dll-Help.xml&lt;br/&gt;ParameterSets : {__AllParameterSets}&lt;br/&gt;Type : Entrez.SearchEntrezCmd&lt;br/&gt;Verb : search&lt;br/&gt;Noun : entrez&lt;br/&gt;&lt;br/&gt;&lt;span style="font-weight: bold;"&gt;Database&lt;/span&gt;: the Entrez database name (can be pubmed, protein, nucleotide, nuccore, nucgss, nucest, structure, genome, books, cancerchromosomes, cdd, domains, gene, genomeprj, gensat, geo, gds, homologene, journals, mesh, ncbisearch, nlmcatalog, omia, omim, pmc, popset, probe, pcassay, pccompound, pcsubstance, snp, taxonomy, unigene, unists)&lt;br/&gt;&lt;br style="font-weight: bold;"/&gt;&lt;span style="font-weight: bold;"&gt;Keywords&lt;/span&gt;: the search strategy. All words should be URL encoded (that is to say blank should be +). Can be keywords plus "AND/OR/NOT" &lt;br/&gt;&lt;br/&gt;Other parameter is not mandatory. &lt;br/&gt;Using &lt;span style="font-weight: bold;"&gt;MaximumRecord&lt;/span&gt; would limit numbers of results returned to you.&lt;br/&gt;Using &lt;span style="font-weight: bold;"&gt;Email &lt;/span&gt;parameter would help NCBI server inform you if something went wrong.&lt;br/&gt;&lt;br/&gt;&lt;blockquote&gt;$resultSummary=search-entrez pubmed "cancer+T+cell" -MaxRecord 10 -Email test@test.com -verbose&lt;br/&gt;&lt;/blockquote&gt;&lt;span style="color: rgb(51, 255, 51); font-weight: bold;"&gt;VERBOSE: Searching Entrez database...&lt;/span&gt;&lt;br style="color: rgb(51, 255, 51); font-weight: bold;"/&gt;&lt;span style="color: rgb(51, 255, 51); font-weight: bold;"&gt;Database: pubmed&lt;/span&gt;&lt;br style="color: rgb(51, 255, 51); font-weight: bold;"/&gt;&lt;span style="color: rgb(51, 255, 51); font-weight: bold;"&gt;Keywords: cancer+T+cell&lt;/span&gt;&lt;br style="color: rgb(51, 255, 51); font-weight: bold;"/&gt;&lt;span style="color: rgb(51, 255, 51); font-weight: bold;"&gt;VERBOSE: Creating Entrez WebService...&lt;/span&gt;&lt;br style="color: rgb(51, 255, 51); font-weight: bold;"/&gt;&lt;span style="color: rgb(51, 255, 51); font-weight: bold;"&gt;VERBOSE: Submit search...&lt;/span&gt;&lt;br style="color: rgb(51, 255, 51); font-weight: bold;"/&gt;&lt;span style="color: rgb(51, 255, 51); font-weight: bold;"&gt;VERBOSE: Number of results item found:51521&lt;/span&gt;&lt;br style="color: rgb(51, 255, 51); font-weight: bold;"/&gt;&lt;span style="color: rgb(51, 255, 51); font-weight: bold;"&gt;VERBOSE: Getting results summary...&lt;/span&gt;&lt;br style="color: rgb(51, 255, 51); font-weight: bold;"/&gt;&lt;span style="color: rgb(51, 255, 51); font-weight: bold;"&gt;VERBOSE: Number of item retrieved:10&lt;/span&gt;&lt;br style="color: rgb(51, 255, 51); font-weight: bold;"/&gt;&lt;span style="color: rgb(51, 255, 51); font-weight: bold;"&gt;VERBOSE: Write results to pipline...&lt;/span&gt;&lt;br/&gt;&lt;br/&gt;Because I was too lazy to write code for results parsing, I just emitted an &lt;span style="font-weight: bold;"&gt;eUtils.eSummaryResultType&lt;/span&gt; object to monad pipline, which make search-Entrez cmdlet return a non-human-readable output. &lt;br/&gt;&lt;blockquote&gt;$resultSummary | format-list&lt;br/&gt;&lt;/blockquote&gt;ERROR :&lt;br/&gt;DocSum : {16408214, 16407851, 16406172, 16404742, 16404738, 16404427, 16403911, 16403282, 16401550, 16399573}&lt;br/&gt;&lt;br/&gt;Where &lt;span style="font-weight: bold;"&gt;ERROR &lt;/span&gt;is a string object for error and &lt;span style="font-weight: bold;"&gt;Docsum&lt;/span&gt; is a collection of DocSumType objects.&lt;br/&gt;&lt;blockquote&gt;public class DocSumType { &lt;br/&gt; private string idField; &lt;br/&gt; private ItemType[] itemField; &lt;br/&gt; public string Id {&lt;br/&gt; get {return this.idField;}&lt;br/&gt; set {this.idField = value;}}&lt;br/&gt; public ItemType[] Item {&lt;br/&gt; get {return this.itemField;}&lt;br/&gt; set {this.itemField = value;}}&lt;br/&gt;}&lt;br/&gt;&lt;/blockquote&gt;To make things even more complicated, the DocSumType.ItemType is a collection of &lt;span style="font-weight: bold;"&gt;NESTED&lt;/span&gt; ItemType object. As you can see &lt;span style="font-weight: bold;"&gt;ItemType.Items&lt;/span&gt; is also a collection of &lt;span style="font-weight: bold;"&gt;ItemType&lt;/span&gt; objects. &lt;br/&gt;&lt;blockquote&gt;public class ItemType { &lt;br/&gt; private ItemType[] itemsField; &lt;br/&gt; private string[] textField; &lt;br/&gt; private string nameField; &lt;br/&gt; private ItemTypeType typeField;&lt;br/&gt; public ItemType[] Items {&lt;br/&gt; get {return this.itemsField;}&lt;br/&gt; set {this.itemsField = value;}}&lt;br/&gt; public string[] Text {&lt;br/&gt; get {return this.textField;}&lt;br/&gt; set {this.textField = value;}}&lt;br/&gt; public string Name {&lt;br/&gt; get {return this.nameField;}&lt;br/&gt; set {this.nameField = value;}}&lt;br/&gt; public ItemTypeType Type {&lt;br/&gt; get {return this.typeField;}&lt;br/&gt; set {this.typeField = value;}}&lt;br/&gt;}&lt;br/&gt;&lt;/blockquote&gt;The good news is that they seem to only nest &lt;span style="font-weight: bold;"&gt;TWO&lt;/span&gt; levels deep for pubmed results. So I write a script to format results.&lt;br/&gt;&lt;blockquote&gt;# Format-eSummary.msh&lt;br/&gt;# Script to format (pubmed) results from Search-Entrez cmdlet&lt;br/&gt;#requires -MshSnapIn EntrezSnapin&lt;br/&gt;param &lt;br/&gt;(&lt;br/&gt; $Summary =$(throw "Please specify an eUtils.eSummaryResultType object to parise.")&lt;br/&gt;)&lt;br/&gt;if ($Summary.DocSum.Length -eq 0)&lt;br/&gt;{&lt;br/&gt; "No hits found!"&lt;br/&gt; return 1&lt;br/&gt;}&lt;br/&gt;foreach ($sum in $Summary.DocSum)&lt;br/&gt;{&lt;br/&gt; "Primary IDs:" + $sum.Id&lt;br/&gt; foreach ($Item in $sum.Item)&lt;br/&gt; {&lt;br/&gt;  $Item.Name + ": " + $Item.Text&lt;br/&gt;  if ($Item.Items)&lt;br/&gt;  {&lt;br/&gt;   foreach($ChildItem in $Item.Items)&lt;br/&gt;   {&lt;br/&gt;    "`t" + $ChildItem.Name + ": "+ $ChildItem.Text &lt;br/&gt;   }&lt;br/&gt;  }&lt;br/&gt; } "====================================================="&lt;br/&gt;}&lt;br/&gt;return 0&lt;br/&gt;&lt;/blockquote&gt;&lt;br/&gt;&lt;blockquote&gt;.\Format-eSummary.msh $resultSummary&lt;br/&gt;&lt;/blockquote&gt;&lt;br/&gt;Primary IDs:16408214&lt;br/&gt;PubDate: 2006 Jan 12&lt;br/&gt;EPubDate: 2006 Jan 12&lt;br/&gt;Source: Cancer Immunol Immunother&lt;br/&gt;AuthorList:&lt;br/&gt; Author: Prell RA&lt;br/&gt; Author: Gearin L&lt;br/&gt; Author: Simmons A&lt;br/&gt; Author: Vanroey M&lt;br/&gt; Author: Jooss K&lt;br/&gt;Title: The anti-tumor efficacy of a GM-CSF-secreting tumor cell vaccine is not&lt;br/&gt;inhibited by docetaxel administration.&lt;br/&gt;Volume:&lt;br/&gt;Issue:&lt;br/&gt;Pages: 1-9&lt;br/&gt;LangList:&lt;br/&gt; Lang: English&lt;br/&gt;NlmUniqueID: 8605732&lt;br/&gt;ISSN: 0340-7004&lt;br/&gt;ESSN: 1432-0851&lt;br/&gt;PubTypeList:&lt;br/&gt; PubType: Journal Article&lt;br/&gt;RecordStatus: PubMed - as supplied by publisher&lt;br/&gt;PubStatus: aheadofprint&lt;br/&gt;ArticleIds:&lt;br/&gt; doi: 10.1007/s00262-005-0116-4&lt;br/&gt; pubmed: 16408214&lt;br/&gt;DOI: 10.1007/s00262-005-0116-4&lt;br/&gt;History:&lt;br/&gt; received: 2005/11/08 00:00&lt;br/&gt; accepted: 2005/12/15 00:00&lt;br/&gt; aheadofprint: 2006/01/12 00:00&lt;br/&gt; pubmed: 2006/01/13 09:00&lt;br/&gt; medline: 2006/01/13 09:00&lt;br/&gt;References:&lt;br/&gt;HasAbstract: 1&lt;br/&gt;PmcRefCount: 0&lt;br/&gt;FullJournalName: Cancer immunology, immunotherapy : CII.&lt;br/&gt;SO: 2006 Jan 12;:1-9&lt;br/&gt;=====================================================&lt;br/&gt;Primary IDs:16407851&lt;br/&gt;PubDate: 2006 Jan 9&lt;br/&gt;EPubDate: 2006 Jan 9&lt;br/&gt;Source: Oncogene&lt;br/&gt;......&lt;/div&gt;&lt;br /&gt;&lt;p&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113718906267830978?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113718906267830978/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/use-search-entrez-cmdlet-and-format.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113718906267830978'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113718906267830978'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/use-search-entrez-cmdlet-and-format.html' title='Use Search-Entrez Cmdlet and Format Results'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113717563357524391</id><published>2006-01-12T22:35:00.000-05:00</published><updated>2006-05-05T11:13:21.596-04:00</updated><title type='text'>Author a Monad Cmdlet as Web Service Client</title><content type='html'>Steps to author a cmdlet, &lt;span style="font-weight: bold;"&gt;Search-Entrez&lt;/span&gt;, which works as NCBI eUtils web service client to build your own Entrez data pipeline.&lt;br /&gt;&lt;br /&gt;For those who don't use Entrez:&amp;nbsp; &lt;a style="font-weight: bold;" href="http://www.ncbi.nlm.nih.gov/Entrez/index.html"&gt;&lt;i&gt;Entrez&lt;/i&gt;&lt;/a&gt; is the integrated, text-based search and retrieval system used at NCBI for the major databases, including PubMed, Nucleotide and Protein Sequences, Protein Structures, Complete Genomes, Taxonomy, and others. If you were a biologist, you probably use Entrez everyday. The graphic below for a breif view of Entrez integration.&lt;br /&gt;&lt;img src="http://www.ncbi.nlm.nih.gov/Database/Gifs/nodes_thumb_small.png" /&gt;&lt;br /&gt;Usually general user will access Entrez by its &lt;a href="http://www.ncbi.nlm.nih.gov/entrez/query.fcgi"&gt;web form interface&lt;/a&gt;. For data mining NCBI made a utility called: &lt;span style="font-weight: bold; font-style: italic;"&gt;eUtils&lt;/span&gt;, which provide a URL tool as well as a SOAP interface. The URL tool requires to construct a customized search URL and returns results as XML. To save some time,&amp;nbsp; I decided to use&amp;nbsp; SOAP&amp;nbsp; interface (version 1.3a). More help on eUtils utility can be found &lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/eutils_help.html"&gt;here&lt;/a&gt;.&amp;nbsp;  Information about SOAP interface can be&amp;nbsp; find &lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/esoap_help.html"&gt;here&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;eUtils have contain several tools :&amp;nbsp;  &lt;ul&gt;&lt;li&gt;&lt;b&gt;&lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/einfo_help.html"&gt;EInfo&lt;/a&gt;:&amp;nbsp; &lt;/b&gt;Provides  field index term counts, last update, and available links for each database.&lt;/li&gt;&lt;li&gt; &lt;b&gt;&lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/esearch_help.html"&gt;ESearch&lt;/a&gt;&lt;/b&gt;:&amp;nbsp; Searches and retrieves primary IDs (for use in EFetch, ELink, and ESummary) and term translations and optionally retains results for future use in the user's environment.&lt;/li&gt;&lt;li&gt; &lt;b&gt;&lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/epost_help.html"&gt;EPost&lt;/a&gt;:&amp;nbsp;&lt;/b&gt; Posts a file containing a list of primary IDs for future use in the user's environment to use with subsequent search strategies.&lt;/li&gt;&lt;li&gt; &lt;b&gt;&lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/esummary_help.html"&gt;ESummary&lt;/a&gt;&lt;/b&gt;: Retrieves document summaries from a list of primary IDs or from the user's environment.&lt;/li&gt;&lt;li&gt; &lt;b&gt;&lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/efetch_help.html"&gt;EFetch&lt;/a&gt;&lt;/b&gt;:&amp;nbsp;  Retrieves records in the requested format from a list of one or more primary IDs or from the user's environment.&lt;/li&gt;&lt;li&gt; &lt;b&gt;&lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/elink_help.html"&gt;ELink&lt;/a&gt;&lt;/b&gt;:&amp;nbsp; Checks for the existence of an external or Related Articles link from a list of one or more primary IDs.&amp;nbsp; Retrieves primary IDs and relevancy scores for links to Entrez databases or Related Articles;&amp;nbsp; creates a hyperlink to the primary LinkOut provider for a specific ID and database, or lists LinkOut URLs and Attributes for multiple IDs.&lt;/li&gt;&lt;li&gt; &lt;b&gt;&lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/egquery_help.html"&gt;EGQuery&lt;/a&gt;&lt;/b&gt;: Provides  Entrez database counts in XML for a single search using  Global Query.&lt;/li&gt;&lt;li&gt; &lt;b&gt;&lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/query/static/espell_help.html"&gt;ESpell:&lt;/a&gt;&lt;/b&gt; Retrieves  spelling suggestions.&lt;/li&gt;&lt;/ul&gt; We will use ESearch and ESummary this time. Now let's start:&lt;br /&gt;1. Create a "Class Libaray" in Visual C# Express.&lt;br /&gt;2. Project -&amp;gt; Add Reference -&amp;gt; &lt;span style="font-size: 11pt; font-family: Arial;"&gt;System.Management.Automation&lt;br /&gt;3. Project -&amp;gt; Add Web Reference -&amp;gt;&lt;/span&gt;&lt;a href="http://eutils.ncbi.nlm.nih.gov/entrez/eutils/soap/eutils_lite.wsdl"&gt; http://eutils.ncbi.nlm.nih.gov/entrez/eutils/soap/eutils_lite.wsdl&lt;/a&gt; (without EFech tool) -&amp;gt; Go -&amp;gt; Change Web Refernece name to "eUtils"&lt;br /&gt;4. Create new class derived from &lt;span style="font-weight: bold;"&gt;MshSnapin&lt;/span&gt; object.&lt;br /&gt;5. Create new class derived from &lt;span style="font-weight: bold;"&gt;Cmdlet&lt;/span&gt; object.&lt;br /&gt;6. Build project to &lt;span style="font-weight: bold;"&gt;EntrezSnapin.dll&lt;/span&gt;.&lt;br /&gt;7. Install mshsnapin using .NET SDK &lt;span style="font-weight: bold;"&gt;installutils.exe&lt;/span&gt; tool.&lt;br /&gt;&lt;blockquote&gt;set-alias installutil $env:windir\Microsoft.NET\Framework\v2.0.50727\installutil&lt;br /&gt;installutil EntrezSnapin.dll&lt;br /&gt;&lt;/blockquote&gt;8. Load mshsnapin using add-mshsnapin cmdlet&lt;br /&gt;&lt;blockquote&gt;get-mshsnapin -reg&lt;br /&gt;add-mshsnapin EntrezSnapin  &lt;/blockquote&gt;9. Now you can enjoy powerful Entrez search tool under msh prompt.&lt;br /&gt;C# Code:&lt;br /&gt;&lt;blockquote&gt;using System;&lt;br /&gt;using System.ComponentModel;&lt;br /&gt;using System.Management.Automation;&lt;br /&gt;using System.Collections;&lt;br /&gt;namespace Entrez&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt; This class defines the properties of a snapin&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; [RunInstaller(true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public class EntrezSnapin : MshSnapIn&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Creates an instance of DemonSnapin class.&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public EntrezSnapin() : base()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ///&amp;lt;summary&amp;gt;The snapin name which is used for registration&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Name&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; { get&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; { return "EntrezSnapin";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Gets vendor of the snapin.&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Vendor&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; { get&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; { return "http://mshforfun.blogspot.com";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Gets description of the snapin. &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public override string Description&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; { get&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; { return "Cmdlets to build your own NCBI Entrez Data pipeline";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// Submit search to entrez database and return results IDs &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Cmdlet("search", "entrez", SupportsShouldProcess = true)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; public class SearchEntrezCmd : Cmdlet&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; #region Parameters&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string db="pubmed"; &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Entrez Database&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Mandatory=true, Position=0)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string Database&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return db; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { db = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string term;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;search terms or phrases with or without Boolean operators&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Mandatory = true, Position = 1)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string Keywords&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return term; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { term = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string retmax = "50";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Maximum number of records to return&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Position = 2)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string MaxRecord&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return retmax; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { retmax = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string email = "";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;To identify your search results history on server&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Position = 3)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string Email&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return email; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { email = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string field = "";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;specific search field for pubmed database&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Position = 4)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string Field&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return field; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { field = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string reldate = "";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Limit items a number of days immediately preceding today's date&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Position = 5)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string RelativeDate&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return reldate; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { reldate = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string mindate = "";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Lower bounded of two specific dates&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Position = 6)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string MinimumDate&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return mindate; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { mindate = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string maxdate = "";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Lower bounded of two specific dates&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Position = 7)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string MaximumDate&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return maxdate; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { maxdate = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string datetype = "";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;Limit dates to a specific date field based on database&amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; [Parameter(Position = 8)]&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public string DateType&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; get { return datetype; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; set { datetype = value; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; #endregion&lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string usehistory = "y";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string tool = "Monad_Entrez_Client";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string retstart = "0";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string rettype = "uilist";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; private string sort = "";&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// Communicating purpose only&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; protected override void BeginProcessing()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteVerbose("Searching Entrez database...\r\nDatabase: " + db + "\r\nKeywords: " + term);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// Get Entrez search results&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; /// &amp;lt;/summary&amp;gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; protected override void ProcessRecord()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (ShouldProcess("Searching Entrez database...\r\nDatabase: " + db + "\r\nKeywords: " + term))&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; try&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteVerbose("Creating Entrez WebService...");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; eUtils.eUtilsService serv = new eUtils.eUtilsService();&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteDebug("WebService:" + serv.ToString());&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteVerbose("Submit search...");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // call NCBI ESearch utility&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // NOTE: search term should be URL encoded &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; eUtils.eSearchResultType Search_Results = serv.run_eSearch_MS(db, term, "", "", usehistory, tool, email, field, reldate, mindate, maxdate, datetype, retstart, retmax, rettype, sort );&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteDebug("Search Results:" + Search_Results.ToString());&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (Search_Results.ERROR != null)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ThrowTerminatingError(new ErrorRecord(new Exception("web service method error"), "eUtils.run_eSearch_MS", ErrorCategory.InvalidResult, Search_Results));&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteVerbose("Number of results item found:" + Search_Results.Count);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteVerbose("Getting results summary...");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // call NCBI ESummary utility&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // NOTE: search term should be URL encoded&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; eUtils.eSummaryResultType Summary_Results = serv.run_eSummary_MS( db, "", Search_Results.WebEnv, Search_Results.QueryKey, Search_Results.RetStart, Search_Results.RetMax,&amp;nbsp; tool, email );&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteDebug("Results summary:" + Summary_Results.ToString());&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if (Summary_Results.ERROR != null)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ThrowTerminatingError(new ErrorRecord(new Exception("web service method error"), "eUtils.run_eSummary_MS", ErrorCategory.InvalidResult, Summary_Results));&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteVerbose("Number of item retrieved:" + Summary_Results.DocSum.Length);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteVerbose("Write results to pipline...");&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; // results output&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; WriteObject(Summary_Results);&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; catch (Exception e)&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ThrowTerminatingError(new ErrorRecord(e, "eUtils", ErrorCategory.ResourceUnavailable, db+term));&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113717563357524391?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113717563357524391/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/author-monad-cmdlet-as-web-service.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113717563357524391'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113717563357524391'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/author-monad-cmdlet-as-web-service.html' title='Author a Monad Cmdlet as Web Service Client'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113678517225026665</id><published>2006-01-09T00:39:00.000-05:00</published><updated>2006-05-05T11:14:38.420-04:00</updated><title type='text'>Bring Statistical Analysis Power to MSH: Hosting R Environment</title><content type='html'>&lt;div xmlns="http://www.w3.org/1999/xhtml"&gt;Quote from /\/\o\/\/ blog entry &lt;a href="http://mow001.blogspot.com/2006/01/hosting-iron-python-in-msh.html"&gt;Hosting Iron python in MSH&lt;/a&gt;: "Nice thing about Monad that it's easy to host other Languages inline." Well, since /\/\o\/\/ did &lt;a href="http://mow001.blogspot.com/2005/10/msh-access-nt-provider.html"&gt;VB.net&lt;/a&gt;, Monad team blog did &lt;a href="http://monadblog.blogspot.com/2005/12/calling-win32-api-functions-through.html"&gt;C#&lt;/a&gt; and those japanese guy did &lt;a href="http://d.hatena.ne.jp/newpops/20060108/p1"&gt;python&lt;/a&gt;. I would like to something a biologist should do: Hosting &lt;span style="font-weight: bold;"&gt;R Environment &lt;/span&gt;in MSH.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;R&lt;/span&gt; is an integrated suite of software facilities for data manipulation, calculation and graphical display.&lt;b&gt; &lt;/b&gt;It consists of a language plus a run-time environment with graphics, a debugger, access to certain system functions, and the ability to run programs stored in script files. &lt;b&gt;R language&lt;/b&gt; is an interpreted computer language derived from S language. Scientist use R mostly as a &lt;span style="font-weight: bold;"&gt;statistical analysis&lt;/span&gt; tool. You can download a copy of R from &lt;a href="http://www.r-project.org/"&gt;R-project home page&lt;/a&gt; (under GNU license).&lt;br /&gt;&lt;br /&gt;My last project involve R is a gene expression profile analysis from microarray experiment two years ago. If you were a computer geek, it will take you less than 30min to learn to use R environment because it is object-oriented and  synax similar to C.&lt;br /&gt;&lt;br /&gt;Monad can can interact with other program using COM-based technologies. For example:&lt;br /&gt;1. From /\/\o\/\/ blog: &lt;a href="http://mow001.blogspot.com/2005/12/monad-really-does-rock.html"&gt;Monad Really Does Rock&lt;/a&gt;&lt;br /&gt;2. From Monad team blog: &lt;a href="http://blogs.msdn.com/monad/archive/2005/12/20/505735.aspx"&gt;Check spelling script&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;In order to use R language interpreter in MSH, we need another R addon: &lt;a href="http://cran.r-project.org/other-software.html"&gt;R-DCOM&lt;/a&gt;, which works with &lt;code&gt;Rproxy.dll&lt;/code&gt; (in the R distribution) and &lt;code&gt;R.dll&lt;/code&gt; to support transfer of data to and from R and remote execution of R commands, as well as embedding of an R graphics window.&lt;br /&gt;&lt;br /&gt;After insatll R and r-DCOM, we can enjoy the power of R under MSH prompt:&lt;br /&gt;&lt;br /&gt;# Create a new com object for R&lt;br /&gt;&lt;blockquote&gt;$RCom = new-object -com StatConnectorSrv.StatConnector&lt;/blockquote&gt;&lt;br /&gt;# Call Init method to load R environment&lt;br /&gt;&lt;blockquote&gt;$RCom.Init("R")&lt;/blockquote&gt;&lt;br /&gt;# Check out available methods&lt;br /&gt;&lt;blockquote&gt;$Rcom |gm&lt;/blockquote&gt;&lt;br /&gt;TypeName: System.__ComObject#{18c8b660-81a2-11d3-9254-00e09812f727}&lt;br /&gt;&lt;br /&gt;Name MemberType Definition&lt;br /&gt;---- ---------- ----------&lt;br /&gt;AddGraphicsDevice Method void AddGraphicsDevice (string, ISGFX)&lt;br /&gt;Close Method void Close ()&lt;br /&gt;Evaluate Method Variant Evaluate (string)&lt;br /&gt;EvaluateNoReturn Method void EvaluateNoReturn (string)&lt;br /&gt;GetConnectorInformation Method string GetConnectorInformation (Informa...&lt;br /&gt;GetErrorId Method int GetErrorId ()&lt;br /&gt;GetErrorText Method string GetErrorText ()&lt;br /&gt;GetInterpreterInformation Method string GetInterpreterInformation (Infor...&lt;br /&gt;GetServerInformation Method string GetServerInformation (Informatio...&lt;br /&gt;GetSupportedTypes Method void GetSupportedTypes (int)&lt;br /&gt;GetSymbol Method Variant GetSymbol (string)&lt;br /&gt;Init Method void Init (string)&lt;br /&gt;RemoveGraphicsDevice Method void RemoveGraphicsDevice (string)&lt;br /&gt;SetCharacterOutputDevice Method void SetCharacterOutputDevice (IStatCon...&lt;br /&gt;SetErrorDevice Method void SetErrorDevice (IStatConnectorChar...&lt;br /&gt;SetSymbol Method void SetSymbol (string, Variant)&lt;br /&gt;SetTracingDevice Method void SetTracingDevice (IStatConnectorCh...&lt;br /&gt;SetUserInterfaceAgent Method void SetUserInterfaceAgent (IStatConnec...&lt;br /&gt;&lt;br /&gt;# Send expression to R interpreter&lt;br /&gt;# where c() is a function to assign a "vector" Variant to x&lt;br /&gt;# remember R language is case senitive&lt;br /&gt;&lt;blockquote&gt;$Rcom.EvaluateNoReturn ("x &lt;-  c(79.98, 80.04, 80.02, 80.04, 80.03, 80.03, 80.04, 79.97, 80.05, 80.03, 80.02, 80.00, 80.02)")&lt;br /&gt;$Rcom.EvaluateNoReturn ("y  &lt;-c(80.02, 79.94, 79.98, 79.97, 79.97, 80.03, 79.95, 79.97)")&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;# use R graphic device to make boxplot&lt;br /&gt;&lt;blockquote&gt;$Rcom.EvaluateNoReturn ("boxplot(x, y)")&lt;/blockquote&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/boxplot.jpg"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://photos1.blogger.com/blogger/5412/2034/320/boxplot.jpg" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;# Student t test: two variant; two sided; unpaired&lt;br /&gt;&lt;blockquote&gt;$Rcom.Evaluate("t.test(x, y, alternative = c(`"two.sided`"))")&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;3.24986738055522   #t&lt;br /&gt;12.0271084945182   #delta-f&lt;br /&gt;0.00693932661444795   #P-value (if less than 0.05, means statitical significant)&lt;br /&gt;0.0138552637266242   #lower 95 percent confidence interval&lt;br /&gt;80.0207692307692   #average of x&lt;br /&gt;0     #alternative hypothesis: true difference in means is not equal to 0&lt;br /&gt;two.sided&lt;br /&gt;Welch Two Sample t-test&lt;br /&gt;x and y&lt;br /&gt;# Dispose R Environment&lt;br /&gt;&lt;blockquote&gt;$Rcom.Close()&lt;/blockquote&gt;&lt;br /&gt;Have fun!&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113678517225026665?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113678517225026665/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/bring-statistical-analysis-power-to.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113678517225026665'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113678517225026665'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/bring-statistical-analysis-power-to.html' title='Bring Statistical Analysis Power to MSH: Hosting R Environment'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113670047223038417</id><published>2006-01-08T01:07:00.000-05:00</published><updated>2006-05-05T11:15:02.996-04:00</updated><title type='text'>GUI version of NCBI Blastn(nr) MSH script</title><content type='html'>&lt;div xmlns="http://www.w3.org/1999/xhtml"&gt;An NCBI Blastn (using nr database) client MSH script with winform GUI. See &lt;a href="http://mshforfun.blogspot.com/2005/12/ncbi-blastn-under-msh-command-line.html"&gt;NCBI Blastn under MSH command line&lt;/a&gt; for a introduction of NCBI Blastn program. &lt;br /&gt;&lt;br /&gt;Although personally I like command line interface, there are always some users prefer GUI. Well, since monad can use &lt;span style="font-weight: bold;"&gt;System.Windows.Forms.form&lt;/span&gt;, it can create comman winform GUI which is similar to what tk/tcl can do. &lt;br /&gt;&lt;br /&gt;One of the big advantage of monad is that script block can be used a &lt;span style="font-weight: bold;"&gt;event handler&lt;/span&gt;. &lt;br /&gt;&lt;br /&gt;Another thing need to mention is that monad use  grave-accent(&lt;span style="font-weight: bold;"&gt;`&lt;/span&gt;) but not "\" for escape sequences. To get more help on &lt;span style="font-weight: bold;"&gt;escape character&lt;/span&gt; using command:&lt;br /&gt;help about_escape_character&lt;br /&gt;Because NCBI Blast server running unix like OS, so the returning results using \n but not \r\n for a new line. We have to replace those \n with \r\n to get a proper view in textbox control.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger/5412/2034/1600/blastn.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/5412/2034/320/blastn.jpg" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;# Blastn-GUI.msh&lt;br /&gt;# ===========================================================================&lt;br /&gt;#&lt;br /&gt;# This code is for test purposes only. Use it at your own risk.&lt;br /&gt;#&lt;br /&gt;# Please do not submit or retrieve more than one request every two seconds.&lt;br /&gt;#&lt;br /&gt;# Results will be kept at NCBI for 24 hours. For best batch performance,&lt;br /&gt;# It is recommend that you submit requests after 2000 EST (0100 GMT) and&lt;br /&gt;# retrieve results before 0500 EST (1000 GMT).&lt;br /&gt;#&lt;br /&gt;# by tony 2006 http://mshforfun.blogspot.com/&lt;br /&gt;# ===========================================================================&lt;br /&gt;[void] [Reflection.Assembly]::Load( `&lt;br /&gt;"System.Windows.Forms, Version=2.0.0.0, Culture=neutral, `&lt;br /&gt;PublicKeyToken=b77a5c561934e089")&lt;br /&gt;$script:form = new-object System.Windows.Forms.form &lt;br /&gt;$Panel = new-object System.Windows.Forms.Panel&lt;br /&gt;$Label = new-object System.Windows.Forms.Label&lt;br /&gt;$Query = new-object System.Windows.Forms.TextBox&lt;br /&gt;$Submit = new-object System.Windows.Forms.Button&lt;br /&gt;$script:Results = new-object System.Windows.Forms.TextBox&lt;br /&gt;$script:Status = new-object System.Windows.Forms.TextBox&lt;br /&gt;&lt;br /&gt;function SubmitQuery([String]$Sequence)&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;if ($Sequence -match "[^ATGCatgcNn]")&lt;br /&gt;&amp;nbsp;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Text += "Error 1: Invalid charactors in query sequence! Only A/T/G/C/N can be used!`r`n`r`n"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Refresh()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.ScrollToCaret()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; return&lt;br /&gt;&amp;nbsp;}&lt;br /&gt;&amp;nbsp;&lt;br /&gt;&amp;nbsp;$Status.Text += "`r`n==================================================`r`n"&lt;br /&gt;&amp;nbsp;$Status.Text += (get-date).ToString("MM-dd-yyyy HH:mm") + ": Submiting sequence...`r`n" &lt;br /&gt;&amp;nbsp;$Status.Refresh()&lt;br /&gt;&amp;nbsp;$Status.ScrollToCaret()&lt;br /&gt;&lt;br /&gt;&amp;nbsp;$uri="http://www.ncbi.nlm.nih.gov/blast/Blast.cgi?CMD=Put&amp;amp;PROGRAM=blastn&amp;amp;DATABASE=nr&amp;amp;QUERY=" + $Sequence&lt;br /&gt;&amp;nbsp;$BlastClient = new-object System.Net.WebClient&lt;br /&gt;&amp;nbsp;$pagecontent = $BlastClient.DownloadString($uri);&lt;br /&gt;&amp;nbsp;if ($pagecontent -match "&amp;nbsp;&amp;nbsp; RID = (.*)") &lt;br /&gt;&amp;nbsp;{ &lt;br /&gt;&amp;nbsp;&amp;nbsp; $RID=$Matches[1]&lt;br /&gt;&amp;nbsp;&amp;nbsp; $Status.Text += "RID =" + $RID + "`r`n"&lt;br /&gt;&amp;nbsp;&amp;nbsp; $Status.Refresh()&lt;br /&gt;&amp;nbsp;&amp;nbsp; $Status.ScrollToCaret()&lt;br /&gt;&amp;nbsp; }&lt;br /&gt;&lt;br /&gt;&amp;nbsp;if ($pagecontent -match "&amp;nbsp;&amp;nbsp; RTOE = (.*)")&lt;br /&gt;&amp;nbsp;{&lt;br /&gt;&amp;nbsp; $TimeToComplete= $Matches[1]&lt;br /&gt;&amp;nbsp; $Status.Text += "Estimated Time to finish searching: " + $TimeToComplete + " seconds`r`nWaiting...`r`n`r`n" &lt;br /&gt;&amp;nbsp; $Status.Refresh()&lt;br /&gt;&amp;nbsp; $Status.ScrollToCaret()&lt;br /&gt;&amp;nbsp;}&lt;br /&gt;&lt;br /&gt;&amp;nbsp;Start-sleep $TimeToComplete&lt;br /&gt;&lt;br /&gt;&amp;nbsp;While ($true)&lt;br /&gt;&amp;nbsp;{&lt;br /&gt;&amp;nbsp;&amp;nbsp; &lt;br /&gt;&amp;nbsp;&amp;nbsp; $uri= "http://www.ncbi.nlm.nih.gov/blast/Blast.cgi?CMD=Get&amp;amp;FORMAT_OBJECT=SearchInfo&amp;amp;RID=" + $RID&amp;nbsp;&amp;nbsp;&amp;nbsp; &lt;br /&gt;&amp;nbsp;&amp;nbsp; $pagecontent = $BlastClient.DownloadString($uri);&lt;br /&gt;&amp;nbsp;&amp;nbsp; if ($pagecontent -match "Status=WAITING")&lt;br /&gt;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Text += (get-date).ToString("MM-dd-yyyy HH:mm") + ": Search not finished yet, waiting... `r`n" &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Refresh()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.ScrollToCaret()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; Start-sleep 5&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; continue&lt;br /&gt;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp; if ($pagecontent -match "Status=FAILED")&lt;br /&gt;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Text += (get-date).ToString("MM-dd-yyyy HH:mm") + ": Error 2 -- Search failed!`r`n`r`n"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Refresh()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return&lt;br /&gt;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp; if ($pagecontent -match "Status=UNKNOWN")&lt;br /&gt;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Text += (get-date).ToString("MM-dd-yyyy HH:mm") + ": Error 3-- Search expired!`r`n`r`n"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Refresh()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return&lt;br /&gt;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp; if ($pagecontent -match "Status=READY")&lt;br /&gt;&amp;nbsp;&amp;nbsp; {&amp;nbsp; &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; if ($pagecontent -match "ThereAreHits=yes")&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Text += (get-date).ToString("MM-dd-yyyy HH:mm") + ": Search complete, retrieving results...`r`n`r`n"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;$Status.Refresh()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;$Status.ScrollToCaret()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; &amp;nbsp;break&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; else&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Text += (get-date).ToString("MM-dd-yyyy HH:mm") + ": Error 4-- No hits found!`r`n`r`n"&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp; $Status.Refresh()&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; return&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp; }&lt;br /&gt;&amp;nbsp;&amp;nbsp; $Status.Text += (get-date).ToString("MM-dd-yyyy HH:mm") + ": Error 5-- Unknown error! `r`n`r`n"&lt;br /&gt;&amp;nbsp;&amp;nbsp; $Status.Refresh()&lt;br /&gt;&amp;nbsp;&amp;nbsp; return&lt;br /&gt;}&lt;br /&gt;$uri= "http://www.ncbi.nlm.nih.gov/blast/Blast.cgi?CMD=Get&amp;amp;RID=" + $RID + "&amp;amp;ALIGNMENTS=500&amp;amp;ALIGNMENT_VIEW=QueryAnchored&amp;amp;FORMATOBJECT=Alignment&amp;amp;FORMAT_TYPE=TEXT"&lt;br /&gt;$Results.Text = $BlastClient.DownloadString($uri).Replace("`n","`r`n");&lt;br /&gt;return &lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;$form.text = "NCBI Blastn(nr) GUI" &lt;br /&gt;$form.Size =&amp;nbsp; "800,600" &lt;br /&gt;&lt;br /&gt;$Panel.Size = "794, 32"&lt;br /&gt;$Panel.Location = "0, 0"&lt;br /&gt;&lt;br /&gt;$Label.Text = "Query:"&lt;br /&gt;$Label.Location = "10, 8"&lt;br /&gt;$Label.Size = "80, 32"&lt;br /&gt;$Panel.Controls.Add($Label)&lt;br /&gt;&lt;br /&gt;$Query.Location = "100, 8"&lt;br /&gt;$Query.Size = "500, 20"&lt;br /&gt;$Panel.Controls.Add($Query)&lt;br /&gt;&lt;br /&gt;$Submit.Location = "710, 8"&lt;br /&gt;$Submit.Text = "Submit"&lt;br /&gt;$Submit.Add_Click({SubmitQuery($Query.Text)})&lt;br /&gt;$Panel.Controls.Add($Submit)&lt;br /&gt;&lt;br /&gt;$form.Controls.Add($Panel)&lt;br /&gt;&lt;br /&gt;$Results.Location = "0, 40"&lt;br /&gt;$Results.Multiline = $True&lt;br /&gt;$Results.Size = "790, 400"&lt;br /&gt;$Results.ScrollBars = "Vertical"&lt;br /&gt;$Results.ReadOnly = $true&lt;br /&gt;$form.Controls.Add($Results)&lt;br /&gt;&lt;br /&gt;$Status.Location = "0, 440"&lt;br /&gt;$Status.Multiline = $True&lt;br /&gt;$Status.Size = "790, 100"&lt;br /&gt;$Status.ScrollBars = "Vertical"&lt;br /&gt;$Status.ReadOnly = $true&lt;br /&gt;$form.Controls.Add($Status)&lt;br /&gt;&lt;br /&gt;$form.showdialog()&amp;nbsp; &lt;/blockquote&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113670047223038417?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113670047223038417/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/gui-version-of-ncbi-blastnnr-msh.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113670047223038417'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113670047223038417'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/gui-version-of-ncbi-blastnnr-msh.html' title='GUI version of NCBI Blastn(nr) MSH script'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113632260298240417</id><published>2006-01-03T16:10:00.000-05:00</published><updated>2006-05-05T11:15:23.883-04:00</updated><title type='text'>Play with ACL in MSH (continued)</title><content type='html'>/\/\o\/\/ kindly replied my blog entry “&lt;a href="http://mshforfun.blogspot.com/2005/12/play-with-acl-in-msh.html"&gt;Play with ACL in MSH&lt;/a&gt;”. In his blog entry “&lt;a href="http://mow001.blogspot.com/2006/01/adding-simple-accesrule-to-file-acl-in.html"&gt;Adding a Simple AccesRule to a file ACL in MSH&lt;/a&gt;”, he found a shortcut to create an instance of “System.Security.AccessControl.FileSystemAccessRule”. Great job! But things can get even better!&lt;br /&gt;&lt;br /&gt;1. You want to &lt;strong&gt;change &lt;/strong&gt;a accessrule but not &lt;strong&gt;overwrite &lt;/strong&gt;it, so &lt;strong&gt;AddAccessRule() &lt;/strong&gt;method is better than &lt;strong&gt;SetAccessRule() &lt;/strong&gt;method. If you want to grant a FullControl privilege to &lt;strong&gt;exact &lt;/strong&gt;same user, they are the same. What if you want to apply a more complex privilege? For example: Read + Write nut not Delete.&lt;br /&gt;&lt;br /&gt;2. get-acl cmdlet return different object:&lt;br /&gt;For a file, it will return “System.Security.AccessControl.FileSecurity”;&lt;br /&gt;For a directory, it will return “System.Security.AccessControl.DirectorySecurity”.&lt;br /&gt;Luckily enough, both object have AddAccessRule() and  RemoveAccessRule() methods. And Even better, both methods take a “System.Security.AccessControl.FileSystemAccessRule” as parameter. So we can set Access control of a file or directory in one simple script.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;# AddRemove-AccessRule.MSH &lt;br /&gt;# Add or remove simple access rule to a file/directory&lt;br /&gt;# using text parameters&lt;br /&gt;#&lt;br /&gt;# original writen by /\/\o\/\/ 2006 &lt;br /&gt;# http://mow001.blogspot.com&lt;br /&gt;#&lt;br /&gt;# modified by tony 2006&lt;br /&gt;# http://mshforfun.blogspot.com&lt;br /&gt;#&lt;br /&gt;#Usage AddRemove-Acl FileOrDirectory (Action) user Rights (Access)&lt;br /&gt;# Action:     Add / Remove&lt;br /&gt;# Rights:     ListDirectory / ReadData / WriteData / CreateFiles /&lt;br /&gt;#          CreateDirectories / AppendData / ReadExtendedAttributes /&lt;br /&gt;#          WriteExtendedAttributes / Traverse / ExecuteFile /&lt;br /&gt;#          DeleteSubdirectoriesAndFiles / ReadAttributes / WriteAttributes/ Write /&lt;br /&gt;#          Delete / ReadPermissions / Read / ReadAndExecute / Modify /&lt;br /&gt;#          ChangePermissions / TakeOwnership / Synchronize / FullControl&lt;br /&gt;# Access:     Allow / Deny&lt;br /&gt;&lt;br /&gt;Param (&lt;br /&gt;     $FileDir,&lt;br /&gt;     $User,&lt;br /&gt;     $Action = "Add",&lt;br /&gt;     [System.Security.AccessControl.FileSystemRights] $Rights,&lt;br /&gt;     [System.Security.AccessControl.AccessControlType] $Access = "Allow"&lt;br /&gt;)&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;trap{Break}&lt;br /&gt;&lt;br /&gt;$AccessControl = get-acl $FileDir&lt;br /&gt;&lt;br /&gt;$AccessRule = new-object System.Security.AccessControl.FileSystemAccessRule($User,$Rights,$Access)&lt;br /&gt;&lt;br /&gt;# check if given user is Valid, this will break function if not so.&lt;br /&gt;$Sid = $AccessRule.IdentityReference.Translate([System.Security.Principal.securityidentifier]) &lt;br /&gt;&lt;br /&gt;resolve-path $FileDir&lt;br /&gt;&lt;br /&gt;"=============================================================="&lt;br /&gt;"Before changes"&lt;br /&gt;$AccessControl.AccessToString&lt;br /&gt;&lt;br /&gt;if ($Action.ToUpper() -eq "ADD") {$AccessControl.AddAccessRule($AccessRule)}&lt;br /&gt;elseif ($Action.ToUpper() -eq "REMOVE") {$AccessControl.RemoveAccessRule($AccessRule)}&lt;br /&gt;&lt;br /&gt;set-acl -aclobject $AccessControl -path $FileDir&lt;br /&gt;&lt;br /&gt;"=============================================================="&lt;br /&gt;"After " + $Action + " access rule: " + "User-"+ $User + " Rights-" + $Rights + " Access-" + $Access&lt;br /&gt;(get-acl $FileDir).AccessToString    &lt;br /&gt;&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113632260298240417?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113632260298240417/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/play-with-acl-in-msh-continued.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113632260298240417'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113632260298240417'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/play-with-acl-in-msh-continued.html' title='Play with ACL in MSH (continued)'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113626583075325753</id><published>2006-01-03T00:23:00.000-05:00</published><updated>2006-01-05T22:16:11.886-05:00</updated><title type='text'>Working with SQL server in monad using pre-compiled .NET Class Library (3)</title><content type='html'>Now the usual routine operation:&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Add a plasmid &lt;/strong&gt;&lt;br /&gt;&lt;strong&gt;Edit a plasmid&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;Why there is no “&lt;strong&gt;Delete plasmid&lt;/strong&gt;” operation?&lt;br /&gt;&lt;br /&gt;Because Biologists &lt;strong&gt;Never, Never, Ever &lt;/strong&gt;lose their plasmids!&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;1. Add following code to our PlasmidView.DLL:&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;namespace PlasmidView&lt;br /&gt;&lt;br /&gt;      public class SQLProvider&lt;br /&gt;     {&lt;br /&gt;           public static PlasmidFull PlasmidFull_ByPlasmidID (int plasmidid)&lt;br /&gt;          {… }&lt;br /&gt;          &lt;br /&gt;          public static void Plasmid_Add (PlasmidFull PlasmidToAdd)&lt;br /&gt;          {… }&lt;br /&gt;          public static void Plasmid_Edit (PlasmidFull PlasmidToEdit)&lt;br /&gt;          {…}&lt;br /&gt;          &lt;br /&gt;          public static string Enzyme_ByEnzymeID (int enzymeID)&lt;br /&gt;          {…}&lt;br /&gt;          public static string BacResistanceType_ByTypeID (int TypeID)&lt;br /&gt;          {…}&lt;br /&gt;          public static string MamResistanceType_ByTypeID (int TypeID)&lt;br /&gt;          {…}&lt;br /&gt;          public static string InsertType_ByInsertTypeID (int insertTypeID)&lt;br /&gt;          {…}&lt;br /&gt;     }&lt;br /&gt;     public class PlasmidFull : PlasmidCore&lt;br /&gt;     {…}&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;2. Get a Plasmid by PlasmidID&lt;/strong&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;[void][System.Reflection.Assembly]::LoadFile("D:\MSH\PlasmidView.dll")&lt;br /&gt;$Plasmid= [PlasmidView.SQLProvider]::PlasmidFull_ByPlasmidID (10)&lt;br /&gt;$Plasmid&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;BacResistance     : 1&lt;br /&gt;MamResistance     : 2&lt;br /&gt;HasGlycerolStock  : False&lt;br /&gt;InsertDescription : IL-17R full length receptor&lt;br /&gt;InsertLength      : 2451&lt;br /&gt;InsertTypeID      : 1&lt;br /&gt;InsertType        : Human&lt;br /&gt;LeftEnzymeID      : 14&lt;br /&gt;LeftEnzyme        : BamHI&lt;br /&gt;RightEnzymeID     : 62&lt;br /&gt;RigthEnzyme       : NcoI&lt;br /&gt;IsBluntLigation   : False&lt;br /&gt;IsSequenced       : True&lt;br /&gt;Comments          :&lt;br /&gt;FullSeq           :&lt;br /&gt;InsertSeq         :&lt;br /&gt;PlasmidID         : 10&lt;br /&gt;BoxID             : B&lt;br /&gt;BoxPosition       : 1&lt;br /&gt;PlasmidName       : IL-17R-FL-HA&lt;br /&gt;DateCreated       : 10/30/2005 9:18:18 PM&lt;br /&gt;UserID            : 1&lt;br /&gt;UserCreated       : me&lt;br /&gt;PlasmidType       : Cytokine Receptor&lt;br /&gt;PlasmidTypeID     : 3&lt;br /&gt;ParentPlasmidID   : 9&lt;br /&gt;ParentPlasmid     : pCMV4 HA Neo&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;3. Edit this plasmid entry&lt;/strong&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;$Plasmid.PlasmidName = “mouse IL-17R-FL-HA”&lt;br /&gt;$Plasmid.InsertTypeID = 2&lt;br /&gt;[PlasmidView.SQLProvider]::Plasmid_Edit($Plasmid)&lt;br /&gt;$Plasmid= [PlasmidView.SQLProvider]::PlasmidFull_ByPlasmidID (10)&lt;br /&gt;$Plasmid&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;BacResistance     : 1&lt;br /&gt;MamResistance     : 2&lt;br /&gt;HasGlycerolStock  : False&lt;br /&gt;InsertDescription : IL-17R full length receptor&lt;br /&gt;InsertLength      : 2451&lt;br /&gt;InsertTypeID      : 2&lt;br /&gt;InsertType        : Mouse&lt;br /&gt;LeftEnzymeID      : 14&lt;br /&gt;LeftEnzyme        : BamHI&lt;br /&gt;RightEnzymeID     : 62&lt;br /&gt;RigthEnzyme       : NcoI&lt;br /&gt;IsBluntLigation   : False&lt;br /&gt;IsSequenced       : True&lt;br /&gt;Comments          :&lt;br /&gt;FullSeq           :&lt;br /&gt;InsertSeq         :&lt;br /&gt;PlasmidID         : 10&lt;br /&gt;BoxID             : B&lt;br /&gt;BoxPosition       : 1&lt;br /&gt;PlasmidName       : mouse IL-17R-FL-HA&lt;br /&gt;DateCreated       : 10/30/2005 9:18:18 PM&lt;br /&gt;UserID            : 1&lt;br /&gt;UserCreated       : me&lt;br /&gt;PlasmidType       : Cytokine Receptor&lt;br /&gt;PlasmidTypeID     : 3&lt;br /&gt;ParentPlasmidID   : 9&lt;br /&gt;ParentPlasmid     : pCMV4 HA Neo&lt;br /&gt;&lt;strong&gt;4. Add a plasmid entry&lt;/strong&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;$Plasmid= new-object PlasmidView.PlasmidFull&lt;br /&gt;$Plasmid.BacResistance   = 1&lt;br /&gt;$Plasmid.MamResistance = 2&lt;br /&gt;$Plasmid.HasGlycerolStock  = $False&lt;br /&gt;$Plasmid.InsertDescription = "truncated IL-17R receptor"&lt;br /&gt;$Plasmid.InsertLength    = 1851&lt;br /&gt;$Plasmid.InsertTypeID    = 2&lt;br /&gt;$Plasmid.LeftEnzymeID    = 14&lt;br /&gt;$Plasmid.RightEnzymeID  = 62&lt;br /&gt;$Plasmid.IsBluntLigation   = $False&lt;br /&gt;$Plasmid.IsSequenced      = $True&lt;br /&gt;$Plasmid.BoxID            = "B"&lt;br /&gt;$Plasmid.BoxPosition  = 90&lt;br /&gt;$Plasmid.PlasmidName     = "truncated mouse IL-17R-FL-HA"&lt;br /&gt;$Plasmid.DateCreated       =  get-date&lt;br /&gt;$Plasmid.UserID           = 1&lt;br /&gt;$Plasmid.PlasmidTypeID    = 3&lt;br /&gt;$Plasmid.ParentPlasmidID   = 9&lt;br /&gt;&lt;br /&gt;$Plasmid&lt;br /&gt;$Plasmid= [PlasmidView.SQLProvider]::Plasmid_Add($Plasmid)&lt;br /&gt;[PlasmidView.SQLProvider]::Plasmid_All()  where-object {$_.PlasmidName&lt;br /&gt;-like "*truncated mouse IL-17R-FL-HA*"}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;PlasmidID       : 22&lt;br /&gt;BoxID           : B&lt;br /&gt;BoxPosition     : 90&lt;br /&gt;PlasmidName     : truncated mouse IL-17R-FL-HA&lt;br /&gt;DateCreated     : 1/3/2006 12:09:52 AM&lt;br /&gt;UserID          : 1&lt;br /&gt;UserCreated     : me&lt;br /&gt;PlasmidType     : Cytokine Receptor&lt;br /&gt;PlasmidTypeID   : 3&lt;br /&gt;ParentPlasmidID : 9&lt;br /&gt;ParentPlasmid   : pCMV4 HA Neo&lt;br /&gt;&lt;br /&gt;Conclusion:&lt;br /&gt;1. One of the advantages of using monad is that it is fully integrated with .Net frameworks. Although MSH does not have class definition machinery right now, we can easily construct a customized class in C# and use it in monad.&lt;br /&gt;&lt;br /&gt;2. Pre-compiled class library will greatly simplify monad script. Even a new user can be trained to work with fairly complex administration jobs.&lt;br /&gt;&lt;br /&gt;3. Security should always be in mind! Expose crucial objects or methods to unauthorized user may cause disastrous effect to system.&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113626583075325753?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113626583075325753/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/working-with-sql-server-in-monad-using_03.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113626583075325753'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113626583075325753'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/working-with-sql-server-in-monad-using_03.html' title='Working with SQL server in monad using pre-compiled .NET Class Library (3)'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113625529279171054</id><published>2006-01-01T21:28:00.000-05:00</published><updated>2006-01-05T22:16:45.856-05:00</updated><title type='text'>Working with SQL server in monad using pre-compiled .NET Class Library (2)</title><content type='html'>Now we can do something fun.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;1. Add following code to our PlasmidView.DLL&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;using System.Collections;&lt;br /&gt;namespace PlasmidView&lt;br /&gt;{&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; public class SQLProvider&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; {&lt;br /&gt;&lt;br /&gt;// return ArrayList of “PlasmidCore” objects of all plasmid information&lt;br /&gt;public static ArrayList Plasmid_All ()&lt;br /&gt;{...}&lt;br /&gt;&lt;br /&gt;// return a PlasmidCore object&lt;br /&gt;public static PlasmidCore PlasmidCore_ByPlasmidID (int plasmidid)&lt;br /&gt;{...}&lt;br /&gt;&lt;br /&gt;// return User objects&lt;br /&gt;public static User User_ByUserID (int userid)&lt;br /&gt;{...}&lt;br /&gt;&lt;br /&gt;// return Plasmid Type (String)&lt;br /&gt;public static string PlasmidType_ByPlasmidTypeID (int plasmidTypeID)&lt;br /&gt;{...}&lt;br /&gt;&lt;br /&gt;public class PlasmidCore&lt;br /&gt;{... }&lt;br /&gt;&lt;br /&gt;public class User&lt;br /&gt;{... }&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;I omit most of C# code here&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;2. Try to get all plasmid informtion&lt;/strong&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;[void][System.Reflection.Assembly]::LoadFile("D:\MSH\PlasmidView.dll")&lt;br /&gt;[PlasmidView.SQLProvider]::Plasmid_All()&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;PlasmidID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 1&lt;br /&gt;BoxID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : A&lt;br /&gt;BoxPosition&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 1&lt;br /&gt;PlasmidName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : pCMV4 Hygro&lt;br /&gt;DateCreated&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 10/30/2005 8:58:24 PM&lt;br /&gt;UserID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;: 1&lt;br /&gt;UserCreated&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : me&lt;br /&gt;PlasmidType&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : Backbone Vector&lt;br /&gt;PlasmidTypeID&amp;nbsp;&amp;nbsp; : 1&lt;br /&gt;ParentPlasmidID : 0&lt;br /&gt;ParentPlasmid&amp;nbsp;&amp;nbsp; : None&lt;br /&gt;&lt;br /&gt;PlasmidID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 2&lt;br /&gt;BoxID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : A&lt;br /&gt;BoxPosition&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 2&lt;br /&gt;PlasmidName&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : pCMV4 Neo&lt;br /&gt;DateCreated&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 10/30/2005 9:07:16 PM&lt;br /&gt;UserID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;: 1&lt;br /&gt;UserCreated&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : me&lt;br /&gt;PlasmidType&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : Backbone Vector&lt;br /&gt;PlasmidTypeID&amp;nbsp;&amp;nbsp; : 1&lt;br /&gt;ParentPlasmidID : 0&lt;br /&gt;ParentPlasmid&amp;nbsp;&amp;nbsp; : None&lt;br /&gt;…&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;3. Try to search plasmid with “hygro” in their names:&lt;/strong&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;[PlasmidView.SQLProvider]::Plasmid_All()&amp;nbsp;&amp;nbsp;where-object {$_.PlasmidName -like “*hygro*”} foreach-object {“============”; “ID:”+ $_.PlasmidID; “Name:” + $_.PlasmidName}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;============&lt;br /&gt;ID:1&lt;br /&gt;Name:pCMV4 Hygro&lt;br /&gt;============&lt;br /&gt;ID:20&lt;br /&gt;Name:TAg Hygro&lt;br /&gt;…&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Conclusion:&lt;/strong&gt;&lt;br /&gt;1. We can easily return a group of objects to monad using &lt;strong&gt;ArrayList&lt;/strong&gt;. Unlike strong typed language (for example, C#) monad detects the base object of each Item in ArrayList. You do &lt;strong&gt;NOT &lt;/strong&gt;have to &lt;strong&gt;cast &lt;/strong&gt;each ArrayList Item to its original base object (PlasmidView.PlasmidCore) when quoting them in a &lt;strong&gt;pipline&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;2. When database is small, using &lt;strong&gt;where-object &lt;/strong&gt;cmdlet to do &lt;strong&gt;search &lt;/strong&gt;is a good idea. Actually I even forgot I had a Plasmid_Search( ) method in my original C# code. But when database grew bigger, better use a Search function to return &lt;strong&gt;limited number &lt;/strong&gt;of objects only from search results.&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113625529279171054?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113625529279171054/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2006/01/working-with-sql-server-in-monad-using.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113625529279171054'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113625529279171054'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2006/01/working-with-sql-server-in-monad-using.html' title='Working with SQL server in monad using pre-compiled .NET Class Library (2)'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113625150733423881</id><published>2005-12-29T20:25:00.000-05:00</published><updated>2006-01-05T22:17:31.610-05:00</updated><title type='text'>Working with SQL server in monad using pre-compiled .NET Class Library (1)</title><content type='html'>As an immunologist, I have to deal with a lot of plasmids. In order to share plasmids with my colleagues, I stored all information of plasmids in an SQL server (express edition) running on a Windows XP desktop.&amp;nbsp;&amp;nbsp;I wrote a small &lt;strong&gt;winform &lt;/strong&gt;program to manage the information stored the SQL server. I have all the data type and program logic (including SQL query) packaged in NET Classes. So if I could reuse those .NET classes in monad, I can do some routine works in MSH scripts and will not waste time to start from scratch.&lt;br/&gt;&lt;br/&gt;What is plasmid anyway? Well, plasmid is a circular DNA molecule found in E.coli.&amp;nbsp;&amp;nbsp;Biologists often use them for gene cloning and expression. If you still don’t know what I am talking about, google (http://www.google.com/search?q=plasmid) for details. &lt;br/&gt;&lt;br/&gt;&lt;strong&gt;First, let’s make a DLL ready for MSH.&lt;/strong&gt;&lt;br/&gt;I opened my winform project; got rid of GUI components; recompiled the project to Class Library (PlasmidView.DLL). The DLL contained classes below:&lt;br/&gt;&lt;br/&gt;&lt;br/&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;using System;&lt;br/&gt;using System.Data;&lt;br/&gt;using System.Data.SqlClient;&lt;br/&gt;&lt;br/&gt;namespace PlasmidView&lt;br/&gt;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public class SQLProvider&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;// retuen a System.Data.SqlClient.SqlConnection&lt;br/&gt;private static SqlConnection GetDBConnection()&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;string ConnectionStr = "server=localhost\\SQLExpress;database=PlasmidDB;Integrated Security=SSPI;Trusted_Connection=Yes";&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;try {&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;return new SqlConnection(ConnectionStr);}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;catch (SqlException e)&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;string SqlMsg = ConstructSqlErrorMessage(e);}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;return null;}&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public static string ConstructSqlErrorMessage(SqlException e)&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;string SqlMsg="";&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;for (int i=0; i &amp;lt; e.Errors.Count; i++)&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;SqlMsg += "Index #" + i + ";" +&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;"Message: " + e.Errors[i].Message + ";" +&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;"LineNumber: " + e.Errors[i].LineNumber + ";" +&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;"Source: " + e.Errors[i].Source + ";" +&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;"Procedure: " + e.Errors[i].Procedure;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;return SqlMsg;}&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;// return a “status” object represent database statitcs&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public static Status GetDBStatus () {&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;Status StatusToGet= null;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;SqlConnection myConnection= GetDBConnection();&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;try {&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;SqlCommand myCommand = new SqlCommand("dbo.DBStatus", myConnection);&lt;br/&gt;// run a stored procedure “dbo.DBStatus”&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;myCommand.CommandType = CommandType.StoredProcedure;&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;myConnection.Open();&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;SqlDataReader reader = myCommand.ExecuteReader();&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;if (reader.Read()){&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;StatusToGet = new Status();&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;StatusToGet.TotalPlasmidNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;=&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;reader.GetInt32(0);&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;StatusToGet.TotalBackboneNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;=&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;reader.GetInt32(1);&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;StatusToGet.LastPlasmidID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;=&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;reader.GetInt32(2);&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;StatusToGet.TotalEnzymeNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;=&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;reader.GetInt32(3);&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;StatusToGet.TotalUserNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;=&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;reader.GetInt32(4);}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;catch (SqlException e){&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;string SqlMsg = ConstructSqlErrorMessage(e);}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;finally&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;myConnection.Close();}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;return StatusToGet;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public class Status&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;int totalPlasmidNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;= 0;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;int totalBackboneNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;= 0;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;int lastPlasmidID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;= 0;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;int totalEnzymeNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;= 0;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;int totalUserNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;= 0;&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public int TotalPlasmidNum {&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;get {return totalPlasmidNum;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;set {totalPlasmidNum=value;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public int TotalBackboneNum {&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;get {return totalBackboneNum;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;set {totalBackboneNum=value;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public int LastPlasmidID {&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;get {return lastPlasmidID;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;set {lastPlasmidID=value;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public int TotalEnzymeNum {&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;get {return totalEnzymeNum;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;set {totalEnzymeNum=value;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public int TotalUserNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;get {return totalUserNum;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;set {totalUserNum=value;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;}&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;public Status()&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;{}&lt;br/&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br/&gt;&lt;br/&gt;&lt;strong&gt;Second, let’s load the PlasmidView.DLL to MSH&lt;/strong&gt;&lt;br/&gt;&lt;br /&gt;&lt;blockquote&gt;[void][System.Reflection.Assembly]::LoadFile("D:\MSH\PlasmidView.dll")&lt;/blockquote&gt;&lt;br/&gt;&lt;br/&gt;&lt;strong&gt;Third, Let’s create a instance of&amp;nbsp;&amp;nbsp;“Status” object:&lt;/strong&gt;&lt;br/&gt;&lt;br /&gt;&lt;blockquote&gt;$Status = new-object PlasmidView.Status&lt;br/&gt;$Status |gm&lt;br/&gt;&lt;/blockquote&gt;&lt;br/&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TypeName: PlasmidView.Status&lt;br/&gt;&lt;br/&gt;Name&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; MemberType Definition&lt;br/&gt;----&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; ---------- ----------&lt;br/&gt;Equals&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Boolean Equals(Object obj)&lt;br/&gt;get_LastPlasmidID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int32 get_LastPlasmidID()&lt;br/&gt;get_TotalBackboneNum Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int32 get_TotalBackboneNum()&lt;br/&gt;get_TotalEnzymeNum&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int32 get_TotalEnzymeNum()&lt;br/&gt;get_TotalPlasmidNum&amp;nbsp;&amp;nbsp;Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int32 get_TotalPlasmidNum()&lt;br/&gt;get_TotalUserNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int32 get_TotalUserNum()&lt;br/&gt;GetHashCode&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Int32 GetHashCode()&lt;br/&gt;GetType&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Type GetType()&lt;br/&gt;set_LastPlasmidID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_LastPlasmidID(Int32 value)&lt;br/&gt;set_TotalBackboneNum Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_TotalBackboneNum(Int32 value)&lt;br/&gt;set_TotalEnzymeNum&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_TotalEnzymeNum(Int32 value)&lt;br/&gt;set_TotalPlasmidNum&amp;nbsp;&amp;nbsp;Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_TotalPlasmidNum(Int32 value)&lt;br/&gt;set_TotalUserNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.Void set_TotalUserNum(Int32 value)&lt;br/&gt;ToString&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Method&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; System.String ToString()&lt;br/&gt;LastPlasmidID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;Property&amp;nbsp;&amp;nbsp; System.Int32 LastPlasmidID {get;set;}&lt;br/&gt;TotalBackboneNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp; System.Int32 TotalBackboneNum {get;set;}&lt;br/&gt;TotalEnzymeNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp; System.Int32 TotalEnzymeNum {get;set;}&lt;br/&gt;TotalPlasmidNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;Property&amp;nbsp;&amp;nbsp; System.Int32 TotalPlasmidNum {get;set;}&lt;br/&gt;TotalUserNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; Property&amp;nbsp;&amp;nbsp; System.Int32 TotalUserNum {get;set;}&lt;br/&gt;&lt;br/&gt;&lt;strong&gt;Now, let’s try the GetDBStatus () method&lt;/strong&gt;&lt;br/&gt;&lt;br /&gt;&lt;blockquote&gt;[PlasmidView.SQLProvider]::GetDBStatus()&lt;br/&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br/&gt;TotalPlasmidNum&amp;nbsp;&amp;nbsp;: 21&lt;br/&gt;TotalBackboneNum : 8&lt;br/&gt;LastPlasmidID&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;: 20&lt;br/&gt;TotalEnzymeNum&amp;nbsp;&amp;nbsp; : 103&lt;br/&gt;TotalUserNum&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; : 8&lt;br/&gt;&lt;br/&gt;&lt;br/&gt;There two things I want to emphases:&lt;br/&gt;&lt;br/&gt;1. The original design requires a username and password for database access.&amp;nbsp;&amp;nbsp; I used Windows NT authentication for SQL server connection, and PlasmidView.SQLProvider class expose all SQL server operation as “&lt;strong&gt;static&lt;/strong&gt;” methods, so the security check has been bypassed.&amp;nbsp;&amp;nbsp;To regain access control over different user, I have to change C# code to check user credential every time before a SQL server operation.&lt;br/&gt;&lt;br/&gt;2. There is really no big difference when using a .Net class in C# or monad. What you need to do is to load the DLL and create the object by new-object cmdlet. Because monad automatically convert “&lt;strong&gt;public” &lt;/strong&gt;class properties to &lt;strong&gt;String&lt;/strong&gt;, quoting a object under MSH prompt will get formatted list of object public properties.&amp;nbsp;&amp;nbsp;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113625150733423881?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113625150733423881/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2005/12/working-with-sql-server-in-monad-using.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113625150733423881'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113625150733423881'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2005/12/working-with-sql-server-in-monad-using.html' title='Working with SQL server in monad using pre-compiled .NET Class Library (1)'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113596642238590189</id><published>2005-12-28T13:13:00.000-05:00</published><updated>2006-05-05T11:16:09.260-04:00</updated><title type='text'>NCBI Blastn under MSH command line</title><content type='html'>From NCBI web site:&lt;br /&gt;&lt;strong&gt;&lt;em&gt;The Basic Local Alignment Search Tool (BLAST) finds regions of local similarity between sequences. The program compares nucleotide or protein sequences to sequence databases and calculates the statistical significance of matches. BLAST can be used to infer functional and evolutionary relationships between sequences as well as help identify members of gene families. &lt;/em&gt;&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Blastn &lt;/strong&gt;is one of my most frequently used tools from NCBI. In stead of going to their web site, I can now run blastn under command line. It is convenient and even faster than web interfaces. Although I use "&lt;strong&gt;nr&lt;/strong&gt;" database here, you can change the URL string to use other database or other blast program.&lt;br /&gt;&lt;br /&gt;As for scripting, nothing magic here. Just rewrite original perl script using .NET class: &lt;strong&gt;System.Net.WebClient &lt;/strong&gt;. For &lt;strong&gt;Regular Expression&lt;/strong&gt;, we can use "&lt;strong&gt;-match&lt;/strong&gt;" expression.&lt;br /&gt;Thanks for &lt;a href="http://www.leeholmes.com/blog/RegularExpressionsInMonad.aspx" target="_blank"&gt;Lee Holmes Blog&lt;/A&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;# Begin of script&lt;br /&gt;# =============================================================&lt;br /&gt;# This code is for test purposes only. Use it at your own risk.&lt;br /&gt;# Please do not submit or retrieve more than one request every &lt;br /&gt;# two seconds. Results will be kept at NCBI for 24 hours. For &lt;br /&gt;# best batch performance,they recommend that you submit requests  &lt;br /&gt;# after 2000 EST (0100 GMT) and retrieve results before 0500 EST &lt;br /&gt;# (1000 GMT).&lt;br /&gt;# reference: &lt;a href="http://www.ncbi.nlm.nih.gov/blast/Doc/urlapi.html" target="_blank"&gt;http://www.ncbi.nlm.nih.gov/blast/Doc/urlapi.html&lt;/a&gt;&lt;br /&gt;# reference: &lt;a href="http://www.ncbi.nlm.nih.gov/blast/docs/web_blast.pl" target="_blank"&gt;http://www.ncbi.nlm.nih.gov/blast/docs/web_blast.pl&lt;/a&gt;&lt;br /&gt;# =============================================================&lt;br /&gt;# return codes:&lt;br /&gt;# 0 – success&lt;br /&gt;# 1 - invalid arguments&lt;br /&gt;# 2 - no hits found&lt;br /&gt;# 3 - rid expired&lt;br /&gt;# 4 - search failed&lt;br /&gt;# 5 - unknown error&lt;br /&gt;# =========================================================&lt;br /&gt;param([string] $query)&lt;br /&gt;&lt;br /&gt;if (-not $query)&lt;br /&gt;{&lt;br /&gt;  "Please specify query seqence!"&lt;br /&gt;  return 1&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;#Submit query sequence&lt;br /&gt;"================================================================="&lt;br /&gt;"Query sequence:"&lt;br /&gt;""&lt;br /&gt;$query&lt;br /&gt;""&lt;br /&gt;"Submit query sequence..."&lt;br /&gt;$uri="http://www.ncbi.nlm.nih.gov/blast/Blast.cgi?CMD=Put&amp;PROGRAM=blastn&amp;DATABASE=nr&amp;QUERY=" + $query&lt;br /&gt;$BlastClient = new-object System.Net.WebClient&lt;br /&gt;$pagecontent = $BlastClient.DownloadString($uri);&lt;br /&gt;"================================================================="&lt;br /&gt;# Get RID&lt;br /&gt;$pagecontent -match "   RID = (.*)"&lt;br /&gt;$RID=$Matches[1] &lt;br /&gt;"RID=" + $RID&lt;br /&gt;" "&lt;br /&gt;$pagecontent -match "   RTOE = (.*)"&lt;br /&gt;$TimeToComplete= $Matches[1]&lt;br /&gt;"Time to complete search: " + $TimeToComplete + " seconds or sooner. Waiting..."&lt;br /&gt;" "&lt;br /&gt;Start-sleep $TimeToComplete&lt;br /&gt;&lt;br /&gt;#Waiting for results&lt;br /&gt;While ($true)&lt;br /&gt;{&lt;br /&gt;  Start-sleep 5&lt;br /&gt;  $uri= "http://www.ncbi.nlm.nih.gov/blast/Blast.cgi?CMD=Get&amp;FORMAT_OBJECT=SearchInfo&amp;RID=" + $RID&lt;br /&gt; &lt;br /&gt;  $pagecontent = $BlastClient.DownloadString($uri);&lt;br /&gt;&lt;br /&gt;  if ($pagecontent -match "Status=WAITING")&lt;br /&gt;  {&lt;br /&gt;    "Results not ready, waiting..."&lt;br /&gt;    "================================================================="&lt;br /&gt;    continue&lt;br /&gt;  }&lt;br /&gt; &lt;br /&gt;  if ($pagecontent -match "Status=FAILED")&lt;br /&gt;  {&lt;br /&gt;    "Search failed, exiting..."&lt;br /&gt;    return 2&lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;  if ($pagecontent -match "Status=UNKNOWN")&lt;br /&gt;  {&lt;br /&gt;    "Search expired, exiting..."&lt;br /&gt;    return 3&lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;  if ($pagecontent -match "Status=READY")&lt;br /&gt;  {  &lt;br /&gt;      if ($pagecontent -match "ThereAreHits=yes")&lt;br /&gt;      {&lt;br /&gt;        "Search complete, retrieving results...";&lt;br /&gt; "================================================================="&lt;br /&gt; break&lt;br /&gt;      }&lt;br /&gt;      else&lt;br /&gt;      {&lt;br /&gt;        "No hits found.\n";&lt;br /&gt;        return 4&lt;br /&gt;      }&lt;br /&gt;   }&lt;br /&gt;   return 5&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;# Get results&lt;br /&gt;$uri= "http://www.ncbi.nlm.nih.gov/blast/Blast.cgi?CMD=Get&amp;RID=" + $RID + "&amp;ALIGNMENTS=500&amp;ALIGNMENT_VIEW=QueryAnchored&amp;FORMATOBJECT=Alignment&amp;FORMAT_TYPE=TEXT"&lt;br /&gt;$pagecontent = $BlastClient.DownloadString($uri);&lt;br /&gt;$pagecontent &gt;.\blast.results&lt;br /&gt;Get-content .\blast.results | more &lt;br /&gt;return 0&lt;br /&gt;#End of script&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;So if we do this under MSH prompt:&lt;br /&gt;&lt;strong&gt;. blastn-nr.msh AAAAAAAAGGGGGGCCCCCTTTT &lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;the output would like:&lt;br /&gt;&lt;br /&gt;==============================================================&lt;br /&gt;Query sequence: AAAAAAAAGGGGGGCCCCCTTTT&lt;br /&gt;Submit query sequence...&lt;br /&gt;RID=1135712055-18130-135523741431.BLASTQ1&lt;br /&gt;Time to complete search: 12 seconds or sooner. Waiting...&lt;br /&gt;Results not ready, waiting...&lt;br /&gt;Search complete, retrieving results...&lt;br /&gt;=============================================================&lt;br /&gt;&lt;br /&gt;BLASTN 2.2.12 [Aug-07-2005]Reference: Altschul, Stephen F., Thomas L. Madden,&lt;br /&gt;Alejandro A. Schffer,Jinghui Zhang, Zheng Zhang, Webb Miller, and David J. Lipman&lt;br /&gt;(1997), "Gapped BLAST and PSI-BLAST: a new generation ofprotein database search&lt;br /&gt;programs", Nucleic Acids Res. 25:3389-3402.&lt;br /&gt;&lt;br /&gt;RID: 1135712055-18130-135523741431.BLASTQ1&lt;br /&gt;&lt;br /&gt;Database: All GenBank+EMBL+DDBJ+PDB sequences (but no EST, STS,GSS,environmental&lt;br /&gt;samples or phase 0, 1 or 2 HTGS sequences) 3,659,359 sequences; 16,326,075,880 &lt;br /&gt;total letters&lt;br /&gt;&lt;br /&gt;Query= (23 letters)&lt;br /&gt;&lt;br /&gt;Score ESequences producing significant alignments: (Bits) Valued&lt;br /&gt;AK202294.1 Mus musculus cDNA, clone:Y1G0140P22, strand:m... 40.1 0.067gb&lt;br /&gt;AF467007.1AF467007S1 Homo sapiens histidine N-methyltrans... 38.2 0.27&lt;br /&gt;dbjAK192209.1 Mus musculus cDNA, clone:Y1G0108D05, strand:m... 38.2 0.27&lt;br /&gt;embAJ333598.1HSA333598 Homo sapiens genomic sequence surrou... 38.2 0.27&lt;br /&gt;embAJ343149.1HSA343149 Homo sapiens genomic sequence surrou... 38.2 0.27&lt;br /&gt;embAJ343845.1HSA343845 Homo sapiens genomic sequence surrou... 38.2 0.27&lt;br /&gt;gbAY811874.1 Schistosoma japonicum SJCHGC01957 protein mRNA, p 36.2 1.0&lt;br /&gt;dbjAB232923.1 Oryzias latipes hox gene cluster, complete cds, 36.2 1.0&lt;br /&gt;dbjBS000120.2 Pan troglodytes chromosome 22 clone:RP43-007D... 36.2 1.0&lt;br /&gt;......&lt;br /&gt;&lt;br /&gt;&amp;gt;gbAY811874.1 Schistosoma japonicum SJCHGC01957 protein mRNA, partial cds&lt;br /&gt;Length=718&lt;br /&gt;Score = 36.2 bits (18),&lt;br /&gt;Expect = 1.0&lt;br /&gt;Identities = 18/18 (100%),&lt;br /&gt;Gaps = 0/18 (0%)&lt;br /&gt;Strand=Plus/Minus&lt;br /&gt;Query 2 AAAAAAAGGGGGGCCCCC 19&lt;br /&gt;Sbjct 156 AAAAAAAGGGGGGCCCCC 139&lt;br /&gt;......&lt;br /&gt;&lt;br /&gt;Database: All GenBank+EMBL+DDBJ+PDB sequences (but no EST, STS,&lt;br /&gt; GSS,environmentalsamples or phase 0, 1 or 2 HTGS sequences)&lt;br /&gt;Posted date: Dec 26, 2005 4:16 AM&lt;br /&gt;Number of letters in database: -853,793,300&lt;br /&gt;Number of sequences in database: 3,659,359&lt;br /&gt;Lambda K H 1.37 0.711 1.31&lt;br /&gt;GappedLambda K H 1.37 0.711 1.31&lt;br /&gt;Matrix: blastn matrix:1 -3&lt;br /&gt;Gap Penalties:&lt;br /&gt;Existence: 5,&lt;br /&gt;Extension: 2&lt;br /&gt;Number of Sequences: 3659359&lt;br /&gt;Number of Hits to DB: 2403072&lt;br /&gt;Number of extensions: 36138&lt;br /&gt;Number of successful extensions: 36138&lt;br /&gt;Number of sequences better than 10: 21&lt;br /&gt;Number of HSP's better than 10 without gapping: 21&lt;br /&gt;Number of HSP's gapped: 36138&lt;br /&gt;Number of HSP's successfully gapped: 21&lt;br /&gt;Number of extra gapped extensions for HSPs above 10: 36070&lt;br /&gt;Length of query: 23&lt;br /&gt;Length of database: 16326075880&lt;br /&gt;Length adjustment: 18&lt;br /&gt;Effective length of query: 5&lt;br /&gt;Effective length of database: 16260207418&lt;br /&gt;Effective search space: 81301037090&lt;br /&gt;Effective search space used: 81301037090&lt;br /&gt;A: 0X1: 11 (21.8 bits)&lt;br /&gt;X2: 15 (29.7 bits)&lt;br /&gt;X3: 25 (49.6 bits)&lt;br /&gt;S1: 11 (22.3 bits)&lt;br /&gt;S2: 17 (34.2 bits)&lt;br /&gt;====================================================&lt;br /&gt;&lt;strong&gt;Have fun!&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113596642238590189?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113596642238590189/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2005/12/ncbi-blastn-under-msh-command-line.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113596642238590189'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113596642238590189'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2005/12/ncbi-blastn-under-msh-command-line.html' title='NCBI Blastn under MSH command line'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113591696097769041</id><published>2005-12-19T23:26:00.000-05:00</published><updated>2006-05-05T11:16:37.920-04:00</updated><title type='text'>Play with ACL in MSH</title><content type='html'>I have a laptop running Windows XP home edition. As you known, to force you pay more money for professional edition, Mico$oft disabled the "Security" tab in file or directory "Properties" dialogue window. To set ACL, I have to use cacls.exe (come with windows). If you want more functionality, use setacl.exe (under GPL, you can download from sourceforge.org)&lt;br /&gt;&lt;br /&gt;It is OK, if you just do adjustments for a few files. It becomes a tedious job, if you have lot of files or directories to modify. So let's give MSH a try.&lt;br /&gt;&lt;br /&gt;There are two cmd-let designed for this job:&lt;br /&gt;get-acl : Gets the access control list (ACL) associated with a file or object.&lt;br /&gt;get-acl [[-Path] System.String[]] [[-Filter] System.String] [[-Include]&lt;br /&gt;system.String[]] [[-Exclude] System.String[]] [[-Audit] [System.Boolean]]&lt;br /&gt;&lt;br /&gt;set-acl: Set the security Access Control List for an item or items.&lt;br /&gt;set-acl [-ACLObject] aclobject [-Path path]&lt;br /&gt;[-Include include] [-Exclude exclude] [-Filter filter] [-Passthru]&lt;br /&gt;&lt;br /&gt;But there is a trick here. In order to set group or set owner, you need an instance of [system.security.principal.ntaccount] object in hand.&lt;br /&gt;&lt;br /&gt;#######################################&lt;br /&gt;# Let's get acl for file text.txt&lt;br /&gt;$acl=get-acl text.txt&lt;br /&gt;$acl format-list&lt;br /&gt;&lt;br /&gt;#You will get something like&lt;br /&gt;#Path : FileSystem::D:\text.txt&lt;br /&gt;#Owner : Computer\me&lt;br /&gt;#Group : Computer\None&lt;br /&gt;#Access : BUILTIN\Administrators Allow FullControl&lt;br /&gt;# Computer\me Allow FullControl&lt;br /&gt;#Audit :&lt;br /&gt;#Sddl : Bla…Bla…Bla…&lt;br /&gt;&lt;br /&gt;#So we can manipulate this acl object now. Let's try to change group to&lt;br /&gt;# BUILTIN\Administrators.&lt;br /&gt;#Get a [system.security.principal.ntaccount] object&lt;br /&gt;$Account = new-object system.security.principal.ntaccount("Administrators ")&lt;br /&gt;&lt;br /&gt;#To check whether the group is valid&lt;br /&gt;$SID = $Account.translate([system.security.principal.securityidentifier])&lt;br /&gt;$SID&lt;br /&gt;&lt;br /&gt;#You will see&lt;br /&gt;#BinaryLength AccountDomainSid Value&lt;br /&gt;#------------ ---------------- -----&lt;br /&gt;# 16 S-1-5-32-544&lt;br /&gt;#If you see some error message here, you $Account is invalid.&lt;br /&gt;&lt;br /&gt;#Use setgroup method of acl object&lt;br /&gt;$acl.setgroup($Account)&lt;br /&gt;$acl format-list&lt;br /&gt;&lt;br /&gt;#You will get something like&lt;br /&gt;#Path : FileSystem::D:\text.txt&lt;br /&gt;#Owner : Computer\me&lt;br /&gt;#Group : BUILTIN\Administrators (We made change here!!!!!!!!!!!!!!!)&lt;br /&gt;#Access : BUILTIN\Administrators Allow FullControl&lt;br /&gt;# Computer\me Allow FullControl&lt;br /&gt;#Audit :&lt;br /&gt;#Sddl : Bla…Bla…Bla…&lt;br /&gt;&lt;br /&gt;#But this ACL object is in memory, we need to apply them to file&lt;br /&gt;set-acl -aclobject $acl -path D:\text.txt&lt;br /&gt;&lt;br /&gt;#make sure you have both -aclobject and -path, otherwise you will get some error.&lt;br /&gt;###############################################&lt;br /&gt;&lt;br /&gt;This scheme can be easily changed to modify directory acl or grant access to any user.&lt;br /&gt;You can use get-member cmd-let to explore other methods or property of $acl. I will leave those excise to readers.&lt;br /&gt;&lt;br /&gt;Reference&lt;br /&gt;&lt;A href="http://mow001.blogspot.com/2005/10/getting-and-using-securityprincipal.html"&gt;http://mow001.blogspot.com/2005/10/getting-and-using-securityprincipal.html&lt;/A&gt;&lt;br /&gt;&lt;br /&gt;[Edit: Monad has now been renamed to Windows PowerShell. This script or discussion may require slight adjustments before it applies directly to newer builds.]&lt;br /&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/PowerShell" rel="tag"&gt;PowerShell&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113591696097769041?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113591696097769041/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2005/12/play-with-acl-in-msh.html#comment-form' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113591696097769041'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113591696097769041'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2005/12/play-with-acl-in-msh.html' title='Play with ACL in MSH'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113591677014741184</id><published>2005-12-16T23:11:00.000-05:00</published><updated>2006-01-05T22:19:57.443-05:00</updated><title type='text'>Find Amino Acid mutation</title><content type='html'>Yesterday, we had a quiz on Mass Spectrometry. There is one question Find Amino Acid mutation:&lt;br /&gt;There is a single amino acid mutation on SOD protein from ALS patient. After degradation by Lys-C proteinase and MALDI-TOF analysis, there is a molecular ion at 1689Da. But in wild type SOD protein, it should be 1765Da. That is to say the single amino acid mutation cause reduce of peptide molacular weight of 66Da. What exactly is that mutation.&lt;br /&gt;&lt;br /&gt;In a another word: there are 20 amino acid,the difference of molecular weight is 66Da, what 2 amino acid is that. This is a simple combination. In the DOS world, I proberbly use QBasic. But now we can try MSH:&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;#Name of Amino acid&lt;br /&gt;$AAName = @("Ala";"Arg";"Asn";"Asp";"Cys";"Glu";"Gln";"Gly";"His";"Ile";"Leu";&lt;br /&gt;"Lys";"Met";"Phe";"Pro";"Ser";"Thr";"Trp";"Tyr";"Val")&lt;br /&gt;&lt;br /&gt;#Molecular weight of amino acid&lt;br /&gt;$AAMw = @(71.08;156.19;114.10;115.09;103.15;129.12;128.13;57.05;137.14;113.16;&lt;br /&gt;113.16;128.17;131.20;147.18;97.12;87.08;101.11;186.21;163.18;99.13)&lt;br /&gt;&lt;br /&gt;#Substract one verse another&lt;br /&gt;for ($i=0;$i -lt 20;$i++) {&lt;br /&gt;for ($j=$i; $j -lt 20;$j++) {&lt;br /&gt;if ($AAMw[$i] -ge $AAMw[$j]) {&lt;br /&gt;$change= $AAMw[$i] - $AAMw[$j]&lt;br /&gt;}&lt;br /&gt;else {&lt;br /&gt;$change= $AAMw[$j] - $AAMw[$i]&lt;br /&gt;}&lt;br /&gt;if ($change -gt 66 -and $change -lt 67) {&lt;br /&gt;if ($AAMw[$i] -ge $AAMw[$j]) {&lt;br /&gt;$AAName[$i] + "(" + $AAMw[$i].Tostring() + ")" + "-&amp;gt;" + $AAName[$j] + "("&lt;br /&gt;+ $AAMw[$j].ToString() + ")" + ":" + $change.ToString()&lt;br /&gt;}&lt;br /&gt;else {&lt;br /&gt;$AAName[$j] + "(" + $AAMw[$j].Tostring() + ")" + "-&amp;gt;" + $AAName[$i] + "("&lt;br /&gt;+ $AAMw[$i].ToString() + ")" + ":" + $change.ToString()&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;Results:&lt;br /&gt;His(137.14)-&amp;gt;Ala(71.08):66.06&lt;br /&gt;Tyr(163.18)-&amp;gt;Pro(97.12):66.06&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113591677014741184?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113591677014741184/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2005/12/find-amino-acid-mutation.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113591677014741184'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113591677014741184'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2005/12/find-amino-acid-mutation.html' title='Find Amino Acid mutation'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113591584066726748</id><published>2005-12-09T23:02:00.000-05:00</published><updated>2006-01-05T22:20:33.086-05:00</updated><title type='text'>My First MSH Script</title><content type='html'>&lt;blockquote&gt;&lt;br /&gt;#===========================================================&lt;br /&gt;#This script will check colinux service, start a colinux console (NT).&lt;br /&gt;#This script comes with NO warrenty! Use at your own risk!&lt;br /&gt;#===========================================================&lt;br /&gt;&lt;br /&gt;"Cheching Colinux Service...."&lt;br /&gt;$CoService = get-service Where-object {$_.ServiceName -like "*colinux*"}&lt;br /&gt;if (!$CoService) { throw "Colinux Service Not Installed ! "}&lt;br /&gt;"Found Colinux Service..."&lt;br /&gt;$CoService&lt;br /&gt;if ( $coservice.status.ToString() -ne "Running"){&lt;br /&gt;"Colinux Service is NOT running ! Try to start Colinux Service..."&lt;br /&gt;$coservice.Start()&lt;br /&gt;}&lt;br /&gt;"Colinux Service Is Running ! Get Colinux-daemon Process..."&lt;br /&gt;$CoProcess = get-process Where-object {$_.ProcessName -like "*colinux-daemon*"}&lt;br /&gt;if (!$CoProcess){ throw "Colinux-daemon Is Not Running ! " }&lt;br /&gt;"Colinux-daemon Is Running ... "&lt;br /&gt;$CoProcess&lt;br /&gt;"Try to start Colinux console..."&lt;br /&gt;$CoConsoleProcess = get-process Where-object {$_.ProcessName -like "*colinux-console*"}&lt;br /&gt;$CoPID = [string] $CoProcess.Id&lt;br /&gt;if (!$CoConsoleProcess){&lt;br /&gt;D:\colinux\colinux-console-nt -a $CoPID&lt;br /&gt;}&lt;br /&gt;else{&lt;br /&gt;"Colinux-console (NT) already running !&lt;br /&gt;"Quiting ..."&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113591584066726748?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113591584066726748/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2005/12/my-first-msh-script.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113591584066726748'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113591584066726748'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2005/12/my-first-msh-script.html' title='My First MSH Script'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-20327311.post-113591532207658544</id><published>2005-12-02T22:52:00.000-05:00</published><updated>2006-01-05T22:21:02.803-05:00</updated><title type='text'>Ready for MSH</title><content type='html'>MSH, code name "Monad" , is next generation of microsoft command line tools.&lt;br /&gt;&lt;br /&gt;Get MSH&lt;br /&gt;&lt;a href="http://www.microsoft.com/technet/scriptcenter/topics/msh/download.mspx"&gt;http://www.microsoft.com/technet/scriptcenter/topics/msh/download.mspx&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Information for monad&lt;br /&gt;&lt;a href="http://www.reskit.net/monad/"&gt;http://www.reskit.net/monad/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Monad team blog&lt;br /&gt;&lt;a href="http://blogs.msdn.com/monad/"&gt;http://blogs.msdn.com/monad/&lt;/a&gt;&lt;br /&gt;&lt;P&gt; Tags: &lt;a href="http://technorati.com/tag/msh" rel="tag"&gt;msh&lt;/a&gt; &amp;nbsp;&amp;nbsp;&amp;nbsp;&lt;a href="http://technorati.com/tag/monad" rel="tag"&gt;monad&lt;/a&gt;&lt;/P&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/20327311-113591532207658544?l=mshforfun.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://mshforfun.blogspot.com/feeds/113591532207658544/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://mshforfun.blogspot.com/2005/12/ready-for-msh.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113591532207658544'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/20327311/posts/default/113591532207658544'/><link rel='alternate' type='text/html' href='http://mshforfun.blogspot.com/2005/12/ready-for-msh.html' title='Ready for MSH'/><author><name>Tony</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry></feed>
