Sunday, April 08, 2007

NSIS & Vista

Для того чтобы установить программу в “Program Files” пользователю нужны административные права. Это не новость. А вот новость, появившаяся в Висте – запустить инсталлятор можно только под пользователем уровня доступа администратора машины.

С версии 2.21 в NSIS-е появилась команда RequestExecutionLevel, которая указывает какими правами должен обладать пользователь для запуска NSIS инсталлятора. RequestExecutionLevel может указывать 3 уровня прав: user, admin, highest. Если программа по умолчанию устанавливается в “Program Files”, то должен быть указан уровень admin. Если Команда не используется, то NSIS инсталлятор автоматически определяется Вистой и при запуске требует административных прав, однако после завершения инсталляции выдает сообщение о том что возможно установка программы прошла некорректно.

Итак, если текущий пользователь не имеет административных прав Виста запросит ввести пароль для пользователя, имеющего такие права, и NSIS инсталлятор запустится под администраторским пользователем. В результате чего появляются следующие проблемы:

Все глобальные переменные системы (%UserProfile%, %LocalAppData% и др.) определяются не для фактически залогиненного акаунта, а для администраторского, под которым запущен инсталлятор. Та же ситуация с переменными NSIS скриптов (например $SMPROGRAMS) и доступом к ветке реестра HKEY_CURRENT_USER.

Такая ситуация с переменными выливается в то, что для обычного пользователя через инсталлятор нельзя проставить даже элементарные линки на программу в “Start Programs”, на “Desktop” и в “Launch Menu”. Для того, чтобы пользователь сразу после инсталляции увидел иконку на рабочем столе ставить ее (и все остальные линки) надо для All Users (команда SetShellVarContext all). Это значит, что фактически программу надо ставить не для конкретного пользователя, а для всех существующих пользователей машины сразу.

И, не смотря на то что здесь в FAQNSIS сказано, что для успешного добавления линков в “Start Programs” при инсталляции и для последующего успешного их удаления при анинсталляции надо указать или “RequestExecutionLevel admin” или “SetShellVarContext all”, на самом деле обе операции должны применяться одновременно:

--

OutFile vista.exe
Name Vista

RequestExecutionLevel admin

Section
  SetShellVarContext all
  CreateShortcut "$SMPROGRAMS\Vista Test\hello.lnk" $WINDIR\notepad.exe
  WriteUninstaller $EXEDIR\uninst.exe
SectionEnd

Section uninstall
  SetShellVarContext all
  Delete "$SMPROGRAMS\Vista Test\hello.lnk"
  RMDir "$SMPROGRAMS\Vista Test"
SectionEnd

--

12 comments:

Anonymous said...

фактически программу надо ставить не для конкретного пользователя, а для всех существующих пользователей машины сразу.
Ну и что? Чем это отличается от поведения предыдущих версий Windows?
Там всё было точно так же, просто в Висте добавился механизм полуавтоматического определения нужных привилегий, но и в старых версиях можно было вручную использовать "Run as...". Попробуйте например под XP что-то записать в ProgramFiles под обычным пользователем, ничего не получится, придётся ставить из под админа и дефолтные папки при этом разумеется будут админские, а не пользователя.

Elena Makurochkina said...

2 anonymous:

> Ну и что? Чем это отличается от поведения предыдущих версий Windows?

Основное отличие в том что в Висте инсталлятор в любом случае, не зависимо от того указана команда запуска под администратором или нет, будет запущен под администраторскими правами (или не будет запущен вообще если залогиненный Standard user не введет пароль для администраторского акаунта).

> Попробуйте например под XP что-то записать в ProgramFiles под обычным пользователем, ничего не получится, придётся ставить из под админа

Ранее, если нет какой либо критической надобности ставить приложение в “Program Files”, пользователь-неадминистратор мог изменить директорию инсталляции программы на любую другую и успешно завершить инсталляцию. Теперь же под пользователем-неадминистратором инсталлятор запустить вообще нельзя.

