Index: sandbox/win/src/broker_services.cc |
diff --git a/sandbox/win/src/broker_services.cc b/sandbox/win/src/broker_services.cc |
index 54d87c44750e6d4e3b8b7474c90dfe807be036dc..b6ae41f679f0aeb4d5fdc9d75bcb848567f35a45 100644 |
--- a/sandbox/win/src/broker_services.cc |
+++ b/sandbox/win/src/broker_services.cc |
@@ -4,6 +4,8 @@ |
#include "sandbox/win/src/broker_services.h" |
+#include <AclAPI.h> |
+ |
#include "base/logging.h" |
#include "base/memory/scoped_ptr.h" |
#include "base/threading/platform_thread.h" |
@@ -153,6 +155,13 @@ BrokerServicesBase::~BrokerServicesBase() { |
// If job_port_ isn't NULL, assumes that the lock has been initialized. |
if (job_port_) |
::DeleteCriticalSection(&lock_); |
+ |
+ // Close any token in the cache. |
+ for (TokenCacheMap::iterator it = token_cache_.begin(); |
+ it != token_cache_.end(); ++it) { |
+ ::CloseHandle(it->second.first); |
+ ::CloseHandle(it->second.second); |
+ } |
} |
TargetPolicy* BrokerServicesBase::CreatePolicy() { |
@@ -299,14 +308,44 @@ ResultCode BrokerServicesBase::SpawnTarget(const wchar_t* exe_path, |
// with the soon to be created target process. |
HANDLE initial_token_temp; |
HANDLE lockdown_token_temp; |
- ResultCode result = policy_base->MakeTokens(&initial_token_temp, |
- &lockdown_token_temp); |
- if (SBOX_ALL_OK != result) |
- return result; |
+ ResultCode result = SBOX_ALL_OK; |
+ |
+ // Make sure our token values aren't too large to pack into token_key. |
+ static_assert(USER_LAST < 8, "TokenLevel too large"); |
+ static_assert(INTEGRITY_LEVEL_LAST < 8, "IntegrityLevel too large"); |
- base::win::ScopedHandle initial_token(initial_token_temp); |
- base::win::ScopedHandle lockdown_token(lockdown_token_temp); |
+ // Pack the various token values into a key we can use foir indexing. |
+ uint32_t token_key = (policy_base->GetInitialTokenLevel() * 8) + |
+ (policy_base->GetLockdownTokenLevel() * 8 * 8) + |
+ (policy_base->GetIntegrityLevel() * 8 * 8 * 8); |
cpu_(ooo_6.6-7.5)
2014/06/04 00:29:27
hmmm .. this looks ugly. lets talk about this craz
jschuh
2014/06/04 04:00:58
Done.
|
+ |
+ TokenCacheMap::iterator it = token_cache_.find(token_key); |
+ if (it != token_cache_.end()) { |
+ initial_token_temp = it->second.first; |
+ lockdown_token_temp = it->second.second; |
+ } else { |
+ result = policy_base->MakeTokens(&initial_token_temp, |
+ &lockdown_token_temp); |
+ if (SBOX_ALL_OK != result) |
+ return result; |
+ token_cache_[token_key] = |
+ std::pair<HANDLE, HANDLE>(initial_token_temp, lockdown_token_temp); |
+ } |
+ |
+ if (!::DuplicateToken(initial_token_temp, SecurityImpersonation, |
+ &initial_token_temp)) { |
+ return SBOX_ERROR_GENERIC; |
+ } |
+ |
+ if (!::DuplicateTokenEx(lockdown_token_temp, TOKEN_ALL_ACCESS, 0, |
+ SecurityIdentification, TokenPrimary, |
+ &lockdown_token_temp)) { |
+ return SBOX_ERROR_GENERIC; |
+ } |
+ base::win::ScopedHandle initial_token(initial_token_temp); |
+ base::win::ScopedHandle lockdown_token(lockdown_token_temp); |
+ |
HANDLE job_temp; |
result = policy_base->MakeJobObject(&job_temp); |
if (SBOX_ALL_OK != result) |