Как проверить, запускается ли приложение из \program files\

Есть ли надежный способ проверить, запущено ли приложение из-под файлов программы?

Если пользователь устанавливает приложение для программирования файлов на локальном компьютере, нам нужно поместить записываемые файлы в другое место, чтобы избежать виртуализации в Vista и Win7. Однако при установке на сетевой диск мы хотим сохранить эти файлы вместе с установкой для общего доступа пользователей.

Сегодня мы делаем сравнение строк между путем запуска и CSIDL_PROGRAM_FILES, но что-то говорит мне, что это очень ненадежный метод.

Любое умное решение там? Есть ли IsRunningFromProtectedFolder() -api, о котором я не знаю? Есть ли какие-либо другие папки, вызывающие те же проблемы, что и программные файлы?

3 ответа

Решение

Это не очень хорошая идея, поскольку пользователь может установить его там, где он хочет, и тогда проверка может завершиться неудачей. Вместо этого установите флажок, когда пользователь устанавливает приложение, решая, установлено ли оно локально или на сервере.

Мы разрешаем нашим пользователям устанавливать в любом месте...

Если пользователь выбрал значение по умолчанию и установлен в Program Files, мы предполагаем, что нам нужно писать в Documents and Settings/Users. В противном случае мы записываем наши данные в папку в каталоге, в котором находится программное обеспечение. Это, конечно, может по-прежнему вызывать проблемы, и установка действительно позволяет людям выбирать другое расположение данных, если они предпочитают не использовать значение по умолчанию.

Кроме того, это простое изменение ini-файла и копия для перемещения данных.

При запуске мы определяем, находимся ли мы в каталоге Program Files, сравнивая значение, которое мы получаем из SHGetFolderPath(CSIDL_PROGRAM_FILES), с началом пути, в котором находится исполняемый файл.

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

Это исходит из предположения, что процессы с повышенными правами всегда используют оригинальные копии, а не виртуализированные (CMIIW). Также я предполагаю, что ваша установка была выполнена с повышенными правами.

Идея состоит в том, чтобы создать "общий" процесс (без повышенных прав, унаследованный), который должен запустить ваш основной установщик. Этот процесс создаст имя файла в выбранной пользователем папке с именем и содержимым, которые знают обе ваши программы (например, test73819704.bin). Если папка виртуализирована, этот файл должен появиться в пользовательском VirtualStore и НЕ ДОЛЖЕН в оригинальном (с точки зрения и привилегий установщика).

Таким образом, для выбранного C:\Program_Files_But_Not_Ne обязательно и Process-1 (повышенный)

  • Процесс-1 гарантирует, что нет файла C:\Program_Files_But_Not_Necessually\test73819704.bin
  • Запускает Процесс-2 без подъема
  • Процесс-2 создает C:\Program_Files_But_Not_Necessually\test73819704.bin и проверяет, действительно ли он существует. Если он существует, он вернется с хорошим кодом возврата, в противном случае - с ошибкой.
  • Процесс-1 ожидает Процесс-2 и анализирует результат. Если это хорошо, проверяет C:\Program_Files_But_Not_Necessually\test73819704.bin, если он существует, перейдите к "Бинго! Виртуализация не произошла", если не существует, "Плохо, давайте найдем другое место хранения". Если код из Process-2 является "неудачным", покажите пользователю сообщение об ошибке.

К сожалению, я не смог проверить это прямо сейчас, но я думаю, что это должно сработать, и в этом есть логика, с Process-2 вы просто эмулируете поведение своей основной программы)

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