Т.е. теперь в случае, для программ, рассчитанных для обычных пользователей, для того, чтобы быть уверенным что инсталляция пройдет корректно и пользователь увидит у себя на рабочем столе и в “Start Programs” линки на программу надо обязательно ставить программу для всех пользователей машины.

Anonymous said...

Итак, UAC - как много в этом слове для администратора сплелось. По-умолчанию Windows Vista идёт со включенным UAC - User Access Control. Признаюсь, когда я получил ноутбуку с Вситой, то меня также временами удивляли сообщения типа подтвердите то, подтвердите это. Естественно я себя тут-же добавил в группу администраторов, сообщения поменяли вид, но не исчезли совсекм, что очень по-забавляло. Также было странно, что я могу писать в Windows папку из под notepad, но оказывается, запуская FAR, и я не могу этого делать. Я был в некотором шоке, но тоже не пошел читать документацию по Всита. Но мне везет, в феврале я был на ТехноРеди в Сиэттле, где Марк Руссиновочи прочел просто зажигательный доклад на тему безопасности в Vista и того как-же все это устроено и работает. Это было просто потрясение.

Во-первых, ребята потратили ведро времени и такое-же ведро денег, чтобы выяснить основные действия пользователей и вывести их из под админских прав, либо виртуализировать файловую систему, реестр так, чтобы старые проги все работали без админа. При этом, при включенном UAC даже если вы будете логиниться администратором, то в токен вы не получите себе админских групп и прав. Вот так! Именно поэтому вы постоянно будете получать уведомления, даже если входите в группу администраторов. Чтобы не получать уведомления никогда, надо отключить UAC. :)

Простой пример - часы, когда в XP или 2000 тыкаешься на часы под обычным пользователем получаешь себе ответ у тя нет прав, чтобы посмотреть цыферблат и календарик ты понял, да! (Кстати, вы давно такую штучку-то видели? Это я к тому, что под обычным пользователем давно кто работал из ITPRo?) Вообщем-то имнно такое поведение и застваляло большинство пользователей становиться администраторами. К этому привыкли и типа de facto у нас все были админы. Теперь халява кончилась, но обратную совместимость по-возможности надо отсавить - это раз(виртуализация), а также показать простой путь достижения цели - это два(как раз диалог запроса прав).

Теперь далее к виртуализации. Все программы, которые не написаны строго под Vista - будут запускаться по-умолчанию в режиме обратной совместимости, где работает виртуализация, т.е. в таком режиме можно даже писать в ProgramFiles и Windows по-механизму copy-on-write(исключение нельзя работать с бинарниками) под обычным пользователем. Собственное если вы переводите программу в режим Vista(а RequestExecutionLevel - это как раз запрос опр. уровня прав, который появился именно в Vista), то естественно, что под обычным пользователям вам не дадут не только ничего писать в защищенные места ничего вообще, но и собственно запуститься без соотв. RequestExecutionLevel'а. При этом, никто не мешает не запрашивать тех прав, которые не надо... Видимо конкретному NSIS это надо, но зачем это надо вопрос к разработчикам NSIS. Например, msi йки запускаются из под любого пользователя - без доп. диалога(если это опять таки специально не запрашивать по RequestExecutionLevel).

Вот такая ботва. Получается, что не только IT Pro не читают доки по Vista, но и ISV также их читают по-диагонали. От этого и растут проблемы, подобно вашей.

Да, и определить в висте кто же реально запустил Setup.exe стало возможною. UAC использует специальный системный вызов, который делает reparent для процесса, запущенного через диалог повышения привелегий. Т.е. процесс запущенный под администратором знает, что его породил процесс такого-то пользователя, соотв. получить инфу о настройках этого пользователя тоже можно. В psexp красиво выглядит дерево запуска, когда из под обычного пользователя запускаешь с повышенными привелегиями процесс. :) Да в настройках task manager и psexpа есть новые интересные колонки - а именно process Integrity level и Virtualization. В TaskManager принудительно процессу можно включать или выключать виртуализацию(что отражается на его доступе в реестр и на файловую системы).

Ссылки по теме

посмотреть и послушать

