// The global is used to extract the principal. already_AddRefed<InternalRequest> InternalRequest::GetRequestConstructorCopy( nsIGlobalObject* aGlobal, ErrorResult& aRv) const { MOZ_RELEASE_ASSERT(!mURLList.IsEmpty(), "Internal Request's urlList should not be empty when " "copied from constructor."); RefPtr<InternalRequest> copy = new InternalRequest(mURLList.LastElement(), mFragment); copy->SetMethod(mMethod); copy->mHeaders = new InternalHeaders(*mHeaders); copy->SetUnsafeRequest(); copy->mBodyStream = mBodyStream; copy->mBodyLength = mBodyLength; // The "client" is not stored in our implementation. Fetch API users should // use the appropriate window/document/principal and other Gecko security // mechanisms as appropriate. copy->mSameOriginDataURL = true; copy->mPreserveContentCodings = true; copy->mReferrer = mReferrer; copy->mReferrerPolicy = mReferrerPolicy; copy->mEnvironmentReferrerPolicy = mEnvironmentReferrerPolicy; copy->mIntegrity = mIntegrity; copy->mMozErrors = mMozErrors; copy->mContentPolicyType = mContentPolicyTypeOverridden ? mContentPolicyType : nsIContentPolicy::TYPE_FETCH; copy->mMode = mMode; copy->mCredentialsMode = mCredentialsMode; copy->mCacheMode = mCacheMode; copy->mRedirectMode = mRedirectMode; copy->mCreatedByFetchEvent = mCreatedByFetchEvent; copy->mContentPolicyTypeOverridden = mContentPolicyTypeOverridden; copy->mPreferredAlternativeDataType = mPreferredAlternativeDataType; return copy.forget(); }
static void TestScanUnsignedMax() { Input<uintmax_t> u; PoisonInput(u); sscanf("14220563454333534", "%" SCNoMAX, &u.i); MOZ_RELEASE_ASSERT(u.i == UINTMAX_C(432157943248732)); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("432157943248732", "%" SCNuMAX, &u.i); MOZ_RELEASE_ASSERT(u.i == UINTMAX_C(432157943248732)); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("4c337ca791", "%" SCNxMAX, &u.i); MOZ_RELEASE_ASSERT(u.i == UINTMAX_C(327281321873)); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); }
static void TestScanUnsigned64() { Input<uint64_t> u; PoisonInput(u); sscanf("17421742173", "%" SCNo64, &u.i); MOZ_RELEASE_ASSERT(u.i == UINT64_C(017421742173)); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("421786713579", "%" SCNu64, &u.i); MOZ_RELEASE_ASSERT(u.i == UINT64_C(421786713579)); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("DEADBEEF7457E", "%" SCNx64, &u.i); MOZ_RELEASE_ASSERT(u.i == UINT64_C(0xDEADBEEF7457E)); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); }
static void TestScanUnsigned32() { Input<uint32_t> u; PoisonInput(u); sscanf("17421742", "%" SCNo32, &u.i); MOZ_RELEASE_ASSERT(u.i == 017421742); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("4217867", "%" SCNu32, &u.i); MOZ_RELEASE_ASSERT(u.i == 4217867); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("2ABCBEEF", "%" SCNx32, &u.i); MOZ_RELEASE_ASSERT(u.i == 0x2ABCBEEF); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); }
static void TestScanUnsigned16() { Input<uint16_t> u; PoisonInput(u); sscanf("1742", "%" SCNo16, &u.i); MOZ_RELEASE_ASSERT(u.i == 01742); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("4217", "%" SCNu16, &u.i); MOZ_RELEASE_ASSERT(u.i == 4217); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("2ABC", "%" SCNx16, &u.i); MOZ_RELEASE_ASSERT(u.i == 0x2ABC); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); }
static void TestScanUnsignedPtr() { Input<uintptr_t> u; PoisonInput(u); sscanf("57060516", "%" SCNoPTR, &u.i); MOZ_RELEASE_ASSERT(u.i == uintptr_t(reinterpret_cast<void*>(12345678))); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("87654321", "%" SCNuPTR, &u.i); MOZ_RELEASE_ASSERT(u.i == uintptr_t(reinterpret_cast<void*>(87654321))); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("4c3a791", "%" SCNxPTR, &u.i); MOZ_RELEASE_ASSERT(u.i == uintptr_t(reinterpret_cast<void*>(0x4c3a791))); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); }
static void TestScanUnsigned8() { #if SHOULD_TEST_8BIT_FORMAT_MACROS Input<uint8_t> u; PoisonInput(u); sscanf("17", "%" SCNo8, &u.i); MOZ_RELEASE_ASSERT(u.i == 017); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("42", "%" SCNu8, &u.i); MOZ_RELEASE_ASSERT(u.i == 42); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); PoisonInput(u); sscanf("2A", "%" SCNx8, &u.i); MOZ_RELEASE_ASSERT(u.i == 0x2A); MOZ_RELEASE_ASSERT(ExtraBitsUntouched(u)); #endif }
bool GLLibraryEGL::EnsureInitialized(bool forceAccel, nsACString* const out_failureId) { if (mInitialized) { return true; } mozilla::ScopedGfxFeatureReporter reporter("EGL"); #ifdef MOZ_B2G if (!sCurrentContext.init()) MOZ_CRASH("GFX: Tls init failed"); #endif #ifdef XP_WIN if (!mEGLLibrary) { // On Windows, the GLESv2, EGL and DXSDK libraries are shipped with libxul and // we should look for them there. We have to load the libs in this // order, because libEGL.dll depends on libGLESv2.dll which depends on the DXSDK // libraries. This matters especially for WebRT apps which are in a different directory. // See bug 760323 and bug 749459 // Also note that we intentionally leak the libs we load. do { // Windows 8.1 has d3dcompiler_47.dll in the system directory. // Try it first. Note that _46 will never be in the system // directory and we ship with at least _43. So there is no point // trying _46 and _43 in the system directory. if (LoadLibrarySystem32(L"d3dcompiler_47.dll")) break; #ifdef MOZ_D3DCOMPILER_VISTA_DLL if (LoadLibraryForEGLOnWindows(NS_LITERAL_STRING(NS_STRINGIFY(MOZ_D3DCOMPILER_VISTA_DLL)))) break; #endif #ifdef MOZ_D3DCOMPILER_XP_DLL if (LoadLibraryForEGLOnWindows(NS_LITERAL_STRING(NS_STRINGIFY(MOZ_D3DCOMPILER_XP_DLL)))) break; #endif MOZ_ASSERT(false, "d3dcompiler DLL loading failed."); } while (false); LoadLibraryForEGLOnWindows(NS_LITERAL_STRING("libGLESv2.dll")); mEGLLibrary = LoadLibraryForEGLOnWindows(NS_LITERAL_STRING("libEGL.dll")); if (!mEGLLibrary) return false; } #else // !Windows // On non-Windows (Android) we use system copies of libEGL. We look for // the APITrace lib, libEGL.so, and libEGL.so.1 in that order. #if defined(ANDROID) if (!mEGLLibrary) mEGLLibrary = LoadApitraceLibrary(); #endif if (!mEGLLibrary) { printf_stderr("Attempting load of libEGL.so\n"); mEGLLibrary = PR_LoadLibrary("libEGL.so"); } #if defined(XP_UNIX) if (!mEGLLibrary) { mEGLLibrary = PR_LoadLibrary("libEGL.so.1"); } #endif if (!mEGLLibrary) { NS_WARNING("Couldn't load EGL LIB."); return false; } #endif // !Windows #define SYMBOL(name) \ { (PRFuncPtr*) &mSymbols.f##name, { "egl" #name, nullptr } } GLLibraryLoader::SymLoadStruct earlySymbols[] = { SYMBOL(GetDisplay), SYMBOL(Terminate), SYMBOL(GetCurrentSurface), SYMBOL(GetCurrentContext), SYMBOL(MakeCurrent), SYMBOL(DestroyContext), SYMBOL(CreateContext), SYMBOL(DestroySurface), SYMBOL(CreateWindowSurface), SYMBOL(CreatePbufferSurface), SYMBOL(CreatePixmapSurface), SYMBOL(BindAPI), SYMBOL(Initialize), SYMBOL(ChooseConfig), SYMBOL(GetError), SYMBOL(GetConfigs), SYMBOL(GetConfigAttrib), SYMBOL(WaitNative), SYMBOL(GetProcAddress), SYMBOL(SwapBuffers), SYMBOL(CopyBuffers), SYMBOL(QueryString), SYMBOL(QueryContext), SYMBOL(BindTexImage), SYMBOL(ReleaseTexImage), SYMBOL(QuerySurface), { nullptr, { nullptr } } }; if (!GLLibraryLoader::LoadSymbols(mEGLLibrary, &earlySymbols[0])) { NS_WARNING("Couldn't find required entry points in EGL library (early init)"); return false; } GLLibraryLoader::SymLoadStruct optionalSymbols[] = { // On Android 4.3 and up, certain features like ANDROID_native_fence_sync // can only be queried by using a special eglQueryString. { (PRFuncPtr*) &mSymbols.fQueryStringImplementationANDROID, { "_Z35eglQueryStringImplementationANDROIDPvi", nullptr } }, { nullptr, { nullptr } } }; // Do not warn about the failure to load this - see bug 1092191 Unused << GLLibraryLoader::LoadSymbols(mEGLLibrary, &optionalSymbols[0], nullptr, nullptr, false); #if defined(MOZ_WIDGET_GONK) && ANDROID_VERSION >= 18 MOZ_RELEASE_ASSERT(mSymbols.fQueryStringImplementationANDROID, "GFX: Couldn't find eglQueryStringImplementationANDROID"); #endif InitClientExtensions(); const auto lookupFunction = (GLLibraryLoader::PlatformLookupFunction)mSymbols.fGetProcAddress; // Client exts are ready. (But not display exts!) if (IsExtensionSupported(ANGLE_platform_angle_d3d)) { GLLibraryLoader::SymLoadStruct d3dSymbols[] = { { (PRFuncPtr*)&mSymbols.fGetPlatformDisplayEXT, { "eglGetPlatformDisplayEXT", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &d3dSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports ANGLE_platform_angle_d3d without exposing its functions!"); MarkExtensionUnsupported(ANGLE_platform_angle_d3d); mSymbols.fGetPlatformDisplayEXT = nullptr; } } // Check the ANGLE support the system has nsCOMPtr<nsIGfxInfo> gfxInfo = do_GetService("@mozilla.org/gfx/info;1"); mIsANGLE = IsExtensionSupported(ANGLE_platform_angle); EGLDisplay chosenDisplay = nullptr; if (IsExtensionSupported(ANGLE_platform_angle_d3d)) { bool accelAngleSupport = IsAccelAngleSupported(gfxInfo, out_failureId); bool shouldTryAccel = forceAccel || accelAngleSupport; bool shouldTryWARP = !forceAccel; // Only if ANGLE not supported or fails // If WARP preferred, will override ANGLE support if (gfxPrefs::WebGLANGLEForceWARP()) { shouldTryWARP = true; shouldTryAccel = false; } // Hardware accelerated ANGLE path (supported or force accel) if (shouldTryAccel) { chosenDisplay = GetAndInitDisplayForAccelANGLE(*this); } // Fallback to a WARP display if ANGLE fails, or if WARP is forced if (!chosenDisplay && shouldTryWARP) { chosenDisplay = GetAndInitWARPDisplay(*this, EGL_DEFAULT_DISPLAY); if (!chosenDisplay) { if (out_failureId->IsEmpty()) { *out_failureId = NS_LITERAL_CSTRING("FEATURE_FAILURE_WARP_FALLBACK"); } NS_ERROR("Fallback WARP context failed to initialize."); return false; } mIsWARP = true; } } else { chosenDisplay = GetAndInitDisplay(*this, EGL_DEFAULT_DISPLAY); } if (!chosenDisplay) { if (out_failureId->IsEmpty()) { *out_failureId = NS_LITERAL_CSTRING("FEATURE_FAILURE_NO_DISPLAY"); } NS_WARNING("Failed to initialize a display."); return false; } mEGLDisplay = chosenDisplay; InitDisplayExtensions(); //////////////////////////////////// // Alright, load display exts. if (IsExtensionSupported(KHR_lock_surface)) { GLLibraryLoader::SymLoadStruct lockSymbols[] = { { (PRFuncPtr*) &mSymbols.fLockSurface, { "eglLockSurfaceKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fUnlockSurface, { "eglUnlockSurfaceKHR", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &lockSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports KHR_lock_surface without exposing its functions!"); MarkExtensionUnsupported(KHR_lock_surface); mSymbols.fLockSurface = nullptr; mSymbols.fUnlockSurface = nullptr; } } if (IsExtensionSupported(ANGLE_surface_d3d_texture_2d_share_handle)) { GLLibraryLoader::SymLoadStruct d3dSymbols[] = { { (PRFuncPtr*) &mSymbols.fQuerySurfacePointerANGLE, { "eglQuerySurfacePointerANGLE", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &d3dSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports ANGLE_surface_d3d_texture_2d_share_handle without exposing its functions!"); MarkExtensionUnsupported(ANGLE_surface_d3d_texture_2d_share_handle); mSymbols.fQuerySurfacePointerANGLE = nullptr; } } if (IsExtensionSupported(KHR_fence_sync)) { GLLibraryLoader::SymLoadStruct syncSymbols[] = { { (PRFuncPtr*) &mSymbols.fCreateSync, { "eglCreateSyncKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fDestroySync, { "eglDestroySyncKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fClientWaitSync, { "eglClientWaitSyncKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fGetSyncAttrib, { "eglGetSyncAttribKHR", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &syncSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports KHR_fence_sync without exposing its functions!"); MarkExtensionUnsupported(KHR_fence_sync); mSymbols.fCreateSync = nullptr; mSymbols.fDestroySync = nullptr; mSymbols.fClientWaitSync = nullptr; mSymbols.fGetSyncAttrib = nullptr; } } if (IsExtensionSupported(KHR_image) || IsExtensionSupported(KHR_image_base)) { GLLibraryLoader::SymLoadStruct imageSymbols[] = { { (PRFuncPtr*) &mSymbols.fCreateImage, { "eglCreateImageKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fDestroyImage, { "eglDestroyImageKHR", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &imageSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports KHR_image(_base) without exposing its functions!"); MarkExtensionUnsupported(KHR_image); MarkExtensionUnsupported(KHR_image_base); MarkExtensionUnsupported(KHR_image_pixmap); mSymbols.fCreateImage = nullptr; mSymbols.fDestroyImage = nullptr; } } else { MarkExtensionUnsupported(KHR_image_pixmap); } if (IsExtensionSupported(ANDROID_native_fence_sync)) { GLLibraryLoader::SymLoadStruct nativeFenceSymbols[] = { { (PRFuncPtr*) &mSymbols.fDupNativeFenceFDANDROID, { "eglDupNativeFenceFDANDROID", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &nativeFenceSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports ANDROID_native_fence_sync without exposing its functions!"); MarkExtensionUnsupported(ANDROID_native_fence_sync); mSymbols.fDupNativeFenceFDANDROID = nullptr; } } mInitialized = true; reporter.SetSuccessful(); return true; }
int main() { MOZ_RELEASE_ASSERT(sum({1, 2, 3, 4, 5, 6}) == 7 * 3); return 0; }
RefPtr<OmxPromiseLayer::OmxCommandPromise> OmxPromiseLayer::SendCommand(OMX_COMMANDTYPE aCmd, OMX_U32 aParam1, OMX_PTR aCmdData) { if (aCmd == OMX_CommandFlush) { // It doesn't support another flush commands before previous one is completed. MOZ_RELEASE_ASSERT(!mFlushCommands.Length()); // Some coomponents don't send event with OMX_ALL, they send flush complete // event with input port and another event for output port. // In prupose of better compatibility, we interpret the OMX_ALL to OMX_DirInput // and OMX_DirOutput flush separately. OMX_DIRTYPE types[] = {OMX_DIRTYPE::OMX_DirInput, OMX_DIRTYPE::OMX_DirOutput}; for(const auto type : types) { if ((aParam1 == type) || (aParam1 == OMX_ALL)) { mFlushCommands.AppendElement(FlushCommand({type, aCmdData})); } if (type == OMX_DirInput) { // Clear all buffered raw data. mRawDatas.Clear(); } } // Don't overlay more than one flush command, some components can't overlay flush commands. // So here we send another flush after receiving the previous flush completed event. if (mFlushCommands.Length()) { OMX_ERRORTYPE err = mPlatformLayer->SendCommand(OMX_CommandFlush, mFlushCommands.ElementAt(0).type, mFlushCommands.ElementAt(0).cmd); if (err != OMX_ErrorNone) { OmxCommandFailureHolder failure(OMX_ErrorNotReady, OMX_CommandFlush); return OmxCommandPromise::CreateAndReject(failure, __func__); } } else { LOG("OMX_CommandFlush parameter error"); OmxCommandFailureHolder failure(OMX_ErrorNotReady, OMX_CommandFlush); return OmxCommandPromise::CreateAndReject(failure, __func__); } } else { OMX_ERRORTYPE err = mPlatformLayer->SendCommand(aCmd, aParam1, aCmdData); if (err != OMX_ErrorNone) { OmxCommandFailureHolder failure(OMX_ErrorNotReady, aCmd); return OmxCommandPromise::CreateAndReject(failure, __func__); } } RefPtr<OmxCommandPromise> p; if (aCmd == OMX_CommandStateSet) { p = mCommandStatePromise.Ensure(__func__); } else if (aCmd == OMX_CommandFlush) { p = mFlushPromise.Ensure(__func__); } else if (aCmd == OMX_CommandPortEnable) { p = mPortEnablePromise.Ensure(__func__); } else if (aCmd == OMX_CommandPortDisable) { p = mPortDisablePromise.Ensure(__func__); } else { LOG("error unsupport command"); MOZ_ASSERT(0); } return p; }
void js::ThisThread::GetName(char* nameBuffer, size_t len) { MOZ_RELEASE_ASSERT(len > 0); *nameBuffer = '\0'; }
void OriginAttributes::CreateSuffix(nsACString& aStr) const { UniquePtr<URLParams> params(new URLParams()); nsAutoString value; // // Important: While serializing any string-valued attributes, perform a // release-mode assertion to make sure that they don't contain characters that // will break the quota manager when it uses the serialization for file // naming (see addonId below). // if (mAppId != nsIScriptSecurityManager::NO_APP_ID) { value.AppendInt(mAppId); params->Set(NS_LITERAL_STRING("appId"), value); } if (mInIsolatedMozBrowser) { params->Set(NS_LITERAL_STRING("inBrowser"), NS_LITERAL_STRING("1")); } if (!mAddonId.IsEmpty()) { if (mAddonId.FindCharInSet(dom::quota::QuotaManager::kReplaceChars) != kNotFound) { #ifdef MOZ_CRASHREPORTER CrashReporter::AnnotateCrashReport(NS_LITERAL_CSTRING("Crash_AddonId"), NS_ConvertUTF16toUTF8(mAddonId)); #endif MOZ_CRASH(); } params->Set(NS_LITERAL_STRING("addonId"), mAddonId); } if (mUserContextId != nsIScriptSecurityManager::DEFAULT_USER_CONTEXT_ID) { value.Truncate(); value.AppendInt(mUserContextId); params->Set(NS_LITERAL_STRING("userContextId"), value); } if (mPrivateBrowsingId) { value.Truncate(); value.AppendInt(mPrivateBrowsingId); params->Set(NS_LITERAL_STRING("privateBrowsingId"), value); } if (!mFirstPartyDomain.IsEmpty()) { MOZ_RELEASE_ASSERT(mFirstPartyDomain.FindCharInSet(dom::quota::QuotaManager::kReplaceChars) == kNotFound); params->Set(NS_LITERAL_STRING("firstPartyDomain"), mFirstPartyDomain); } aStr.Truncate(); params->Serialize(value); if (!value.IsEmpty()) { aStr.AppendLiteral("^"); aStr.Append(NS_ConvertUTF16toUTF8(value)); } // In debug builds, check the whole string for illegal characters too (just in case). #ifdef DEBUG nsAutoCString str; str.Assign(aStr); MOZ_ASSERT(str.FindCharInSet(dom::quota::QuotaManager::kReplaceChars) == kNotFound); #endif }
void unmapPages(void* p, size_t size) { if (munmap(p, size)) MOZ_RELEASE_ASSERT(errno == ENOMEM); }
void ThreadStackHelper::CollectNativeLeafAddr(void* aAddr) { MOZ_RELEASE_ASSERT(mStackToFill); TryAppendFrame(HangEntryProgCounter(reinterpret_cast<uintptr_t>(aAddr))); }
void SharedSurface_SurfaceTexture::WaitForBufferOwnership() { MOZ_RELEASE_ASSERT(!mSurface->GetAvailable()); mSurface->SetAvailable(true); }
/* static */ const CanonicalBrowsingContext* CanonicalBrowsingContext::Cast( const BrowsingContext* aContext) { MOZ_RELEASE_ASSERT(XRE_IsParentProcess()); return static_cast<const CanonicalBrowsingContext*>(aContext); }
bool GLLibraryEGL::EnsureInitialized() { if (mInitialized) { return true; } mozilla::ScopedGfxFeatureReporter reporter("EGL"); #ifdef MOZ_B2G if (!sCurrentContext.init()) MOZ_CRASH("Tls init failed"); #endif #ifdef XP_WIN if (!mEGLLibrary) { // On Windows, the GLESv2, EGL and DXSDK libraries are shipped with libxul and // we should look for them there. We have to load the libs in this // order, because libEGL.dll depends on libGLESv2.dll which depends on the DXSDK // libraries. This matters especially for WebRT apps which are in a different directory. // See bug 760323 and bug 749459 // Also note that we intentionally leak the libs we load. do { // Windows 8.1 has d3dcompiler_47.dll in the system directory. // Try it first. Note that _46 will never be in the system // directory and we ship with at least _43. So there is no point // trying _46 and _43 in the system directory. if (LoadLibrarySystem32(L"d3dcompiler_47.dll")) break; #ifdef MOZ_D3DCOMPILER_VISTA_DLL if (LoadLibraryForEGLOnWindows(NS_LITERAL_STRING(NS_STRINGIFY(MOZ_D3DCOMPILER_VISTA_DLL)))) break; #endif #ifdef MOZ_D3DCOMPILER_XP_DLL if (LoadLibraryForEGLOnWindows(NS_LITERAL_STRING(NS_STRINGIFY(MOZ_D3DCOMPILER_XP_DLL)))) break; #endif MOZ_ASSERT(false, "d3dcompiler DLL loading failed."); } while (false); LoadLibraryForEGLOnWindows(NS_LITERAL_STRING("libGLESv2.dll")); mEGLLibrary = LoadLibraryForEGLOnWindows(NS_LITERAL_STRING("libEGL.dll")); if (!mEGLLibrary) return false; } #else // !Windows // On non-Windows (Android) we use system copies of libEGL. We look for // the APITrace lib, libEGL.so, and libEGL.so.1 in that order. #if defined(ANDROID) if (!mEGLLibrary) mEGLLibrary = LoadApitraceLibrary(); #endif if (!mEGLLibrary) { printf_stderr("Attempting load of libEGL.so\n"); mEGLLibrary = PR_LoadLibrary("libEGL.so"); } #if defined(XP_UNIX) if (!mEGLLibrary) { mEGLLibrary = PR_LoadLibrary("libEGL.so.1"); } #endif if (!mEGLLibrary) { NS_WARNING("Couldn't load EGL LIB."); return false; } #endif // !Windows #define SYMBOL(name) \ { (PRFuncPtr*) &mSymbols.f##name, { "egl" #name, nullptr } } GLLibraryLoader::SymLoadStruct earlySymbols[] = { SYMBOL(GetDisplay), SYMBOL(Terminate), SYMBOL(GetCurrentSurface), SYMBOL(GetCurrentContext), SYMBOL(MakeCurrent), SYMBOL(DestroyContext), SYMBOL(CreateContext), SYMBOL(DestroySurface), SYMBOL(CreateWindowSurface), SYMBOL(CreatePbufferSurface), SYMBOL(CreatePixmapSurface), SYMBOL(BindAPI), SYMBOL(Initialize), SYMBOL(ChooseConfig), SYMBOL(GetError), SYMBOL(GetConfigs), SYMBOL(GetConfigAttrib), SYMBOL(WaitNative), SYMBOL(GetProcAddress), SYMBOL(SwapBuffers), SYMBOL(CopyBuffers), SYMBOL(QueryString), SYMBOL(QueryContext), SYMBOL(BindTexImage), SYMBOL(ReleaseTexImage), SYMBOL(QuerySurface), { nullptr, { nullptr } } }; if (!GLLibraryLoader::LoadSymbols(mEGLLibrary, &earlySymbols[0])) { NS_WARNING("Couldn't find required entry points in EGL library (early init)"); return false; } GLLibraryLoader::SymLoadStruct optionalSymbols[] = { // On Android 4.3 and up, certain features like ANDROID_native_fence_sync // can only be queried by using a special eglQueryString. { (PRFuncPtr*) &mSymbols.fQueryStringImplementationANDROID, { "_Z35eglQueryStringImplementationANDROIDPvi", nullptr } }, { nullptr, { nullptr } } }; // Do not warn about the failure to load this - see bug 1092191 GLLibraryLoader::LoadSymbols(mEGLLibrary, &optionalSymbols[0], nullptr, nullptr, false); #if defined(MOZ_WIDGET_GONK) && ANDROID_VERSION >= 18 MOZ_RELEASE_ASSERT(mSymbols.fQueryStringImplementationANDROID, "Couldn't find eglQueryStringImplementationANDROID"); #endif //Initialize client extensions InitExtensionsFromDisplay(EGL_NO_DISPLAY); GLLibraryLoader::PlatformLookupFunction lookupFunction = (GLLibraryLoader::PlatformLookupFunction)mSymbols.fGetProcAddress; #ifdef XP_WIN if (IsExtensionSupported(ANGLE_platform_angle_d3d)) { GLLibraryLoader::SymLoadStruct d3dSymbols[] = { { (PRFuncPtr*)&mSymbols.fGetPlatformDisplayEXT, { "eglGetPlatformDisplayEXT", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &d3dSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports ANGLE_platform_angle_d3d without exposing its functions!"); MarkExtensionUnsupported(ANGLE_platform_angle_d3d); mSymbols.fGetPlatformDisplayEXT = nullptr; } } #endif mEGLDisplay = GetAndInitDisplay(*this, EGL_DEFAULT_DISPLAY); const char* vendor = (char*)fQueryString(mEGLDisplay, LOCAL_EGL_VENDOR); if (vendor && (strstr(vendor, "TransGaming") != 0 || strstr(vendor, "Google Inc.") != 0)) { mIsANGLE = true; } if (mIsANGLE) { EGLDisplay newDisplay = EGL_NO_DISPLAY; // D3D11 ANGLE only works with OMTC; there's a bug in the non-OMTC layer // manager, and it's pointless to try to fix it. We also don't try // D3D11 ANGLE if the layer manager is prefering D3D9 (hrm, do we care?) if (gfxPrefs::LayersOffMainThreadCompositionEnabled() && !gfxPrefs::LayersPreferD3D9()) { if (gfxPrefs::WebGLANGLEForceD3D11()) { newDisplay = GetAndInitDisplay(*this, LOCAL_EGL_D3D11_ONLY_DISPLAY_ANGLE); } else if (gfxPrefs::WebGLANGLETryD3D11() && gfxPlatform::CanUseDirect3D11ANGLE()) { newDisplay = GetAndInitDisplay(*this, LOCAL_EGL_D3D11_ELSE_D3D9_DISPLAY_ANGLE); } } if (newDisplay != EGL_NO_DISPLAY) { DebugOnly<EGLBoolean> success = fTerminate(mEGLDisplay); MOZ_ASSERT(success == LOCAL_EGL_TRUE); mEGLDisplay = newDisplay; vendor = (char*)fQueryString(mEGLDisplay, LOCAL_EGL_VENDOR); } } InitExtensionsFromDisplay(mEGLDisplay); if (IsExtensionSupported(KHR_lock_surface)) { GLLibraryLoader::SymLoadStruct lockSymbols[] = { { (PRFuncPtr*) &mSymbols.fLockSurface, { "eglLockSurfaceKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fUnlockSurface, { "eglUnlockSurfaceKHR", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &lockSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports KHR_lock_surface without exposing its functions!"); MarkExtensionUnsupported(KHR_lock_surface); mSymbols.fLockSurface = nullptr; mSymbols.fUnlockSurface = nullptr; } } if (IsExtensionSupported(ANGLE_surface_d3d_texture_2d_share_handle)) { GLLibraryLoader::SymLoadStruct d3dSymbols[] = { { (PRFuncPtr*) &mSymbols.fQuerySurfacePointerANGLE, { "eglQuerySurfacePointerANGLE", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &d3dSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports ANGLE_surface_d3d_texture_2d_share_handle without exposing its functions!"); MarkExtensionUnsupported(ANGLE_surface_d3d_texture_2d_share_handle); mSymbols.fQuerySurfacePointerANGLE = nullptr; } } //XXX: use correct extension name if (IsExtensionSupported(ANGLE_surface_d3d_texture_2d_share_handle)) { GLLibraryLoader::SymLoadStruct d3dSymbols[] = { { (PRFuncPtr*)&mSymbols.fSurfaceReleaseSyncANGLE, { "eglSurfaceReleaseSyncANGLE", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &d3dSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports ANGLE_surface_d3d_texture_2d_share_handle without exposing its functions!"); MarkExtensionUnsupported(ANGLE_surface_d3d_texture_2d_share_handle); mSymbols.fSurfaceReleaseSyncANGLE = nullptr; } } if (IsExtensionSupported(KHR_fence_sync)) { GLLibraryLoader::SymLoadStruct syncSymbols[] = { { (PRFuncPtr*) &mSymbols.fCreateSync, { "eglCreateSyncKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fDestroySync, { "eglDestroySyncKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fClientWaitSync, { "eglClientWaitSyncKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fGetSyncAttrib, { "eglGetSyncAttribKHR", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &syncSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports KHR_fence_sync without exposing its functions!"); MarkExtensionUnsupported(KHR_fence_sync); mSymbols.fCreateSync = nullptr; mSymbols.fDestroySync = nullptr; mSymbols.fClientWaitSync = nullptr; mSymbols.fGetSyncAttrib = nullptr; } } if (IsExtensionSupported(KHR_image) || IsExtensionSupported(KHR_image_base)) { GLLibraryLoader::SymLoadStruct imageSymbols[] = { { (PRFuncPtr*) &mSymbols.fCreateImage, { "eglCreateImageKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fDestroyImage, { "eglDestroyImageKHR", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &imageSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports KHR_image(_base) without exposing its functions!"); MarkExtensionUnsupported(KHR_image); MarkExtensionUnsupported(KHR_image_base); MarkExtensionUnsupported(KHR_image_pixmap); mSymbols.fCreateImage = nullptr; mSymbols.fDestroyImage = nullptr; } } else { MarkExtensionUnsupported(KHR_image_pixmap); } if (IsExtensionSupported(ANDROID_native_fence_sync)) { GLLibraryLoader::SymLoadStruct nativeFenceSymbols[] = { { (PRFuncPtr*) &mSymbols.fDupNativeFenceFDANDROID, { "eglDupNativeFenceFDANDROID", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &nativeFenceSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports ANDROID_native_fence_sync without exposing its functions!"); MarkExtensionUnsupported(ANDROID_native_fence_sync); mSymbols.fDupNativeFenceFDANDROID = nullptr; } } mInitialized = true; reporter.SetSuccessful(); return true; }
void ThreadStackHelper::CollectJitReturnAddr(void* aAddr) { MOZ_RELEASE_ASSERT(mStackToFill); TryAppendFrame(HangEntryJit()); }
void VsyncBridgeChild::ProcessingError(Result aCode, const char* aReason) { MOZ_RELEASE_ASSERT(aCode == MsgDropped, "Processing error in VsyncBridgeChild"); }
void ThreadStackHelper::CollectPseudoEntry(const js::ProfileEntry& aEntry) { // For non-js frames we just include the raw label. if (!aEntry.isJs()) { const char* entryLabel = aEntry.label(); // entryLabel is a statically allocated string, so we want to store a // reference to it without performing any allocations. This is important, as // we aren't allowed to allocate within this function. // // The variant for this kind of label in our HangStack object is a // `nsCString`, which normally contains heap allocated string data. However, // `nsCString` has an optimization for literal strings which causes the // backing data to not be copied when being copied between nsCString // objects. // // We take advantage of that optimization by creating a nsCString object // which has the LITERAL flag set. Without this optimization, this code // would be incorrect. nsCString label; label.AssignLiteral(entryLabel, strlen(entryLabel)); // Let's make sure we don't deadlock here, by asserting that `label`'s // backing data matches. MOZ_RELEASE_ASSERT(label.BeginReading() == entryLabel, "String copy performed during ThreadStackHelper::CollectPseudoEntry"); TryAppendFrame(label); return; } if (!aEntry.script()) { TryAppendFrame(HangEntrySuppressed()); return; } if (!IsChromeJSScript(aEntry.script())) { TryAppendFrame(HangEntryContent()); return; } // Rather than using the profiler's dynamic string, we compute our own string. // This is because we want to do some size-saving strategies, and throw out // information which won't help us as much. // XXX: We currently don't collect the function name which hung. const char* filename = JS_GetScriptFilename(aEntry.script()); unsigned lineno = JS_PCToLineNumber(aEntry.script(), aEntry.pc()); // Some script names are in the form "foo -> bar -> baz". // Here we find the origin of these redirected scripts. const char* basename = GetPathAfterComponent(filename, " -> "); if (basename) { filename = basename; } // Strip chrome:// or resource:// off of the filename if present. basename = GetFullPathForScheme(filename, "chrome://"); if (!basename) { basename = GetFullPathForScheme(filename, "resource://"); } if (!basename) { // If we're in an add-on script, under the {profile}/extensions // directory, extract the path after the /extensions/ part. basename = GetPathAfterComponent(filename, "/extensions/"); } if (!basename) { // Only keep the file base name for paths outside the above formats. basename = strrchr(filename, '/'); basename = basename ? basename + 1 : filename; // Look for Windows path separator as well. filename = strrchr(basename, '\\'); if (filename) { basename = filename + 1; } } char buffer[128]; // Enough to fit longest js file name from the tree size_t len = SprintfLiteral(buffer, "%s:%u", basename, lineno); if (len < sizeof(buffer)) { mDesiredBufferSize += len + 1; if (mStackToFill->stack().Capacity() > mStackToFill->stack().Length() && (mStackToFill->strbuffer().Capacity() - mStackToFill->strbuffer().Length()) > len + 1) { // NOTE: We only increment this if we're going to successfully append. mDesiredStackSize += 1; uint32_t start = mStackToFill->strbuffer().Length(); mStackToFill->strbuffer().AppendElements(buffer, len); mStackToFill->strbuffer().AppendElement('\0'); mStackToFill->stack().AppendElement(HangEntryBufOffset(start)); return; } } TryAppendFrame(HangEntryChromeScript()); }
bool BasePrincipal::Subsumes(nsIPrincipal* aOther, DocumentDomainConsideration aConsideration) { MOZ_RELEASE_ASSERT(aOther, "The caller is performing a nonsensical security check!"); return SubsumesInternal(aOther, aConsideration); }
void PackagedAppVerifier::OnManifestVerified(bool aSuccess) { MOZ_RELEASE_ASSERT(NS_IsMainThread(), "OnManifestVerified must be on main thread."); LOG(("PackagedAppVerifier::OnManifestVerified: %d", aSuccess)); // The listener could have been removed before we verify the resource. if (!mListener) { return; } if (!aSuccess && mBypassVerification) { aSuccess = true; LOG(("Developer mode! Treat junk signature valid.")); } if (aSuccess && !mSignature.IsEmpty()) { // Get the package location from the manifest nsAutoCString packageOrigin; mPackagedAppUtils->GetPackageOrigin(packageOrigin); if (packageOrigin != mPackageOrigin) { aSuccess = false; LOG(("moz-package-location doesn't match:\nFrom: %s\nManifest: %s\n", mPackageOrigin.get(), packageOrigin.get())); } } // Only when the manifest verified and package has signature would we // regard this package is signed. mIsPackageSigned = aSuccess && !mSignature.IsEmpty(); mState = aSuccess ? STATE_MANIFEST_VERIFIED_OK : STATE_MANIFEST_VERIFIED_FAILED; // Obtain the package identifier from manifest if the package is signed. if (mIsPackageSigned) { mPackagedAppUtils->GetPackageIdentifier(mPackageIdentifer); LOG(("PackageIdentifer is: %s", mPackageIdentifer.get())); } // If the package is signed, add related info to the package cache. if (mIsPackageSigned && mPackageCacheEntry) { LOG(("This package is signed. Add this info to the cache channel.")); if (mPackageCacheEntry) { mPackageCacheEntry->SetMetaDataElement(kSignedPakIdMetadataKey, mPackageIdentifer.get()); mPackageCacheEntry = nullptr; // the cache entry is no longer needed. } } RefPtr<ResourceCacheInfo> info(mPendingResourceCacheInfoList.popFirst()); MOZ_ASSERT(info); mListener->OnVerified(true, // aIsManifest. info->mURI, info->mCacheEntry, info->mStatusCode, info->mIsLastPart, aSuccess); LOG(("Ready to verify resources that were cached during verification")); // Verify the resources which were cached during verification accordingly. for (auto i = mPendingResourceCacheInfoList.getFirst(); i; i = i->getNext()) { VerifyResource(i); } }
js::Thread::~Thread() { LockGuard<Mutex> lock(idMutex_); MOZ_RELEASE_ASSERT(!joinable(lock)); }
static void BroadcastSetThreadSandbox(const sock_fprog* aFilter) { pid_t pid, tid, myTid; DIR *taskdp; struct dirent *de; // This function does not own *aFilter, so this global needs to // always be zeroed before returning. gSetSandboxFilter = aFilter; static_assert(sizeof(mozilla::Atomic<int>) == sizeof(int), "mozilla::Atomic<int> isn't represented by an int"); pid = getpid(); myTid = syscall(__NR_gettid); taskdp = opendir("/proc/self/task"); if (taskdp == nullptr) { SANDBOX_LOG_ERROR("opendir /proc/self/task: %s\n", strerror(errno)); MOZ_CRASH(); } EnterChroot(); // In case this races with a not-yet-deprivileged thread cloning // itself, repeat iterating over all threads until we find none // that are still privileged. bool sandboxProgress; do { sandboxProgress = false; // For each thread... while ((de = readdir(taskdp))) { char *endptr; tid = strtol(de->d_name, &endptr, 10); if (*endptr != '\0' || tid <= 0) { // Not a task ID. continue; } if (tid == myTid) { // Drop this thread's privileges last, below, so we can // continue to signal other threads. continue; } MOZ_RELEASE_ASSERT(gSeccompTsyncBroadcastSignum != 0); // Reset the futex cell and signal. gSetSandboxDone = 0; if (syscall(__NR_tgkill, pid, tid, gSeccompTsyncBroadcastSignum) != 0) { if (errno == ESRCH) { SANDBOX_LOG_ERROR("Thread %d unexpectedly exited.", tid); // Rescan threads, in case it forked before exiting. sandboxProgress = true; continue; } SANDBOX_LOG_ERROR("tgkill(%d,%d): %s\n", pid, tid, strerror(errno)); MOZ_CRASH(); } // It's unlikely, but if the thread somehow manages to exit // after receiving the signal but before entering the signal // handler, we need to avoid blocking forever. // // Using futex directly lets the signal handler send the wakeup // from an async signal handler (pthread mutex/condvar calls // aren't allowed), and to use a relative timeout that isn't // affected by changes to the system clock (not possible with // POSIX semaphores). // // If a thread doesn't respond within a reasonable amount of // time, but still exists, we crash -- the alternative is either // blocking forever or silently losing security, and it // shouldn't actually happen. static const int crashDelay = 10; // seconds struct timespec timeLimit; clock_gettime(CLOCK_MONOTONIC, &timeLimit); timeLimit.tv_sec += crashDelay; while (true) { static const struct timespec futexTimeout = { 0, 10*1000*1000 }; // 10ms // Atomically: if gSetSandboxDone == 0, then sleep. if (syscall(__NR_futex, reinterpret_cast<int*>(&gSetSandboxDone), FUTEX_WAIT, 0, &futexTimeout) != 0) { if (errno != EWOULDBLOCK && errno != ETIMEDOUT && errno != EINTR) { SANDBOX_LOG_ERROR("FUTEX_WAIT: %s\n", strerror(errno)); MOZ_CRASH(); } } // Did the handler finish? if (gSetSandboxDone > 0) { if (gSetSandboxDone == 2) { sandboxProgress = true; } break; } // Has the thread ceased to exist? if (syscall(__NR_tgkill, pid, tid, 0) != 0) { if (errno == ESRCH) { SANDBOX_LOG_ERROR("Thread %d unexpectedly exited.", tid); } // Rescan threads, in case it forked before exiting. // Also, if it somehow failed in a way that wasn't ESRCH, // and still exists, that will be handled on the next pass. sandboxProgress = true; break; } struct timespec now; clock_gettime(CLOCK_MONOTONIC, &now); if (now.tv_sec > timeLimit.tv_sec || (now.tv_sec == timeLimit.tv_sec && now.tv_nsec > timeLimit.tv_nsec)) { SANDBOX_LOG_ERROR("Thread %d unresponsive for %d seconds." " Killing process.", tid, crashDelay); MOZ_CRASH(); } } } rewinddir(taskdp); } while (sandboxProgress); void (*oldHandler)(int); oldHandler = signal(gSeccompTsyncBroadcastSignum, SIG_DFL); gSeccompTsyncBroadcastSignum = 0; if (oldHandler != SetThreadSandboxHandler) { // See the comment on FindFreeSignalNumber about race conditions. SANDBOX_LOG_ERROR("handler for signal %d was changed to %p!", gSeccompTsyncBroadcastSignum, oldHandler); MOZ_CRASH(); } Unused << closedir(taskdp); // And now, deprivilege the main thread: SetThreadSandbox(); gSetSandboxFilter = nullptr; }
void SandboxBroker::SetSecurityLevelForContentProcess(int32_t aSandboxLevel) { MOZ_RELEASE_ASSERT(mPolicy, "mPolicy must be set before this call."); sandbox::JobLevel jobLevel; sandbox::TokenLevel accessTokenLevel; sandbox::IntegrityLevel initialIntegrityLevel; sandbox::IntegrityLevel delayedIntegrityLevel; // The setting of these levels is pretty arbitrary, but they are a useful (if // crude) tool while we are tightening the policy. Gaps are left to try and // avoid changing their meaning. MOZ_RELEASE_ASSERT(aSandboxLevel >= 1, "Should not be called with aSandboxLevel < 1"); if (aSandboxLevel >= 20) { jobLevel = sandbox::JOB_LOCKDOWN; accessTokenLevel = sandbox::USER_LOCKDOWN; initialIntegrityLevel = sandbox::INTEGRITY_LEVEL_LOW; delayedIntegrityLevel = sandbox::INTEGRITY_LEVEL_UNTRUSTED; } else if (aSandboxLevel >= 10) { jobLevel = sandbox::JOB_RESTRICTED; accessTokenLevel = sandbox::USER_LIMITED; initialIntegrityLevel = sandbox::INTEGRITY_LEVEL_LOW; delayedIntegrityLevel = sandbox::INTEGRITY_LEVEL_LOW; } else if (aSandboxLevel >= 2) { jobLevel = sandbox::JOB_INTERACTIVE; accessTokenLevel = sandbox::USER_INTERACTIVE; initialIntegrityLevel = sandbox::INTEGRITY_LEVEL_LOW; delayedIntegrityLevel = sandbox::INTEGRITY_LEVEL_LOW; } else if (aSandboxLevel == 1) { jobLevel = sandbox::JOB_NONE; accessTokenLevel = sandbox::USER_NON_ADMIN; initialIntegrityLevel = sandbox::INTEGRITY_LEVEL_LOW; delayedIntegrityLevel = sandbox::INTEGRITY_LEVEL_LOW; } sandbox::ResultCode result = mPolicy->SetJobLevel(jobLevel, 0 /* ui_exceptions */); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "Setting job level failed, have you set memory limit when jobLevel == JOB_NONE?"); result = mPolicy->SetTokenLevel(sandbox::USER_RESTRICTED_SAME_ACCESS, accessTokenLevel); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "Lockdown level cannot be USER_UNPROTECTED or USER_LAST if initial level was USER_RESTRICTED_SAME_ACCESS"); result = mPolicy->SetIntegrityLevel(initialIntegrityLevel); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "SetIntegrityLevel should never fail, what happened?"); result = mPolicy->SetDelayedIntegrityLevel(delayedIntegrityLevel); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "SetDelayedIntegrityLevel should never fail, what happened?"); if (aSandboxLevel > 2) { result = mPolicy->SetAlternateDesktop(true); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "Failed to create alternate desktop for sandbox."); } sandbox::MitigationFlags mitigations = sandbox::MITIGATION_BOTTOM_UP_ASLR | sandbox::MITIGATION_HEAP_TERMINATE | sandbox::MITIGATION_SEHOP | sandbox::MITIGATION_DEP_NO_ATL_THUNK | sandbox::MITIGATION_DEP; result = mPolicy->SetProcessMitigations(mitigations); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "Invalid flags for SetProcessMitigations."); mitigations = sandbox::MITIGATION_STRICT_HANDLE_CHECKS | sandbox::MITIGATION_DLL_SEARCH_ORDER; result = mPolicy->SetDelayedProcessMitigations(mitigations); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "Invalid flags for SetDelayedProcessMitigations."); // Add the policy for the client side of a pipe. It is just a file // in the \pipe\ namespace. We restrict it to pipes that start with // "chrome." so the sandboxed process cannot connect to system services. result = mPolicy->AddRule(sandbox::TargetPolicy::SUBSYS_FILES, sandbox::TargetPolicy::FILES_ALLOW_ANY, L"\\??\\pipe\\chrome.*"); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "With these static arguments AddRule should never fail, what happened?"); // Add the policy for the client side of the crash server pipe. result = mPolicy->AddRule(sandbox::TargetPolicy::SUBSYS_FILES, sandbox::TargetPolicy::FILES_ALLOW_ANY, L"\\??\\pipe\\gecko-crash-server-pipe.*"); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "With these static arguments AddRule should never fail, what happened?"); // The content process needs to be able to duplicate named pipes back to the // broker process, which are File type handles. result = mPolicy->AddRule(sandbox::TargetPolicy::SUBSYS_HANDLES, sandbox::TargetPolicy::HANDLES_DUP_BROKER, L"File"); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "With these static arguments AddRule should never fail, what happened?"); // The content process needs to be able to duplicate shared memory handles, // which are Section handles, to the broker process and other child processes. result = mPolicy->AddRule(sandbox::TargetPolicy::SUBSYS_HANDLES, sandbox::TargetPolicy::HANDLES_DUP_BROKER, L"Section"); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "With these static arguments AddRule should never fail, what happened?"); result = mPolicy->AddRule(sandbox::TargetPolicy::SUBSYS_HANDLES, sandbox::TargetPolicy::HANDLES_DUP_ANY, L"Section"); MOZ_RELEASE_ASSERT(sandbox::SBOX_ALL_OK == result, "With these static arguments AddRule should never fail, what happened?"); }
void SandboxEarlyInit(GeckoProcessType aType) { const SandboxInfo info = SandboxInfo::Get(); if (info.Test(SandboxInfo::kUnexpectedThreads)) { return; } MOZ_RELEASE_ASSERT(IsSingleThreaded()); // Which kinds of resource isolation (of those that need to be set // up at this point) can be used by this process? bool canChroot = false; bool canUnshareNet = false; bool canUnshareIPC = false; switch (aType) { case GeckoProcessType_Default: MOZ_ASSERT(false, "SandboxEarlyInit in parent process"); return; #ifdef MOZ_GMP_SANDBOX case GeckoProcessType_GMPlugin: if (!info.Test(SandboxInfo::kEnabledForMedia)) { break; } canUnshareNet = true; canUnshareIPC = true; // Need seccomp-bpf to intercept open(). canChroot = info.Test(SandboxInfo::kHasSeccompBPF); break; #endif // In the future, content processes will be able to use some of // these. default: // Other cases intentionally left blank. break; } // If TSYNC is not supported, set up signal handler // used to enable seccomp on each thread. if (!info.Test(SandboxInfo::kHasSeccompTSync)) { gSeccompTsyncBroadcastSignum = FindFreeSignalNumber(); if (gSeccompTsyncBroadcastSignum == 0) { SANDBOX_LOG_ERROR("No available signal numbers!"); MOZ_CRASH(); } void (*oldHandler)(int); oldHandler = signal(gSeccompTsyncBroadcastSignum, SetThreadSandboxHandler); if (oldHandler != SIG_DFL) { // See the comment on FindFreeSignalNumber about race conditions. SANDBOX_LOG_ERROR("signal %d in use by handler %p!\n", gSeccompTsyncBroadcastSignum, oldHandler); MOZ_CRASH(); } } // If there's nothing to do, then we're done. if (!canChroot && !canUnshareNet && !canUnshareIPC) { return; } { LinuxCapabilities existingCaps; if (existingCaps.GetCurrent() && existingCaps.AnyEffective()) { SANDBOX_LOG_ERROR("PLEASE DO NOT RUN THIS AS ROOT. Strange things may" " happen when capabilities are dropped."); } } // If capabilities can't be gained, then nothing can be done. if (!info.Test(SandboxInfo::kHasUserNamespaces)) { // Drop any existing capabilities; unsharing the user namespace // would implicitly drop them, so if we're running in a broken // configuration where that would matter (e.g., running as root // from a non-root-owned mode-0700 directory) this means it will // break the same way on all kernels and be easier to troubleshoot. LinuxCapabilities().SetCurrent(); return; } // The failure cases for the various unshares, and setting up the // chroot helper, don't strictly need to be fatal -- but they also // shouldn't fail on any reasonable system, so let's take the small // risk of breakage over the small risk of quietly providing less // security than we expect. (Unlike in SandboxInfo, this is in the // child process, so crashing here isn't as severe a response to the // unexpected.) if (!UnshareUserNamespace()) { SANDBOX_LOG_ERROR("unshare(CLONE_NEWUSER): %s", strerror(errno)); // If CanCreateUserNamespace (SandboxInfo.cpp) returns true, then // the unshare shouldn't have failed. MOZ_CRASH("unshare(CLONE_NEWUSER)"); } // No early returns after this point! We need to drop the // capabilities that were gained by unsharing the user namesapce. if (canUnshareIPC && syscall(__NR_unshare, CLONE_NEWIPC) != 0) { SANDBOX_LOG_ERROR("unshare(CLONE_NEWIPC): %s", strerror(errno)); MOZ_CRASH("unshare(CLONE_NEWIPC)"); } if (canUnshareNet && syscall(__NR_unshare, CLONE_NEWNET) != 0) { SANDBOX_LOG_ERROR("unshare(CLONE_NEWNET): %s", strerror(errno)); MOZ_CRASH("unshare(CLONE_NEWNET)"); } if (canChroot) { gChrootHelper = MakeUnique<SandboxChroot>(); if (!gChrootHelper->Prepare()) { SANDBOX_LOG_ERROR("failed to set up chroot helper"); MOZ_CRASH("SandboxChroot::Prepare"); } } if (!LinuxCapabilities().SetCurrent()) { SANDBOX_LOG_ERROR("dropping capabilities: %s", strerror(errno)); MOZ_CRASH("can't drop capabilities"); } }
AbstractThread* DocGroup::AbstractMainThreadFor(TaskCategory aCategory) { MOZ_RELEASE_ASSERT(NS_IsMainThread()); return mTabGroup->AbstractMainThreadFor(aCategory); }
bool GLLibraryEGL::EnsureInitialized() { if (mInitialized) { return true; } mozilla::ScopedGfxFeatureReporter reporter("EGL"); #ifdef MOZ_B2G if (!sCurrentContext.init()) MOZ_CRASH("Tls init failed"); #endif #ifdef XP_WIN #ifdef MOZ_WEBGL if (!mEGLLibrary) { // On Windows, the GLESv2, EGL and DXSDK libraries are shipped with libxul and // we should look for them there. We have to load the libs in this // order, because libEGL.dll depends on libGLESv2.dll which depends on the DXSDK // libraries. This matters especially for WebRT apps which are in a different directory. // See bug 760323 and bug 749459 // Also note that we intentionally leak the libs we load. do { // Windows 8.1 has d3dcompiler_47.dll in the system directory. // Try it first. Note that _46 will never be in the system // directory and we ship with at least _43. So there is no point // trying _46 and _43 in the system directory. if (LoadLibrarySystem32(L"d3dcompiler_47.dll")) break; #ifdef MOZ_D3DCOMPILER_VISTA_DLL if (LoadLibraryForEGLOnWindows(NS_LITERAL_STRING(NS_STRINGIFY(MOZ_D3DCOMPILER_VISTA_DLL)))) break; #endif #ifdef MOZ_D3DCOMPILER_XP_DLL if (LoadLibraryForEGLOnWindows(NS_LITERAL_STRING(NS_STRINGIFY(MOZ_D3DCOMPILER_XP_DLL)))) break; #endif MOZ_ASSERT(false, "d3dcompiler DLL loading failed."); } while (false); LoadLibraryForEGLOnWindows(NS_LITERAL_STRING("libGLESv2.dll")); mEGLLibrary = LoadLibraryForEGLOnWindows(NS_LITERAL_STRING("libEGL.dll")); if (!mEGLLibrary) return false; } #endif // MOZ_WEBGL #else // !Windows // On non-Windows (Android) we use system copies of libEGL. We look for // the APITrace lib, libEGL.so, and libEGL.so.1 in that order. #if defined(ANDROID) if (!mEGLLibrary) mEGLLibrary = LoadApitraceLibrary(); #endif if (!mEGLLibrary) { printf_stderr("Attempting load of libEGL.so\n"); mEGLLibrary = PR_LoadLibrary("libEGL.so"); } #if defined(XP_UNIX) if (!mEGLLibrary) { mEGLLibrary = PR_LoadLibrary("libEGL.so.1"); } #endif if (!mEGLLibrary) { NS_WARNING("Couldn't load EGL LIB."); return false; } #endif // !Windows #define SYMBOL(name) \ { (PRFuncPtr*) &mSymbols.f##name, { "egl" #name, nullptr } } GLLibraryLoader::SymLoadStruct earlySymbols[] = { SYMBOL(GetDisplay), SYMBOL(GetCurrentSurface), SYMBOL(GetCurrentContext), SYMBOL(MakeCurrent), SYMBOL(DestroyContext), SYMBOL(CreateContext), SYMBOL(DestroySurface), SYMBOL(CreateWindowSurface), SYMBOL(CreatePbufferSurface), SYMBOL(CreatePixmapSurface), SYMBOL(BindAPI), SYMBOL(Initialize), SYMBOL(ChooseConfig), SYMBOL(GetError), SYMBOL(GetConfigs), SYMBOL(GetConfigAttrib), SYMBOL(WaitNative), SYMBOL(GetProcAddress), SYMBOL(SwapBuffers), SYMBOL(CopyBuffers), SYMBOL(QueryString), SYMBOL(QueryContext), SYMBOL(BindTexImage), SYMBOL(ReleaseTexImage), SYMBOL(QuerySurface), { nullptr, { nullptr } } }; if (!GLLibraryLoader::LoadSymbols(mEGLLibrary, &earlySymbols[0])) { NS_WARNING("Couldn't find required entry points in EGL library (early init)"); return false; } GLLibraryLoader::SymLoadStruct optionalSymbols[] = { // On Android 4.3 and up, certain features like ANDROID_native_fence_sync // can only be queried by using a special eglQueryString. { (PRFuncPtr*) &mSymbols.fQueryStringImplementationANDROID, { "_Z35eglQueryStringImplementationANDROIDPvi", nullptr } }, { nullptr, { nullptr } } }; GLLibraryLoader::LoadSymbols(mEGLLibrary, &optionalSymbols[0]); #if defined(MOZ_WIDGET_GONK) && ANDROID_VERSION >= 18 MOZ_RELEASE_ASSERT(mSymbols.fQueryStringImplementationANDROID, "Couldn't find eglQueryStringImplementationANDROID"); #endif mEGLDisplay = fGetDisplay(EGL_DEFAULT_DISPLAY); if (!fInitialize(mEGLDisplay, nullptr, nullptr)) return false; const char *vendor = (const char*) fQueryString(mEGLDisplay, LOCAL_EGL_VENDOR); if (vendor && (strstr(vendor, "TransGaming") != 0 || strstr(vendor, "Google Inc.") != 0)) { mIsANGLE = true; } InitExtensions(); GLLibraryLoader::PlatformLookupFunction lookupFunction = (GLLibraryLoader::PlatformLookupFunction)mSymbols.fGetProcAddress; if (IsExtensionSupported(KHR_lock_surface)) { GLLibraryLoader::SymLoadStruct lockSymbols[] = { { (PRFuncPtr*) &mSymbols.fLockSurface, { "eglLockSurfaceKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fUnlockSurface, { "eglUnlockSurfaceKHR", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &lockSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports KHR_lock_surface without exposing its functions!"); MarkExtensionUnsupported(KHR_lock_surface); mSymbols.fLockSurface = nullptr; mSymbols.fUnlockSurface = nullptr; } } if (IsExtensionSupported(ANGLE_surface_d3d_texture_2d_share_handle)) { GLLibraryLoader::SymLoadStruct d3dSymbols[] = { { (PRFuncPtr*) &mSymbols.fQuerySurfacePointerANGLE, { "eglQuerySurfacePointerANGLE", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &d3dSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports ANGLE_surface_d3d_texture_2d_share_handle without exposing its functions!"); MarkExtensionUnsupported(ANGLE_surface_d3d_texture_2d_share_handle); mSymbols.fQuerySurfacePointerANGLE = nullptr; } } if (IsExtensionSupported(KHR_fence_sync)) { GLLibraryLoader::SymLoadStruct syncSymbols[] = { { (PRFuncPtr*) &mSymbols.fCreateSync, { "eglCreateSyncKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fDestroySync, { "eglDestroySyncKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fClientWaitSync, { "eglClientWaitSyncKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fGetSyncAttrib, { "eglGetSyncAttribKHR", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &syncSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports KHR_fence_sync without exposing its functions!"); MarkExtensionUnsupported(KHR_fence_sync); mSymbols.fCreateSync = nullptr; mSymbols.fDestroySync = nullptr; mSymbols.fClientWaitSync = nullptr; mSymbols.fGetSyncAttrib = nullptr; } } if (IsExtensionSupported(KHR_image) || IsExtensionSupported(KHR_image_base)) { GLLibraryLoader::SymLoadStruct imageSymbols[] = { { (PRFuncPtr*) &mSymbols.fCreateImage, { "eglCreateImageKHR", nullptr } }, { (PRFuncPtr*) &mSymbols.fDestroyImage, { "eglDestroyImageKHR", nullptr } }, { nullptr, { nullptr } } }; bool success = GLLibraryLoader::LoadSymbols(mEGLLibrary, &imageSymbols[0], lookupFunction); if (!success) { NS_ERROR("EGL supports KHR_image(_base) without exposing its functions!"); MarkExtensionUnsupported(KHR_image); MarkExtensionUnsupported(KHR_image_base); MarkExtensionUnsupported(KHR_image_pixmap); mSymbols.fCreateImage = nullptr; mSymbols.fDestroyImage = nullptr; } } else { MarkExtensionUnsupported(KHR_image_pixmap); } mInitialized = true; reporter.SetSuccessful(); return true; }
void SandboxEarlyInit(GeckoProcessType aType, bool aIsNuwa) { // Bug 1168555: Nuwa isn't reliably single-threaded at this point; // it starts an IPC I/O thread and then shuts it down before calling // the plugin-container entry point, but that thread may not have // finished exiting. If/when any type of sandboxing is used for the // Nuwa process (e.g., unsharing the network namespace there instead // of for each content process, to save memory), this will need to be // changed by moving the SandboxEarlyInit call to an earlier point. if (aIsNuwa) { return; } MOZ_RELEASE_ASSERT(IsSingleThreaded()); const SandboxInfo info = SandboxInfo::Get(); // Which kinds of resource isolation (of those that need to be set // up at this point) can be used by this process? bool canChroot = false; bool canUnshareNet = false; bool canUnshareIPC = false; switch (aType) { case GeckoProcessType_Default: MOZ_ASSERT(false, "SandboxEarlyInit in parent process"); return; #ifdef MOZ_GMP_SANDBOX case GeckoProcessType_GMPlugin: if (!info.Test(SandboxInfo::kEnabledForMedia)) { break; } canUnshareNet = true; canUnshareIPC = true; // Need seccomp-bpf to intercept open(). canChroot = info.Test(SandboxInfo::kHasSeccompBPF); break; #endif // In the future, content processes will be able to use some of // these. default: // Other cases intentionally left blank. break; } // If there's nothing to do, then we're done. if (!canChroot && !canUnshareNet && !canUnshareIPC) { return; } { LinuxCapabilities existingCaps; if (existingCaps.GetCurrent() && existingCaps.AnyEffective()) { SANDBOX_LOG_ERROR("PLEASE DO NOT RUN THIS AS ROOT. Strange things may" " happen when capabilities are dropped."); } } // If capabilities can't be gained, then nothing can be done. if (!info.Test(SandboxInfo::kHasUserNamespaces)) { // Drop any existing capabilities; unsharing the user namespace // would implicitly drop them, so if we're running in a broken // configuration where that would matter (e.g., running as root // from a non-root-owned mode-0700 directory) this means it will // break the same way on all kernels and be easier to troubleshoot. LinuxCapabilities().SetCurrent(); return; } // The failure cases for the various unshares, and setting up the // chroot helper, don't strictly need to be fatal -- but they also // shouldn't fail on any reasonable system, so let's take the small // risk of breakage over the small risk of quietly providing less // security than we expect. (Unlike in SandboxInfo, this is in the // child process, so crashing here isn't as severe a response to the // unexpected.) if (!UnshareUserNamespace()) { SANDBOX_LOG_ERROR("unshare(CLONE_NEWUSER): %s", strerror(errno)); // If CanCreateUserNamespace (SandboxInfo.cpp) returns true, then // the unshare shouldn't have failed. MOZ_CRASH("unshare(CLONE_NEWUSER)"); } // No early returns after this point! We need to drop the // capabilities that were gained by unsharing the user namesapce. if (canUnshareIPC && syscall(__NR_unshare, CLONE_NEWIPC) != 0) { SANDBOX_LOG_ERROR("unshare(CLONE_NEWIPC): %s", strerror(errno)); MOZ_CRASH("unshare(CLONE_NEWIPC)"); } if (canUnshareNet && syscall(__NR_unshare, CLONE_NEWNET) != 0) { SANDBOX_LOG_ERROR("unshare(CLONE_NEWNET): %s", strerror(errno)); MOZ_CRASH("unshare(CLONE_NEWNET)"); } if (canChroot) { gChrootHelper = MakeUnique<SandboxChroot>(); if (!gChrootHelper->Prepare()) { SANDBOX_LOG_ERROR("failed to set up chroot helper"); MOZ_CRASH("SandboxChroot::Prepare"); } } if (!LinuxCapabilities().SetCurrent()) { SANDBOX_LOG_ERROR("dropping capabilities: %s", strerror(errno)); MOZ_CRASH("can't drop capabilities"); } }
/* static */ already_AddRefed<CanonicalBrowsingContext> CanonicalBrowsingContext::Get( uint64_t aId) { MOZ_RELEASE_ASSERT(XRE_IsParentProcess()); return BrowsingContext::Get(aId).downcast<CanonicalBrowsingContext>(); }