30/Mar/2013にあった、めとべやでのセッションでXingle先生が、PowerShellの限界とか、PowerShellダメ!! とか言われたので試しました。 いえ別にムキにはなっていませんし、Surface開けて真っ先にやったことがPowershellなんてこともありません。
PowerShell ISEがない
アイスがないとか、なんてことでしょう……。 この時点でやる気が8割失われました。 でもps1が読めるっていうし……が、頑張る。
ちなみに、ProcessでPowerShell_ISEでもダメでした。
PowerShellをタスクバーにピン止め
当然です。やりましょう。
Set-ExecutionPolicyは可能
何はともあれ、新PCを手に入れたらやりましょう。 例の通り、管理者権限でPowerShellを起動します。
Set-ExecutionPolicy RemoteSigned
Enable-PSremotingは可能
これで、Windows RT端末に他のPowerShell使える端末からリモート操作ができます。 これも、管理者権限でPowerShellを起動します。
Enable-PSRemoting
Surfaceに繋ぐPCでTrustedHost設定も可能
管理者権限で、ClientがTurstするServerを設定をします。 これ、いまだに「なぜClientが信頼するServerを設定する」のか謎でしょうがないです。 これをしないと、対象のPCに手元のClient PCから接続できません。
winrm s winrm/config/client '@{TrustedHosts="*"}'
勿論Surface上で有効化も可能です。
コマンドレット数が制限されてる
さて、まずは何が出来ないのか見る前に、ざっくりとWindows 8とWindows RTとのコマンドレット数の違いから見ましょう。
OS | Cmdlet数 |
Windows 8 Pro (No Module) | 1396 |
Surface RT | 869 |
Windows 8が、Document下の.\WindowsPowerShell\Modulesをリネームして読み込まないようにした状態です。 Windows RTは、購入直後10分ぐらいです。 [
何のコマンドが無いのかを見ると、Invoke-Processを初めとしてちょろちょろ抜けています……なので、PowerShellからProcess実行は此処でも制限をかけようとしているようですね。
参照の追加はできるがインスタンスからメソッドが
参照の追加、コンパイルしてロードまでやってくれる便利な奴といえば、Add-Typeですね。 では、参照追加の必要な[System.Windows.Forms]
を試しましょう。
Add-Type -AssembyName System.Windows.Forms
追加できました。では、読めているかを確認してみて…
[System.Windows.Forms.MessageBox]
読めてます。
ではメソッドを呼び出そうとすると
[System.Windows.Forms.MessageBox]::Show("")
メソッドを呼び出せません。この言語モードでは、メソッドの呼び出しはコアの型のみでサポートされています。
言語ですか……ふむ。
昔ながらのあれもだめ
今は亡きあれです、[Reflection.Assembly]を使ってみましょう。
[Reflection.Assembly]::LoadWithPartialName("System.Windows.Forms")
同じエラーではじかれます。
メソッドを呼び出せません。この言語モードでは、メソッドの呼び出しはコアの型のみでサポートされています。
ようはNew-Objectが許可されていない
つまり、New-Objectの時点でダメな訳です。
New-Object -ComObject Excel.Application
型を生成できません。この言語モードでは、メソッドの呼び出しはコアの型のみでサポートされています。
C# Definitionを直に読み込ませたらどう
誰もが考える方法です。
Add-Type -TypeDefinition "public class hogehoge {}"
型を追加できません。この言語モードでは、新しい方の定義はサポートされていません。
言語モードってどういうこと
これは、RunSpaceの言語モードを示します。
$host.Runspace.LanguageMode
通常、Windows 8などのx86/64 PCでは、次の言語モードです。
FullLanguage
これが、Windows RT, Surfaceではこうです。
ConstrainedLanguage
つまり言語モードが違うために出来ないわけですね。
セッションの言語モードを変えてみる
なら、Session中の言語をFull Languageに変えたらごまかされない?とやってみます。 セッションを作って。
$surface = New-PSSession -ComputerName surface
セッション成立を確認して
$surface
セッションに入って…これで、Surface上で操作となります。 Microsoft Account同志なのでGet-Credentialいらず ((
Enter-PSSession -Session $surface
Surface上で、PSSessionConfigurationを取得します。
[surface]: PS C:\Users\acquire\Documents> Get-PSSessionConfiguration | select *
結果です。
Architecture : 32 Filename : %windir%\system32\pwrshplugin.dll ResourceUri : http://schemas.microsoft.com/powershell/microsoft.powershell MaxConcurrentCommandsPerShell : 1000 Capability : {Shell} xmlns : http://schemas.microsoft.com/wbem/wsman/1/config/PluginConfiguration MaxConcurrentUsers : 5 Name : microsoft.powershell SupportsOptions : true ProcessIdleTimeoutSec : 0 ExactMatch : False RunAsUser : IdleTimeoutms : 7200000 OutputBufferingMode : Block PSVersion : 3.0 SecurityDescriptorSddl : O:NSG:BAD:P(A;;GA;;;BA)(A;;GA;;;RM)S:P(AU;FA;GA;;;WD)(AU;SA;GXGW;;;WD) MaxShellsPerUser : 25 AutoRestart : false MaxShells : 25 MaxIdleTimeoutms : 2147483647 Uri : http://schemas.microsoft.com/powershell/microsoft.powershell SDKVersion : 2 XmlRenderingType : text RunAsPassword : MaxProcessesPerShell : 15 ParentResourceUri : http://schemas.microsoft.com/powershell/microsoft.powershell Enabled : true UseSharedProcess : false MaxMemoryPerShellMB : 1024 lang : ja-JP Permission : BUILTIN\Administrators AccessAllowed, BUILTIN\Remote Management Users AccessAllowed Architecture : 32 Filename : %windir%\system32\pwrshplugin.dll PSSessionConfigurationTypeName : Microsoft.PowerShell.Workflow.PSWorkflowSessionConfiguration MaxProcessesPerShell : 15 MaxConcurrentCommandsPerShell : 1000 PersistencePath : C:\Users\acquire\AppData\Local\Microsoft\Windows\PowerShell\WF\PS Capability : {Shell} AllowedActivity : {PSDefaultActivities} xmlns : http://schemas.microsoft.com/wbem/wsman/1/config/PluginConfiguration PersistWithEncryption : False MaxConcurrentUsers : 5 RemoteNodeSessionIdleTimeoutSec : 60 Name : microsoft.powershell.workflow OutOfProcessActivity : {InlineScript} SessionConfigurationData : <SessionConfigurationData> <Param Name="ModulesToImport" Value="%windir%\system32\windowspowershell\v1.0\Modu les\PSWorkflow"/> <Param Name="PrivateData"> <PrivateData> <Pa ram Name="enablevalidation" Value="true" /> </Pri vateData> </Param> </Sess ionConfigurationData> MaxSessionsPerWorkflow : 5 SupportsOptions : true ProcessIdleTimeoutSec : 28800 ExactMatch : False RunAsUser : IdleTimeoutms : 7200000 SessionThrottleLimit : 100 OutputBufferingMode : Block MaxActivityProcesses : 5 ResourceUri : http://schemas.microsoft.com/powershell/microsoft.powershell.workflow ActivityProcessIdleTimeoutSec : 60 MaxPersistenceStoreSizeGB : 10 SecurityDescriptorSddl : O:NSG:BAD:P(A;;GA;;;BA)(A;;GA;;;RM)S:P(AU;FA;GA;;;WD)(AU;SA;GXGW;;;WD) MaxShellsPerUser : 25 ModulesToImport : %windir%\system32\windowspowershell\v1.0\Modules\PSWorkflow AutoRestart : false MaxShells : 25 MaxConnectedSessions : 100 MaxMemoryPerShellMB : 1024 MaxIdleTimeoutms : 2147483647 Uri : http://schemas.microsoft.com/powershell/microsoft.powershell.workflow SDKVersion : 2 XmlRenderingType : text RunAsPassword : PSVersion : 3.0 ParentResourceUri : http://schemas.microsoft.com/powershell/microsoft.powershell.workflow MaxRunningWorkflows : 30 WorkflowShutdownTimeoutMSec : 500 EnableValidation : true Enabled : true UseSharedProcess : true MaxSessionsPerRemoteNode : 5 MaxDisconnectedSessions : 1000 AssemblyName : Microsoft.PowerShell.Workflow.ServiceCore, Version=3.0.0.0, Culture=neutral, PublicKe yToken=31bf3856ad364e35, processorArchitecture=MSIL lang : ja-JP Permission : BUILTIN\Administrators AccessAllowed, BUILTIN\Remote Management Users AccessAllowed
新しいセッション設定をRT上で出します。
New-PSSessionConfigurationFile -Path .\default.pssc
取得できたファイルで、LanguageをFull Languageになっていることを確認します。 大丈夫ですね?
@{ # このセッション構成に使用されるスキーマのバージョン番号 SchemaVersion = '1.0.0.0' # このセッション構成を一意に識別するために使用される ID。 GUID = 'c4d41614-4bf7-4ed8-951a-ff23963f14f2' # このセッション構成の実行ポリシーを指定します ExecutionPolicy = 'Restricted' # このセッション構成の言語モードを指定します LanguageMode = 'FullLanguage' # このセッション構成の初期状態 SessionType = 'Default' # このセッション構成で定義される環境変数 # EnvironmentVariables = # このセッション構成の作成者 Author = 'acquire' # Company associated with this session configuration CompanyName = '不明' # このセッション構成の著作権情報 Copyright = '(c) 2013 acquire. All rights reserved.' # このセッション構成の機能の説明 # Description = # このセッション構成で使用される Windows PowerShell エンジンのバージョン # PowerShellVersion = # インポートされるモジュール。 # ModulesToImport = # このセッション構成で読み込まれるアセンブリ # AssembliesToLoad = # このセッション構成で表示されるエイリアス # VisibleAliases = # このセッション構成で表示されるコマンドレット VisibleCmdlets = 'Get-*' # このセッション構成で表示される関数 # VisibleFunctions = # このセッション構成で表示されるプロバイダー # VisibleProviders = # このセッション構成で定義されるエイリアス # AliasDefinitions = # このセッション構成で定義される関数 # FunctionDefinitions = # このセッション構成で定義される変数 # VariableDefinitions = # このセッション構成で読み込まれる型ファイル (.ps1xml) # TypesToProcess = # このセッション構成で読み込まれる書式ファイル (.ps1xml)。 # FormatsToProcess = # セッションの構成後に実行するスクリプトを指定します # ScriptsToProcess = }
Windows RT, Surface上でFull Languageな設定を読み込ませます。
Register-PSSessionConfiguration -Name "FullLanguage" -Path .\default.pssc
Language設定がFullLanguageになったことを確認します。
Get-PSSessionConfiguration | select *
なってます。
[Surface]: PS C:\Users\acquire\Desktop> Get-PSSessionConfiguration | select * Copyright : (c) 2013 acquire. All rights reserved. CompanyName : 不明 GUID : c4d41614-4bf7-4ed8-951a-ff23963f14f2 Author : acquire VisibleCmdlets : Get-* SessionType : Default ExecutionPolicy : Restricted SchemaVersion : 1.0.0.0 LanguageMode : FullLanguage Architecture : 32 Filename : %windir%\system32\pwrshplugin.dll ResourceUri : http://schemas.microsoft.com/powershell/FullLanguage MaxConcurrentCommandsPerShell : 1000 Capability : {Shell} xmlns : http://schemas.microsoft.com/wbem/wsman/1/config/PluginConfiguration MaxConcurrentUsers : 5 Name : FullLanguage SupportsOptions : true ProcessIdleTimeoutSec : 0 ExactMatch : true ConfigFilePath : C:\Windows\System32\WindowsPowerShell\v1.0\SessionConfig\FullLanguage_c4d41614-4bf7-4ed 8-951a-ff23963f14f2.pssc RunAsUser : IdleTimeoutms : 7200000 OutputBufferingMode : Block PSVersion : 3.0 SecurityDescriptorSddl : O:NSG:BAD:P(A;;GA;;;BA)(A;;GA;;;RM)S:P(AU;FA;GA;;;WD)(AU;SA;GXGW;;;WD) MaxShellsPerUser : 25 AutoRestart : false MaxShells : 25 MaxIdleTimeoutms : 43200000 Uri : http://schemas.microsoft.com/powershell/FullLanguage SDKVersion : 2 XmlRenderingType : text RunAsPassword : MaxProcessesPerShell : 15 ParentResourceUri : http://schemas.microsoft.com/powershell/FullLanguage Enabled : True UseSharedProcess : false MaxMemoryPerShellMB : 1024 lang : ja-JP Permission : BUILTIN\Administrators AccessAllowed, BUILTIN\Remote Management Users AccessAllowed Architecture : 32 Filename : %windir%\system32\pwrshplugin.dll ResourceUri : http://schemas.microsoft.com/powershell/microsoft.powershell MaxConcurrentCommandsPerShell : 1000 Capability : {Shell} xmlns : http://schemas.microsoft.com/wbem/wsman/1/config/PluginConfiguration MaxConcurrentUsers : 5 Name : microsoft.powershell SupportsOptions : true ProcessIdleTimeoutSec : 0 ExactMatch : False RunAsUser : IdleTimeoutms : 7200000 OutputBufferingMode : Block PSVersion : 3.0 SecurityDescriptorSddl : O:NSG:BAD:P(A;;GA;;;BA)(A;;GA;;;RM)S:P(AU;FA;GA;;;WD)(AU;SA;GXGW;;;WD) MaxShellsPerUser : 25 AutoRestart : false MaxShells : 25 MaxIdleTimeoutms : 2147483647 Uri : http://schemas.microsoft.com/powershell/microsoft.powershell SDKVersion : 2 XmlRenderingType : text RunAsPassword : MaxProcessesPerShell : 15 ParentResourceUri : http://schemas.microsoft.com/powershell/microsoft.powershell Enabled : true UseSharedProcess : false MaxMemoryPerShellMB : 1024 lang : ja-JP Permission : BUILTIN\Administrators AccessAllowed, BUILTIN\Remote Management Users AccessAllowed Architecture : 32 Filename : %windir%\system32\pwrshplugin.dll PSSessionConfigurationTypeName : Microsoft.PowerShell.Workflow.PSWorkflowSessionConfiguration MaxProcessesPerShell : 15 MaxConcurrentCommandsPerShell : 1000 PersistencePath : C:\Users\acquire\AppData\Local\Microsoft\Windows\PowerShell\WF\PS Capability : {Shell} AllowedActivity : {PSDefaultActivities} xmlns : http://schemas.microsoft.com/wbem/wsman/1/config/PluginConfiguration PersistWithEncryption : False MaxConcurrentUsers : 5 RemoteNodeSessionIdleTimeoutSec : 60 Name : microsoft.powershell.workflow OutOfProcessActivity : {InlineScript} SessionConfigurationData : <SessionConfigurationData> <Param Name="ModulesToImport" Value="%windir%\system32\windowspowershell\v1.0\Modu les\PSWorkflow"/> <Param Name="PrivateData"> <PrivateData> <Pa ram Name="enablevalidation" Value="true" /> </Pri vateData> </Param> </Sess ionConfigurationData> MaxSessionsPerWorkflow : 5 SupportsOptions : true ProcessIdleTimeoutSec : 28800 ExactMatch : False RunAsUser : IdleTimeoutms : 7200000 SessionThrottleLimit : 100 OutputBufferingMode : Block MaxActivityProcesses : 5 ResourceUri : http://schemas.microsoft.com/powershell/microsoft.powershell.workflow ActivityProcessIdleTimeoutSec : 60 MaxPersistenceStoreSizeGB : 10 SecurityDescriptorSddl : O:NSG:BAD:P(A;;GA;;;BA)(A;;GA;;;RM)S:P(AU;FA;GA;;;WD)(AU;SA;GXGW;;;WD) MaxShellsPerUser : 25 ModulesToImport : %windir%\system32\windowspowershell\v1.0\Modules\PSWorkflow AutoRestart : false MaxShells : 25 MaxConnectedSessions : 100 MaxMemoryPerShellMB : 1024 MaxIdleTimeoutms : 2147483647 Uri : http://schemas.microsoft.com/powershell/microsoft.powershell.workflow SDKVersion : 2 XmlRenderingType : text RunAsPassword : PSVersion : 3.0 ParentResourceUri : http://schemas.microsoft.com/powershell/microsoft.powershell.workflow MaxRunningWorkflows : 30 WorkflowShutdownTimeoutMSec : 500 EnableValidation : true Enabled : true UseSharedProcess : true MaxSessionsPerRemoteNode : 5 MaxDisconnectedSessions : 1000 AssemblyName : Microsoft.PowerShell.Workflow.ServiceCore, Version=3.0.0.0, Culture=neutral, PublicKe yToken=31bf3856ad364e35, processorArchitecture=MSIL lang : ja-JP Permission : BUILTIN\Administrators AccessAllowed, BUILTIN\Remote Management Users AccessAllowed
もう一回Add-Typeを試しましょう。
Add-Type -Assem System.web
メソッド呼び出しです。
[System.Web.Httputility]::UrlEncode("ああり",[System.Text.Encoding]::default)
ぐぬぬ……だめでした…
メソッドを呼び出せません。この言語モードでは、メソッドの呼び出しはコアの型のみでサポートされています。 発生場所 行:1 文字:1 + [System.Web.Httputility]::UrlEncode("ああり",[System.Text.Encoding]::default) + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + CategoryInfo : InvalidOperation: (:) []、RuntimeException + FullyQualifiedErrorId : MethodInvocationNotSupportedInConstrainedLanguage
懲りずに、System.Windows.Formsでやるも
Add-Type -Assem System.Windows.Forms
ここまでは前回と一緒。
[System.Windows.Forms.MessageBox]
で、ダメ
[System.Windows.Forms.MessageBox]::Show("")
メソッドを呼び出せません。この言語モードでは、メソッドの呼び出しはコアの型のみでサポートされています。 発生場所 行:1 文字:1 + [System.Windows.Forms.MessageBox]::Show("") + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + CategoryInfo : InvalidOperation: (:) []、RuntimeException + FullyQualifiedErrorId : MethodInvocationNotSupportedInConstrainedLanguage
制限まとめ
残念この上ないのですが、Windows RTは、.NETとPowerShell両面でがちがちに固められています。 が、PowerShell側は、言語を騙せればイケそうですね (( つまりこれらが原因です。
- 既定のRunSpaceにおける言語($host.Runspace.LanguageMode)が、ConstrainedLanguageになっているため、多くの.NETやいくつかのCmdletに接続制限が掛かっている。
- Microsoftの署名なしのソースを、コンパイル/読み込みできない。 これによりAdd-Typeでの定義、dll読み込みが禁止されています。
あ、VBSやCOMがダメなのは見てのとおりです。
Windows RT上でのPowerShell
PowerShell純正コマンドレット800余りで頑張りましょう。 .ps1は読めましたので。 あと、Get-CIMClassはイケたのでWMIは触れそうです。