Mark Russinovich: From Winternals to Microsoft, On Windows Security, Windows CoreArch.
http://channel9.msdn.com/showpost.aspx?postid=294410 (Must read т.к. сказать. :))

почитать:

0. Help в Vista - там поиск по UAC или User Access Control - чтобы понять что это такое.

1. User Account Control Overview - http://technet.microsoft.com/en-us/windowsvista/aa906021.aspx

2. Understanding and Configuring User Account Control in Windows Vista - сложно, но про всё и в детялях для IT Pro

http://technet2.microsoft.com/WindowsVista/en/library/00d04415-2b2f-422c-b70e-b18ff918c2811033.mspx?mfr=true

Как это можно применять - Марка в Блоге:

Про надоевший диалог
http://blogs.technet.com/markrussinovich/archive/2006/10/01/The-Case-of-the-Notepad-that-Wouldn_2700_t-Run.aspx

Про новое разделение прав, никто не замечал, что например IE работает в спец. режиме и во многие места писать не сможет, хотя вроде бы работает
под правами пользователя. Проявление - это как Lingvo 11-12 по Ctrl+c+C вызывает перевод слов из IE, выдает ошибку и потом вообще не работает, даже закрыть нельзя. :)

http://blogs.technet.com/markrussinovich/archive/2007/02/12/638372.aspx


3. Developer Best Practices and Guidelines for Applications in a Least Privileged Environment http://msdn2.microsoft.com/en-us/library/aa480150.aspx. Соотв для ISV

Читаем MANы - оно рулез... :)))

P.P.S. Попробуйте в requestExecutionLevel в NSIS поставить asInvoker, должно перестать спрашивать права администратора по-поводу и без. :)

Elena Makurochkina said...

lvetal, большое спасибо за подробное введение в UAC.

Но в данном случае вся проблема не в UAC, а в NSIS.
NSIS (Nullsoft Scriptable Install System) - это система для создания инсталляторов под Windows.

1. > При этом, никто не мешает не запрашивать тех прав, которые не надо... Видимо конкретному NSIS это надо, но зачем это надо вопрос к разработчикам NSIS.

Vista автоматически определяет инсталлятор, созданный с помощью NSIS и для запуска требует прав администратора не зависимо указано ли RequestExecutionLevel admin или нет. Т.е. для инсталлятора, собранного на версии NSIS-а 4-х летней давности Vista все равно запросит права администратора, не смотря на то что разработчики в то время даже не подозревали о RequestExecutionLevel. Обычное же приложение, у которого не указан RequestExecutionLeve, в отличие от NSIS инсталлятора, будет Вистой запущено под текущем пользователем, но только если у пользователя нет достаточных прав это рпиложение не сможет ничего писать в защищенные места. Соответственно механизм определения NSIS-го инсталлятора встроен именно в Висту (как и где это встроено не важно).
Если в инсталляторе RequestExecutionLevel не указан, то Виста предполагает что д.б. RequestExecutionLevel admin и действует соответственно, но после инсталляции выдает сообщение, что возможно инсталляция прошла с ошибками (что пользователю не очень то приятно, соответственно теперь RequestExecutionLevel желательно указывать).

2. NSIS обычно используют для создания инсталляторов для продуктов для конечного пользователя. Т.е. собранный на NSIS инсталлятор должен корректно работать не зависимо от OS, прав текущего пользователя и, главное, уровня знаний текущего пользователя. Желательно предполагать, что пользователь не знает о компьютерах вообще ничего!

3. Смысл инсталлятора в том, чтобы подготовить окружение для работы программы. И в первую очередь это относится к записи нужной для работы программы информации в защищенные места. Т.е. в большинстве случаев инсталлятор надо создавать с RequestExecutionLevel admin. Если же приложение простое и не требует дополнительных настроек, то инсталлятор можно создавать с RequestExecutionLevel user, но при этом надо изменить дефолтную дирректорию инсталляции программы с "Program Files" на какую-нибудь другую, т.к. в "Program Files" инсталлятор все равно записать ничего не сможет.

Anonymous said...

