mirror of
https://github.com/etlegacy/Update-Installer.git
synced 2025-02-17 00:41:11 +00:00
Add code to launch applications with elevated priviledges on Mac from the old updater.
This commit is contained in:
parent
44c1937d96
commit
8e47110231
1 changed files with 95 additions and 0 deletions
|
@ -77,6 +77,101 @@ void ProcessUtils::runElevatedLinux(const std::string& executable,
|
|||
void ProcessUtils::runElevatedMac(const std::string& executable,
|
||||
const std::list<std::string>& args)
|
||||
{
|
||||
OSStatus status;
|
||||
AuthorizationRef authorizationRef;
|
||||
|
||||
status = AuthorizationCreate(
|
||||
NULL,
|
||||
kAuthorizationEmptyEnvironment,
|
||||
kAuthorizationFlagDefaults,
|
||||
&authorizationRef);
|
||||
|
||||
AuthorizationItem right = { kAuthorizationRightExecute, 0, NULL, 0 };
|
||||
AuthorizationRights rights = { 1, &right };
|
||||
|
||||
AuthorizationFlags flags = kAuthorizationFlagDefaults |
|
||||
kAuthorizationFlagInteractionAllowed |
|
||||
kAuthorizationFlagPreAuthorize |
|
||||
kAuthorizationFlagExtendRights;
|
||||
|
||||
if (status == errAuthorizationSuccess)
|
||||
{
|
||||
status = AuthorizationCopyRights(authorizationRef, &rights, NULL,
|
||||
flags, NULL);
|
||||
|
||||
if (status == errAuthorizationSuccess)
|
||||
{
|
||||
char** args;
|
||||
args = (char**) malloc(sizeof(char*) * arguments.count() + 1);
|
||||
|
||||
int i;
|
||||
for (i = 0; i < arguments.size(); i++)
|
||||
{
|
||||
args[i] = strdup(arguments[i].c_str());
|
||||
}
|
||||
args[i] = NULL;
|
||||
|
||||
FILE* pipe = NULL;
|
||||
|
||||
char* tool = strdup(executable.c_str());
|
||||
|
||||
status = AuthorizationExecuteWithPrivileges(authorizationRef, tool,
|
||||
kAuthorizationFlagDefaults, args, &pipe);
|
||||
|
||||
if (status == errAuthorizationSuccess)
|
||||
{
|
||||
// AuthorizationExecuteWithPrivileges does not provide a way to get the process ID
|
||||
// of the child process.
|
||||
//
|
||||
// Discussions on Apple development forums suggest two approaches for working around this,
|
||||
//
|
||||
// - Modify the child process to sent its process ID back to the parent via
|
||||
// the pipe passed to AuthorizationExecuteWithPrivileges.
|
||||
//
|
||||
// - Use the generic Unix wait() call.
|
||||
//
|
||||
// This code uses wait(), which is simpler, but suffers from the problem that wait() waits
|
||||
// for any child process, not necessarily the specific process launched
|
||||
// by AuthorizationExecuteWithPrivileges.
|
||||
//
|
||||
// Apple's documentation (see 'Authorization Services Programming Guide') suggests
|
||||
// installing files in an installer as a legitimate use for
|
||||
// AuthorizationExecuteWithPrivileges but in general strongly recommends
|
||||
// not using this call and discusses a number of other alternatives
|
||||
// for performing privileged operations,
|
||||
// which we could consider in future.
|
||||
|
||||
int childStatus;
|
||||
pid_t childPid = wait(&childStatus);
|
||||
|
||||
if (childStatus != 0)
|
||||
{
|
||||
LOG(Error,"elevated process failed with status " + intToStr(childStatus) + " pid "
|
||||
+ intToStr(childPid));
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG(Info,"elevated process succeded with pid " + intToStr(childPid));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG(Error,"failed to launch elevated process " + intToStr(status));
|
||||
}
|
||||
|
||||
// If we want to know more information about what has happened:
|
||||
// http://developer.apple.com/mac/library/documentation/Security/Reference/authorization_ref/Reference/reference.html#//apple_ref/doc/uid/TP30000826-CH4g-CJBEABHG
|
||||
free(tool);
|
||||
for (i = 0; i < arguments.count(); i++)
|
||||
{
|
||||
free(args[i]);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG(Error,"failed to get rights to launch elevated process. status: " + intToStr(status));
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
|
Loading…
Reference in a new issue