diff options
| author | Jason Molenda <jmolenda@apple.com> | 2015-10-22 04:17:26 +0000 |
|---|---|---|
| committer | Jason Molenda <jmolenda@apple.com> | 2015-10-22 04:17:26 +0000 |
| commit | 76a2d615add9ac345cf967e39b00cd365bb286c2 (patch) | |
| tree | dbe6ddcc5067b140437691448c92174e746acbfe /lldb/source/Host/macosx | |
| parent | eb7927ee8f2838e153c3002e94a6af9d18b76d92 (diff) | |
| download | bcm5719-llvm-76a2d615add9ac345cf967e39b00cd365bb286c2.tar.gz bcm5719-llvm-76a2d615add9ac345cf967e39b00cd365bb286c2.zip | |
Move the launch-as-root xpc service from lldb to xcode, to
make it easier to run hand-built lldb roots and retain those
entitlements. This is currently only used by Xcode; command
line lldb doesn't expose the SBLaunchInfo::SetUserID()
launch option.
<rdar://problem/23154486>
llvm-svn: 250981
Diffstat (limited to 'lldb/source/Host/macosx')
8 files changed, 16 insertions, 463 deletions
diff --git a/lldb/source/Host/macosx/Host.mm b/lldb/source/Host/macosx/Host.mm index 0cb8adde8a5..6c3d2617380 100644 --- a/lldb/source/Host/macosx/Host.mm +++ b/lldb/source/Host/macosx/Host.mm @@ -18,7 +18,22 @@ #if !defined(NO_XPC_SERVICES) #define __XPC_PRIVATE_H__ #include <xpc/xpc.h> -#include "launcherXPCService/LauncherXPCService.h" + +#define LaunchUsingXPCRightName "com.apple.dt.Xcode.RootDebuggingXPCService" + +// These XPC messaging keys are used for communication between Host.mm and the XPC service. +#define LauncherXPCServiceAuthKey "auth-key" +#define LauncherXPCServiceArgPrefxKey "arg" +#define LauncherXPCServiceEnvPrefxKey "env" +#define LauncherXPCServiceCPUTypeKey "cpuType" +#define LauncherXPCServicePosixspawnFlagsKey "posixspawnFlags" +#define LauncherXPCServiceStdInPathKeyKey "stdInPath" +#define LauncherXPCServiceStdOutPathKeyKey "stdOutPath" +#define LauncherXPCServiceStdErrPathKeyKey "stdErrPath" +#define LauncherXPCServiceChildPIDKey "childPID" +#define LauncherXPCServiceErrorTypeKey "errorType" +#define LauncherXPCServiceCodeTypeKey "errorCode" + #endif #include "llvm/Support/Host.h" diff --git a/lldb/source/Host/macosx/launcherXPCService/LauncherRootXPCService-Info.plist b/lldb/source/Host/macosx/launcherXPCService/LauncherRootXPCService-Info.plist deleted file mode 100644 index 59b8bfac8cf..00000000000 --- a/lldb/source/Host/macosx/launcherXPCService/LauncherRootXPCService-Info.plist +++ /dev/null @@ -1,46 +0,0 @@ -#if RC_XBS && !RC_BUILDIT -#define AND_APPLE_CODE_SIGNED and ${IS_APPLE_CODE_SIGNED} -#else -#define AND_APPLE_CODE_SIGNED -#endif - -<?xml version="1.0" encoding="UTF-8"?> -<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd"> -<plist version="1.0"> -<dict> - <key>CFBundleDevelopmentRegion</key> - <string>English</string> - <key>CFBundleExecutable</key> - <string>${EXECUTABLE_NAME}</string> - <key>CFBundleIdentifier</key> - <string>${EXECUTABLE_NAME}</string> - <key>CFBundleInfoDictionaryVersion</key> - <string>6.0</string> - <key>CFBundleName</key> - <string>${PRODUCT_NAME}</string> - <key>CFBundlePackageType</key> - <string>XPC!</string> - <key>CFBundleShortVersionString</key> - <string>1.0</string> - <key>CFBundleSignature</key> - <string>????</string> - <key>CFBundleVersion</key> - <string>350.99.0</string> - <key>NSHumanReadableCopyright</key> - <string>Copyright © 2012 Apple Inc. All rights reserved.</string> - <key>XPCService</key> - <dict> - <key>_AllowedClients</key> - <array> - <string> identifier = com.apple.lldb AND_APPLE_CODE_SIGNED</string> - <string> identifier = com.apple.dt.Xcode AND_APPLE_CODE_SIGNED</string> - </array> - <key>_RoleAccount</key> - <string>root</string> - <key>ServiceType</key> - <string>Application</string> - <key>JoinExistingSession</key> - <true/> - </dict> -</dict> -</plist> diff --git a/lldb/source/Host/macosx/launcherXPCService/LauncherRootXPCService.mm b/lldb/source/Host/macosx/launcherXPCService/LauncherRootXPCService.mm deleted file mode 100644 index a39e4d03974..00000000000 --- a/lldb/source/Host/macosx/launcherXPCService/LauncherRootXPCService.mm +++ /dev/null @@ -1,50 +0,0 @@ -#include <AvailabilityMacros.h> - -#if !defined(MAC_OS_X_VERSION_10_7) || MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_7 -#define BUILDING_ON_SNOW_LEOPARD 1 -#endif - -#if !BUILDING_ON_SNOW_LEOPARD -#define __XPC_PRIVATE_H__ -#include <xpc/xpc.h> -#include <Security/Security.h> -#include "LauncherXPCService.h" - -// Returns 0 if successful. -int _validate_authorization(xpc_object_t message) -{ - size_t data_length = 0ul; - const char *data_bytes = (const char *)xpc_dictionary_get_data(message, LauncherXPCServiceAuthKey, &data_length); - - AuthorizationExternalForm extAuth; - if (data_length < sizeof(extAuth.bytes)) - return 1; - - memcpy(extAuth.bytes, data_bytes, sizeof(extAuth.bytes)); - AuthorizationRef authRef; - if (AuthorizationCreateFromExternalForm(&extAuth, &authRef) != errAuthorizationSuccess) - return 2; - - AuthorizationItem item1 = { LaunchUsingXPCRightName, 0, NULL, 0 }; - AuthorizationItem items[] = {item1}; - AuthorizationRights requestedRights = {1, items }; - AuthorizationRights *outAuthorizedRights = NULL; - OSStatus status = AuthorizationCopyRights(authRef, &requestedRights, kAuthorizationEmptyEnvironment, kAuthorizationFlagDefaults, &outAuthorizedRights); - - // Given a set of rights, return the subset that is currently authorized by the AuthorizationRef given; count(subset) > 0 -> success. - bool auth_success = (status == errAuthorizationSuccess && outAuthorizedRights && outAuthorizedRights->count > 0) ? true : false; - if (outAuthorizedRights) AuthorizationFreeItemSet(outAuthorizedRights); - if (!auth_success) - return 3; - - // On Lion, because the rights initially doesn't exist in /etc/authorization, if an admin user logs in and uses lldb within the first 5 minutes, - // it is possible to do AuthorizationCopyRights on LaunchUsingXPCRightName and get the rights back. - // As another security measure, we make sure that the LaunchUsingXPCRightName rights actually exists. - status = AuthorizationRightGet(LaunchUsingXPCRightName, NULL); - if (status == errAuthorizationSuccess) - return 0; - else - return 4; -} - -#endif diff --git a/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService-Info.plist b/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService-Info.plist deleted file mode 100644 index 8ec625b8f61..00000000000 --- a/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService-Info.plist +++ /dev/null @@ -1,44 +0,0 @@ -#if RC_XBS && !RC_BUILDIT -#define AND_APPLE_CODE_SIGNED and ${IS_APPLE_CODE_SIGNED} -#else -#define AND_APPLE_CODE_SIGNED -#endif - -<?xml version="1.0" encoding="UTF-8"?> -<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd"> -<plist version="1.0"> -<dict> - <key>CFBundleDevelopmentRegion</key> - <string>English</string> - <key>CFBundleExecutable</key> - <string>${EXECUTABLE_NAME}</string> - <key>CFBundleIdentifier</key> - <string>${EXECUTABLE_NAME}</string> - <key>CFBundleInfoDictionaryVersion</key> - <string>6.0</string> - <key>CFBundleName</key> - <string>${PRODUCT_NAME}</string> - <key>CFBundlePackageType</key> - <string>XPC!</string> - <key>CFBundleShortVersionString</key> - <string>1.0</string> - <key>CFBundleSignature</key> - <string>????</string> - <key>CFBundleVersion</key> - <string>350.99.0</string> - <key>NSHumanReadableCopyright</key> - <string>Copyright © 2012 Apple Inc. All rights reserved.</string> - <key>XPCService</key> - <dict> - <key>_AllowedClients</key> - <array> - <string> identifier = com.apple.lldb AND_APPLE_CODE_SIGNED</string> - <string> identifier = com.apple.dt.Xcode AND_APPLE_CODE_SIGNED</string> - </array> - <key>ServiceType</key> - <string>Application</string> - <key>JoinExistingSession</key> - <true/> - </dict> -</dict> -</plist> diff --git a/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService.entitlements b/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService.entitlements deleted file mode 100644 index a3088cce3eb..00000000000 --- a/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService.entitlements +++ /dev/null @@ -1,8 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd"> -<plist version="1.0"> -<dict> - <key>com.apple.private.xpc.role-account</key> - <true/> -</dict> -</plist> diff --git a/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService.h b/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService.h deleted file mode 100644 index 2181173bc49..00000000000 --- a/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService.h +++ /dev/null @@ -1,19 +0,0 @@ -#ifndef LLDB_LauncherXPCService_h -#define LLDB_LauncherXPCService_h - -#define LaunchUsingXPCRightName "com.apple.lldb.LaunchUsingXPC" - -// These XPC messaging keys are used for communication between Host.mm and the XPC service. -#define LauncherXPCServiceAuthKey "auth-key" -#define LauncherXPCServiceArgPrefxKey "arg" -#define LauncherXPCServiceEnvPrefxKey "env" -#define LauncherXPCServiceCPUTypeKey "cpuType" -#define LauncherXPCServicePosixspawnFlagsKey "posixspawnFlags" -#define LauncherXPCServiceStdInPathKeyKey "stdInPath" -#define LauncherXPCServiceStdOutPathKeyKey "stdOutPath" -#define LauncherXPCServiceStdErrPathKeyKey "stdErrPath" -#define LauncherXPCServiceChildPIDKey "childPID" -#define LauncherXPCServiceErrorTypeKey "errorType" -#define LauncherXPCServiceCodeTypeKey "errorCode" - -#endif diff --git a/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService.mm b/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService.mm deleted file mode 100644 index 5ec3be0a1c6..00000000000 --- a/lldb/source/Host/macosx/launcherXPCService/LauncherXPCService.mm +++ /dev/null @@ -1,17 +0,0 @@ -#include <AvailabilityMacros.h> - -#if !defined(MAC_OS_X_VERSION_10_7) || MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_7 -#define BUILDING_ON_SNOW_LEOPARD 1 -#endif - -#if !BUILDING_ON_SNOW_LEOPARD -#define __XPC_PRIVATE_H__ -#include <xpc/xpc.h> - -// Returns 0 if successful. This is launching as self. No need for further authorization. -int _validate_authorization(xpc_object_t message) -{ - return 0; -} - -#endif diff --git a/lldb/source/Host/macosx/launcherXPCService/main.mm b/lldb/source/Host/macosx/launcherXPCService/main.mm deleted file mode 100644 index 3dc5e2c3f1a..00000000000 --- a/lldb/source/Host/macosx/launcherXPCService/main.mm +++ /dev/null @@ -1,278 +0,0 @@ -// -// main.m -// Used in both LauncherXPCService and LaunchRootXPCService targets -// -// Copyright (c) 2012 Apple Inc. All rights reserved. -// -#include <AvailabilityMacros.h> - -#if !defined(MAC_OS_X_VERSION_10_7) || MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_7 -#define BUILDING_ON_SNOW_LEOPARD 1 -#endif - -#if !BUILDING_ON_SNOW_LEOPARD -#define __XPC_PRIVATE_H__ -#include <xpc/xpc.h> -#include <spawn.h> -#include <signal.h> -#include <assert.h> -#include <sys/errno.h> -#include "LauncherXPCService.h" - -// Declaration. Returns 0 if successful. -int _validate_authorization(xpc_object_t message); - -// Returns 0 if successful. -int -_setup_posixspawn_attributes_file_actions(xpc_object_t message, posix_spawnattr_t *attr, posix_spawn_file_actions_t *file_actions) -{ - *attr = 0; - - int errorCode = posix_spawnattr_init(attr); - if (errorCode) - return errorCode; - - cpu_type_t cpuType = (cpu_type_t)xpc_dictionary_get_int64(message, LauncherXPCServiceCPUTypeKey); - if (cpuType == -2) - { - cpuType= CPU_TYPE_ANY; - } - size_t realCount; - errorCode = posix_spawnattr_setbinpref_np(attr, 1, &cpuType, &realCount); - if (errorCode) - return errorCode; - - sigset_t no_signals; - sigset_t all_signals; - sigemptyset (&no_signals); - sigfillset (&all_signals); - posix_spawnattr_setsigmask(attr, &no_signals); - posix_spawnattr_setsigdefault(attr, &all_signals); - - short flags = xpc_dictionary_get_int64(message, LauncherXPCServicePosixspawnFlagsKey); - errorCode = posix_spawnattr_setflags(attr, flags); - if (errorCode) - return errorCode; - - // Setup any file actions. - errorCode = posix_spawn_file_actions_init(file_actions); - if (errorCode) - return errorCode; - - const char *path = xpc_dictionary_get_string(message, LauncherXPCServiceStdInPathKeyKey); - if (path) - { - errorCode = posix_spawn_file_actions_addopen(file_actions, STDIN_FILENO, path, O_NOCTTY | O_RDONLY, 0); - } - else - { - errorCode = posix_spawn_file_actions_addclose(file_actions, STDIN_FILENO); - } - if (errorCode) - return errorCode; - - path = xpc_dictionary_get_string(message, LauncherXPCServiceStdOutPathKeyKey); - if (path) - { - errorCode = posix_spawn_file_actions_addopen(file_actions, STDOUT_FILENO, path, O_NOCTTY | O_CREAT | O_WRONLY, 0640); - } - else - { - errorCode = posix_spawn_file_actions_addclose(file_actions, STDOUT_FILENO); - } - if (errorCode) - return errorCode; - - path = xpc_dictionary_get_string(message, LauncherXPCServiceStdErrPathKeyKey); - if (path) - { - errorCode = posix_spawn_file_actions_addopen(file_actions, STDERR_FILENO, path, O_NOCTTY | O_CREAT | O_RDWR, 0640); - } - else - { - errorCode = posix_spawn_file_actions_addclose(file_actions, STDERR_FILENO); - } - - return errorCode; -} - -bool -extract_args(xpc_object_t message, const char *prefix, const char ***argsOut) -{ - char buf[50]; // long enough for 'argXXX' - memset(buf, 0, 50); - sprintf(buf, "%sCount", prefix); - int argsCount = (int)xpc_dictionary_get_int64(message, buf); - if (argsCount == 0) - { - return true; - } - - const char **argsp = NULL; - argsp = (const char **)malloc((argsCount+1) * sizeof(argsp[0])); - if (argsp == NULL) - { - return false; - } - - for (int i=0; i<argsCount; i++) - { - memset(buf, 0, 50); - sprintf(buf, "%s%i", prefix, i); - const char *arg = xpc_dictionary_get_string(message, buf); - argsp[i] = arg; - } - argsp[argsCount] = NULL; - - *argsOut = argsp; - return true; -} - -// Returns 0 if successful. -int -get_args(xpc_object_t message, const char **path, const char ***argsOut, const char ***envOut) -{ - if (!extract_args(message, LauncherXPCServiceArgPrefxKey, argsOut)) - { - return 1; - } - if (path && argsOut && *argsOut) - { - *path = (*argsOut)[0]; - } - - if (!extract_args(message, LauncherXPCServiceEnvPrefxKey, envOut)) - { - return 2; - } - - return 0; -} - -void -_wait_for_child_exit(pid_t childPID) -{ - dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0); - dispatch_source_t source = dispatch_source_create(DISPATCH_SOURCE_TYPE_PROC, childPID, DISPATCH_PROC_EXIT, queue); - - if (source) { - dispatch_source_set_cancel_handler(source, ^{ - dispatch_release(source); - }); - - dispatch_source_set_event_handler(source, ^{ - - // Either finding the process was successful, or the process disappeared before libdispatch got around to hooking up the source. - dispatch_source_cancel(source); - - int status, ret; - do - { - ret = waitpid(childPID, &status, 0); - } while (ret < 0 && errno == EINTR); - - }); - dispatch_resume(source); - } -} - -static void -launcherXPC_peer_event_handler(xpc_connection_t peer, xpc_object_t event) -{ - xpc_type_t type = xpc_get_type(event); - if (type == XPC_TYPE_ERROR) - { - if (event == XPC_ERROR_CONNECTION_INVALID) - { - // The client process on the other end of the connection has either - // crashed or cancelled the connection. After receiving this error, - // the connection is in an invalid state, and you do not need to - // call xpc_connection_cancel(). Just tear down any associated state - // here. - } - else if (event == XPC_ERROR_TERMINATION_IMMINENT) - { - // Handle per-connection termination cleanup. - } - } - else - { - assert(type == XPC_TYPE_DICTIONARY); - // Handle the message. - - pid_t childPID = 0; - posix_spawn_file_actions_t file_actions; - posix_spawnattr_t attributes; - - /* - Types of error. Error code will be specific to each type. - 100 - authorization failure - 101 - posixspawn attributes problem - 102 - get args/env problem - 103 - posixspawn problem - */ - int errorType = 100; - int errorCode = _validate_authorization(event); - if (!errorCode) - { - errorType = 101; - errorCode = _setup_posixspawn_attributes_file_actions(event, &attributes, &file_actions); - if (!errorCode) { - const char *path = NULL; - const char **argvp = NULL; - const char **envp = NULL; - errorType = 102; - errorCode = get_args(event, &path, &argvp, &envp); - if (!errorCode) - { - errorType = 103; - errorCode = posix_spawn(&childPID, path, &file_actions, &attributes, (char * const *)argvp, (char * const *)envp); - - if (errorCode == 0) - { - _wait_for_child_exit(childPID); - } - } - if (argvp) - free(argvp); - if (envp) - free(envp); - } - } - - xpc_object_t reply = xpc_dictionary_create_reply(event); - - xpc_dictionary_set_int64(reply, LauncherXPCServiceChildPIDKey, childPID); - if (!childPID) - { - xpc_dictionary_set_int64(reply, LauncherXPCServiceErrorTypeKey, errorType); - xpc_dictionary_set_int64(reply, LauncherXPCServiceCodeTypeKey, errorCode); - } - - xpc_connection_send_message(peer, reply); - xpc_release(reply); - } -} - -static void -launcherXPC_event_handler(xpc_connection_t peer) -{ - // By defaults, new connections will target the default dispatch - // concurrent queue. - xpc_connection_set_event_handler(peer, ^(xpc_object_t event) { - launcherXPC_peer_event_handler(peer, event); - }); - - // This will tell the connection to begin listening for events. If you - // have some other initialization that must be done asynchronously, then - // you can defer this call until after that initialization is done. - xpc_connection_resume(peer); -} - -int -main(int argc, const char *argv[]) -{ - xpc_main(launcherXPC_event_handler); - return 0; -} -#endif |

