2

WMIオブジェクトの2つのメソッドを呼び出すために、昇格して実行する必要があるプログラムを作成しました。管理者グループのユーザーが「昇格モード」で実行すると、魅力のように機能します。しかし、今の問題は、すべての人が実行する必要があり、すべての人が作業するマシンの管理者権限を持っているわけではないということです。そこで、「Domain Admins」グループのユーザーになりすまして、プログラム自体を再起動させることにしました。

そのための私のコードは次のとおりです。

 ProcessStartInfo proc = new ProcessStartInfo();
 proc.WorkingDirectory = Environment.CurrentDirectory;
 proc.FileName = System.Windows.Forms.Application.ExecutablePath; ;
 proc.UserName = "USERNAME";
 SecureString secure = new SecureString();
 foreach (var item in "PASSWORD")
 {
     secure.AppendChar(item);
 }
 proc.Password = secure;
 proc.Domain = "DOMAIN";
 proc.UseShellExecute = false;
 proc.Verb = "runas";
 Process.Start(proc);

UACが有効になっている場合、これには2つの問題があります。まず、プログラムのインストールフォルダーのACLに偽装する必要のあるユーザーを明示的に追加しない場合(ユーザーは、フォルダーとそれに含まれるすべてのファイルへのフルアクセス権を持つAdministratorsグループに既に存在します)、をスローしSystem.ComponentModel.Win32Exception: The directory name is invalidます。ディレクトリパスを再確認しましたが、実際には有効です(ユーザーがACLに明示的に含まれている場合に機能します)。

これで、ユーザーが明示的に追加され、例外がない場合、プログラムはユーザーとして実行されますが、昇格された権限では実行されないため、呼び出しは機能しません。

私は何が間違っているのですか?ご協力いただきありがとうございます。

同様の問題についてすでにいくつかの質問があることは知っていますが、解決策/回答のいずれも私の問題を解決しなかったか、それらが十分に詳細でなく、あまりにも長い間非アクティブでした。

4

1 に答える 1

2

私は同じ問題を抱えています。昇格と資格情報の提供を同時に行うことはできませんでした。'runas'動詞を使用するには、UseShellExecute = trueを設定する必要がありますが、資格情報を提供するには、falseに設定する必要があります。私がやったことは、管理者権限をテストし、それらが存在しない場合は、ローカル管理者権限を持つ別のユーザーとしてアプリケーションを再起動することです。次に、「runas」動詞を使用して、資格情報を提供せずにprocess.startを実行します。この時点で、ユーザーはUACプロンプトを受け取り、[はい]を選択すると、プロセスが昇格して実行されます。私はVBで私のものを書きましたが、考え方は同じです。これが私のコードです。IsUserAdminGroupは次の場所から使用されました。

UAC自己標高


     Try
    'check if user is administrator
    Dim fInAdminGroup As Boolean = Me.IsUserInAdminGroup
    If (Me.IsUserInAdminGroup = False) Then
    'check if process is running under user you want to elevate
        If Not (System.Environment.UserName = "") Then
    'this process restarts the app as the desired admin user
            Dim path As String = Environment.CurrentDirectory
            Dim filename As String = Application.ExecutablePath
    'create secure string password
            Dim passwordPre As String = ""
            Dim passwordChars As Char() = passwordPre.ToCharArray()
            Dim password As New SecureString()
            For Each c As Char In passwordChars
                password.AppendChar(c)
            Next
            Dim procInfo As New System.Diagnostics.Process
            procInfo.StartInfo.FileName = filename
            procInfo.StartInfo.UserName = ""
            procInfo.StartInfo.Domain = ""
            procInfo.StartInfo.Password = password
            procInfo.StartInfo.UseShellExecute = False
    'load user profile was needed for a legacy application I used that failed without the user hive loaded
            'procInfo.StartInfo.LoadUserProfile = True
            procInfo.StartInfo.CreateNoWindow = True
            procInfo.StartInfo.WorkingDirectory = path
            procInfo.Start()
            Application.Exit()
        Else
            MsgBox("Unable to open, call support.", MsgBoxStyle.Critical, "Run Failed")
            Application.Exit()
        End If
    ElseIf (System.Environment.UserName = "") Then
        Me.Visible = False
        Me.Hide()
    'this process starts the desired app elevated
        Dim procInfo As New System.Diagnostics.Process
        procInfo.StartInfo.FileName = "ptpublisher.exe"
        procInfo.StartInfo.Verb = "runas"
        procInfo.StartInfo.UseShellExecute = True
        procInfo.StartInfo.CreateNoWindow = True
        procInfo.StartInfo.WorkingDirectory = "C:\Program Files (x86)\Primera Technology\PTPublisher"
        procInfo.StartInfo.Arguments = ""
        procInfo.Start()
        Application.Exit()
    End If
Catch ex As Exception
    MsgBox(ex.Message, MsgBoxStyle.Critical, "Run Failed")
    Application.Exit()
End Try
于 2013-09-13T15:00:06.393 に答える