Функция ShowWindow не работает, когда целевое приложение запускается от имени администратора

Я пишу программу, которая показывает / скрывает окно какого-либо целевого приложения. Я проверял это раньше и заметил что-то странное. Если я запускаю целевое приложение от имени администратора (щелкните правой кнопкой мыши -> Свойства, вкладка "Совместимость", "Запустите эту программу от имени администратора"), оно не будет работать.

Для демонстрации я написал простое приложение с графическим интерфейсом под названием "TargetApplication", а затем я написал следующий код, чтобы протестировать показ / скрытие этого приложения:

class Program
{
  static void Main(string[] args)
  {
    IntPtr windowPtr = FindWindow(null, "TargetApplication");
    ShowWindow(windowPtr, 0); // 0 = Hide            
    Console.WriteLine("The window is now hidden. Press Enter to restore");
    Console.ReadLine();
    ShowWindow(windowPtr, 9); // 9 = Restore
    Console.WriteLine("The window is now restored. Press Enter to exit.");            
    Console.ReadLine();
  }

  [DllImport("user32.dll", EntryPoint = "FindWindow", SetLastError = true)]
  static extern IntPtr FindWindow(string lpClassName, string lpWindowName);

  [DllImport("user32.dll")]
  static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);
}

Если я запускаю оконное приложение без прав администратора, оно не работает.

Кто-нибудь может проверить это для меня? Я загрузил.exe для обоих приложений здесь:

TestShowWindow Скачать

Все, что вам нужно сделать, это загрузить их и запустить TestApplication.exe, а затем запустить TestShowWindow.exe. Вы обнаружите, что, изменив TestApplication.exe для запуска от имени администратора, ShowWindow больше не работает.

Конечно, если вы не доверяете загрузке моих материалов, вы всегда можете скомпилировать мой код и протестировать его в любом целевом приложении в Windows, для которого вы можете изменить режим совместимости.

PS Я не уверен, если это имеет значение, но я использую Windows 8 Pro. 64-битный.

2 ответа

Решение

Это по замыслу. Это менее известный близнец UAC, называемый UIPI или изоляция привилегий пользовательского интерфейса. Не повышенная программа не может управлять повышенной. Учитывая возможности UI Automation, это является очевидной контрмерой, чтобы не дать программам использовать возможности расширенного процесса. Нарушение безопасности называется разрушенной атакой.

Обходные пути должны предоставить манифест с uiAccess = true для программы, хранящейся в файлах c:\windows или c:\program и снабженной сертификатом. И для целевой программы вызвать ChangeWindowMessageFilter, чтобы разрешить отправку определенных сообщений. В вашем случае это должно быть WM_SHOWWINDOW.

Если вы не возражаете, окно работает так, как будто вы свернули его на панель задач; Вы можете, как правило, показывать и скрывать окна от процессов с повышенными правами, публикуя WM_SYSCOMMAND с wParam SC_RESTORE или SC_MINIMIZE.

Другие вопросы по тегам