Основное отличие в том что в Висте инсталлятор в любом случае, не зависимо от того указана команда запуска под администратором или нет, будет запущен под администраторскими правами
Вот именно это и не соответствует действительности. Сейчас специально создал в InnoSetup файл с "PrivilegesRequired=none" и запустил в Висте под гостем: никаких вопросов не возникло, всё нормально запустилось и отработало (в ProgramFiles разумеется не смогло установиться). Так что проблема тут не в виста, а в NSIS (или вы просто что-то не поняли в настройках, но тут я ничего не могу сказать, так как не пользуюсь NSIS).

Anonymous said...

Ok. собственно о том и речь, что исталятор возможно кривой. Ты может стоит использовать более прямой инсталятор? В исходном посте(даже двух) звучало, что блин опять эта Виста, да как оно. :) Вообщем-то, так оно и происходит, когда документацию разработчики не читают.

Задача Висты с вызовом этого диалога в том, чтобы у пользователя приложение заработало, поэтому он вылазиет, когда запрашиваются какие-либо экстра права. А зачем эти экстра права NSIS(даже 4х летней давности) запрашивает - хбз! :)

Elena Makurochkina said...

2 Anonimus:
> Сейчас специально создал в InnoSetup файл с "PrivilegesRequired=none" и запустил в Висте под гостем: никаких вопросов не возникло

Конечно вопросов не возникло, т.к. есть команда PrivilegesRequired. Можно указать не none, а user – результат д.б. тот же самый. См. пункт 3 предыдущего комментария - зачем вообще нужны сетапы. В общем то если сетапу не надо ничего ставить кроме программы, то ему можно указывать RequestExecutionLevel user (а можно сетап вообще не делать – отдал пользователю exe-к и все :-) ).
Вы попробуйте создать InnoSetup файл без команды PrivilegesRequired. В этом случае Виста не получив команды какие требуются привелегии, но определив что это сетап должна запросить права администратора.

Elena Makurochkina said...

2 lvetal:
собственно о том и речь, что исталятор возможно кривой. Ты может стоит использовать более прямой инсталятор?

Oткрываем вашу же ссылку: http://technet2.microsoft.com/WindowsVista/en/library/00d04415-2b2f-422c-b70e-b18ff918c2811033.mspx?mfr=true
И внимательно читаем раздел Installer Detection Technology. В том числе обращаем внимание на «Windows Vista heuristically detects installation programs and requests administrator credentials or approval from the administrator user in order to run with access privileges.» , а так же the following attributes are checked to determine whether it is an installer: […] Targeted sequences of bytes within the executable
NSIS – вполне хороший инсталлятор. И он определяется Вистой автоматически!

> Задача Висты с вызовом этого диалога в том, чтобы у пользователя приложение заработало, поэтому он вылазиет, когда запрашиваются какие-либо экстра права. А зачем эти экстра права NSIS(даже 4х летней давности) запрашивает - хбз! :)

И еще раз. Когда у инсталлятора не указан уровень требующихся привилегий Виста сама считает что инсталлятор должен быть запущен под администратором.
Т.е. это не NSIS 4х летней давности запрашивает права, а Виста определив что запускается инсталятор (по сигнатуре) и не найдя команды указывающей какие привилегии требуются для выполнения считает что привилегии должны быть административные.

Anonymous said...

Прошу заметить, не для всех инсталяторов и даже пакетов вызывается этот диалог повышения привелегий. Для тех которых вызывать не надо - не вызывается, а дальше ну виста умная - это да. стремиться сделать так, чтобы всё работало _у пользователя_. Т.е. заранее продумать тему, что если уж девелоперы не подумали каких прав надо, то как обычно считают, что все под админами сидят(и это слишком во многих случахя правда, таким вот образом девелоперов будут по-сути воспитывать писать нормальный сфот)и именно от этого пытаеться вызвать этот диалог by default, т.к. привелегии для инсталятора нужны. К тому-же, Вы же самаи пишете парой постов ранее, что задача инсталятора писать в том-числе и в админ-онли места.

Как я и заметил выше девелоперы привыкли, что все-все-все вопросы обратной совместимости и даже безопасности будут решать в Майрософт и только там. Ну вот ситуация маленько поменялась - предлагается совместно писать безопасный и добртный софт. Поэтому привычку не читать документацию и запрашивать права как заблагорассудиться придётся оставить.

То что вы доки теперь читаете - это очень хорошо, просто прекрасно - вы уже на правильном пути. Кроме этих док есть еще и другие доки, более узко-направленные. :) Вообщем-то и даже в основных доках написано какие методы для работы инсталятора естьи как закурчиваеть инсталлер так, чтобы вопросов глупых не задавалось. Это возможно. Правда-правда! Даже тулы есть на download.microsoft.com бесплатные. :)

В общеизветсной доке про то как задавать вопросы была хорошая мысль, которая масштабируется в принципе. Таки прищли к тому, что найдя ошибку в ядре линукс, возможно стоит почитать доки, FAQ, списки рассылки и проблема будет решена? :))) Или вы сейчас начнете убеждать, что да как они могли, да это баги!!! Да это мега дыры в безопасности!!! "...фактически программу надо ставить для всех..."

P.S. Таки теперь инсталлер нормальный получилось сделать для VISTA с помощью вашего любимого nsis? :) Если получилось - значит все ок, если нет - пешите будем думать как помочь.

P.P.S. Из той-же доки, что вы цытировали, когда у инсталятора не указывается уровень привелегий, то происходит
Note:
The User Account Control: Detect application installations and prompt for elevation setting must be enabled for installer detection to detect installation programs. This setting is enabled by default and can be configured with the Security Policy Manager snap-in (secpol.msc) or with Group Policy (gpedit.msc).

Т.е. и отключить такое поведение в Vista можно. Не прошито это железобетонно типа как "бага". MANы - рулез форева, тем более столько стараний в TechNet и MSDN вкладывается. Ух. :)

Elena Makurochkina said...

lvetal , у меня такое ощущение, что вы целенаправленно «пытаетесь не понять» о чем я пишу.

> Т.е. заранее продумать тему, что если уж девелоперы не подумали каких прав надо, то как обычно считают, что все под админами сидят

Надо заметить, что далеко не все фирмы с выходом Висты кинулись выпускать новые версии. Плюс пользователи часто используют приложения, которые давно не поддерживаются разработчиками, соответственно инсталляторы у них "волосатой" давности, разработчики которых тогда, много лет назад, не могли предположить, что будут подобные нововведения в Висте.

> а дальше ну виста умная - это да. стремиться сделать так, чтобы всё работало _у пользователя_.

Напоминаю, пост был для разработчиков, работающих с NSIS. И о том, как можно нормально настроить NSIS для работы под Вистой в связи с ее нововведениями.

> Даже тулы есть на download.microsoft.com бесплатные.

Там очень много всего есть. У вас есть ссылки на конкретные системы для создания инсталляторов (хотя бы их названия)? Ссылка на download.microsoft.com аналогична фразе «поищите в интернете».

Вы, кстати, представляете что значить сменить инсталлятор для крупного продукта или для линейки продуктов? Это много часов времени на изучение возможностей новой инсталляционной системы для того чтобы понять устраивает она или нет, потом много часов для написания нового инсталлятора на этой новой системе и потом очень-очень много часов тестирования, т.к. все это должно корректно работать подпользователями с разными правами и не только в Висте, но и с OS предыдущих версий (и все это без разделения на разные сетап-фалы).

> То что вы доки теперь читаете - это очень хорошо, просто прекрасно - вы уже на правильном пути.

Я если честно, не поняла такого агрессивного настроя... Я что, была в какой то ж*пе и теперь на правильном пути выбирания из нее?

> Как я и заметил выше девелоперы привыкли, что все-все-все вопросы обратной совместимости и даже безопасности будут решать в Майрософт и только там.

И за что же Вы так разработчиков не уважаете?

А обеспечение обратной совместимости это обязанность строителя платформы. Кстати сам MS и не протестует. Вы же почему-то считаете, что это добрая воля MS. Или, по вашему мнению, все программы, написанные для более ранних версий должны резко перестать работать? Или должны перестать работать только инсталляторы, написанные для ранних версий?

PS: По поводу является ли повышенная умность Висты дырой или нет - это вопрос, причем после прочтения любых мануалов.
Когда разработчик готовит свой продукт, он старается сделать его наиболее удобным в использовании для пользователя (в том числе это относится и к инсталляторам).
Но когда Вы на своей машине пускаете инсталлятор, у которого не указаны права, Вы не знаете не указаны ли они по недосмотру или по злому умыслу. Т.е. злоумышленник может просто не указать уровень прав и получить админский доступ к машине по дефолту.

PPS: Большинство разработчиков, не смотря на ваше мнение, мануалы читают.
Информации в сети очень и очень много и чтобы найти полезные крупицы надо потратить много времени.
К сожалению, часто бывает, что даже если где-то и есть полезная информация она просто не попадается при поиске.

Elena Makurochkina said...

2 lvetal:

PPPS:

> Tаки теперь инсталлер нормальный получилось сделать для VISTA с помощью вашего любимого nsis? :) Если получилось - значит все ок, если нет - пешите будем думать как помочь.

Молодой человек, научитесь сначала внимательно слушать (в данном случае читать) прежде чем что либо писать. Если бы вы сам пост прочли до конца (даже без комментариев), вы бы узнали о том что надо написать в NSIS скрипте и как надо поменять логику инсталляции, чтобы инсталляция прошла успешно.

NSIS - удобная и очень легкая система. Популярная у тысяч разработчиков. Если Вы услышали это название в первый раз задумайтесь, может стоит не язвить (фразами типа "с помощью вашего любимого nsis?") а предположить что Ваши знания не идеальны и почитать повнимательнее о том, о чем не знаете.

Дальнейшие посты в подобном вашему тоне буду удалять. И поправьте, пожалуйста, свой профайл на ITBlogs (я конечно могу ошибаться, но по моему это Ваш: lvetal), а то "машины, сноуборды, лень и ничего не деланье" в качестве интересов не очень подходят человеку, пытающемуся наставлять окружающих.

Anonymous said...

Елена, говорят, что в интернете тон не понятен. Прошу извинить, если вдруг.

Для написания любых инсталяторов(а особенно деинсталяторов), необходимо оч. хорошее знание платформы и её поведения. Поэтому, и нужно почитать не только доки от NSIS, но и от платформы. Потому что на мой взглядт в NSIS не оч. верно реализовали абстракцию запроса прав, возможно в будущем её приведут в более соотв. вид, чтобы не смущать разработчиков. Что такое NSIS я знаю довольно давно - это действительно довольно простой и удобный инсталятор, но у него есть ряд недостатков, как и у многих других программ "хакерского" вида, а именно не четкое следование документации к платформе.

Что касается старых инсталяторов, то попробую объяснить еще раз запрос для них связан с тем, чтобы в итоге пользователь получил рабочую программу. Связано это со старой парадигмой, что все де работают под админами. Но! данное поведение by default можно отключить на системе. Вот так. Т.к. поста было два, то я отвечал в одном из них, чтобы не разносить дискуссию. Поэтому часть объяснений про UAC были для ваших вопросов, которые вы подняли в следующем посте, связанных с возможностью запускать инсталятор и кучей окон запроса прав.

В текущей жизни продвинутый администратор и часто сталкиваюсь с работами разработчиков, которые делают вещи "по-недосмотру", которые потом поддерживать - это оч. не легкое дело. Также бывает, что инсталяторы приходиться перепаковывать и переделывать, чтобы использовать в корп. среде. Опыт разработки позволяет разобраться в том, что же "не-досмотрели", и вот это "что-же недосмотрели" во многом связано с тем, что первоситочники и HOW TO народ читать забывает, не успевает, тяжело найти и т.п.

интересы у меня действительно машины, сноуборды, лень и ничего неделанье... :) Лень - оно же вестимо двигатель прогресса. :)

Привет.