author | Wes Kocher <wkocher@mozilla.com> |
Fri, 19 Sep 2014 17:25:13 -0700 | |
changeset 206285 | 27253887d2ccaaf1e00b49033a0d8b0efe3b27b6 |
parent 206267 | a85324dfc960d9394bb751515584f37933823e49 (current diff) |
parent 206284 | f23be5f26fbba70fd254c62fb37880575b562dbb (diff) |
child 206286 | 005fcb5b5fb4faad89c9919f8f0238decc2e916a |
child 206304 | d1e5c67ead37c55a83cb8a7e0a32d78e57c8b3ef |
child 206331 | da1f707ddef9164b3aea7499acb2c0226692d7ac |
child 206392 | a634cd133bcbb8b8ab4ce328abebb31d7709e264 |
push id | 27520 |
push user | kwierso@gmail.com |
push date | Sat, 20 Sep 2014 00:25:19 +0000 |
treeherder | mozilla-central@27253887d2cc [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
reviewers | merge |
milestone | 35.0a1 |
first release with | nightly linux32
27253887d2cc
/
35.0a1
/
20140920030206
/
files
nightly linux64
27253887d2cc
/
35.0a1
/
20140920030206
/
files
nightly mac
27253887d2cc
/
35.0a1
/
20140920030206
/
files
nightly win32
27253887d2cc
/
35.0a1
/
20140920030206
/
files
nightly win64
27253887d2cc
/
35.0a1
/
20140920030206
/
files
|
last release without | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
releases | nightly linux32
35.0a1
/
20140920030206
/
pushlog to previous
nightly linux64
35.0a1
/
20140920030206
/
pushlog to previous
nightly mac
35.0a1
/
20140920030206
/
pushlog to previous
nightly win32
35.0a1
/
20140920030206
/
pushlog to previous
nightly win64
35.0a1
/
20140920030206
/
pushlog to previous
|
--- a/content/media/gmp/GMPProcessParent.h +++ b/content/media/gmp/GMPProcessParent.h @@ -5,17 +5,16 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #ifndef GMPProcessParent_h #define GMPProcessParent_h 1 #include "mozilla/Attributes.h" #include "base/basictypes.h" #include "base/file_path.h" -#include "base/scoped_ptr.h" #include "base/thread.h" #include "base/waitable_event.h" #include "chrome/common/child_process_host.h" #include "mozilla/ipc/GeckoChildProcessHost.h" namespace mozilla { namespace gmp {
deleted file mode 100644 --- a/dom/canvas/WebGLBindableName.cpp +++ /dev/null @@ -1,27 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ - -#include "WebGLBindableName.h" -#include "GLConsts.h" -#include "mozilla/Assertions.h" - -using namespace mozilla; - -WebGLBindableName::WebGLBindableName() - : mGLName(LOCAL_GL_NONE) - , mTarget(LOCAL_GL_NONE) -{ } - -void -WebGLBindableName::BindTo(GLenum target) -{ - MOZ_ASSERT(target != LOCAL_GL_NONE, "Can't bind to GL_NONE."); - MOZ_ASSERT(mTarget == LOCAL_GL_NONE || mTarget == target, "Rebinding is illegal."); - - bool targetChanged = (target != mTarget); - mTarget = target; - if (targetChanged) - OnTargetChanged(); -}
--- a/dom/canvas/WebGLBindableName.h +++ b/dom/canvas/WebGLBindableName.h @@ -3,34 +3,56 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #ifndef WEBGLBINDABLENAME_H_ #define WEBGLBINDABLENAME_H_ #include "WebGLTypes.h" +#include "GLDefs.h" +#include "mozilla/TypeTraits.h" +#include "mozilla/Assertions.h" + namespace mozilla { /** Represents a GL name that can be bound to a target. */ +template<typename T> class WebGLBindableName { public: - WebGLBindableName(); - void BindTo(GLenum target); + + WebGLBindableName() + : mGLName(0) + , mTarget(LOCAL_GL_NONE) + { } + + void BindTo(T target) + { + MOZ_ASSERT(target != LOCAL_GL_NONE, "Can't bind to GL_NONE."); + MOZ_ASSERT(!HasEverBeenBound() || mTarget == target, "Rebinding is illegal."); - bool HasEverBeenBound() const { return mTarget != 0; } + bool targetChanged = (target != mTarget); + mTarget = target; + if (targetChanged) + OnTargetChanged(); + } + + bool HasEverBeenBound() const { return mTarget != LOCAL_GL_NONE; } GLuint GLName() const { return mGLName; } - GLenum Target() const { return mTarget; } + T Target() const { + MOZ_ASSERT(HasEverBeenBound()); + return mTarget; + } protected: //! Called after mTarget has been changed by BindTo(target). virtual void OnTargetChanged() {} GLuint mGLName; - GLenum mTarget; + T mTarget; }; } // namespace mozilla #endif // !WEBGLBINDABLENAME_H_
--- a/dom/canvas/WebGLBuffer.cpp +++ b/dom/canvas/WebGLBuffer.cpp @@ -8,17 +8,17 @@ #include "GLContext.h" #include "mozilla/dom/WebGLRenderingContextBinding.h" #include "WebGLContext.h" #include "WebGLElementArrayCache.h" using namespace mozilla; WebGLBuffer::WebGLBuffer(WebGLContext *context) - : WebGLBindableName() + : WebGLBindableName<GLenum>() , WebGLContextBoundObject(context) , mByteLength(0) { SetIsDOMBinding(); mContext->MakeContextCurrent(); mContext->gl->fGenBuffers(1, &mGLName); mContext->mBuffers.insertBack(this); }
--- a/dom/canvas/WebGLBuffer.h +++ b/dom/canvas/WebGLBuffer.h @@ -15,17 +15,17 @@ #include "WebGLTypes.h" namespace mozilla { class WebGLElementArrayCache; class WebGLBuffer MOZ_FINAL : public nsWrapperCache - , public WebGLBindableName + , public WebGLBindableName<GLenum> , public WebGLRefCountedObject<WebGLBuffer> , public LinkedListElement<WebGLBuffer> , public WebGLContextBoundObject { public: explicit WebGLBuffer(WebGLContext* aContext); void Delete();
--- a/dom/canvas/WebGLContext.cpp +++ b/dom/canvas/WebGLContext.cpp @@ -1741,17 +1741,17 @@ WebGLContext::GetSurfaceSnapshot(bool* a void WebGLContext::DidRefresh() { if (gl) { gl->FlushIfHeavyGLCallsSinceLastFlush(); } } -bool WebGLContext::TexImageFromVideoElement(GLenum texImageTarget, GLint level, +bool WebGLContext::TexImageFromVideoElement(const TexImageTarget texImageTarget, GLint level, GLenum internalformat, GLenum format, GLenum type, mozilla::dom::Element& elt) { HTMLVideoElement* video = HTMLVideoElement::FromContentOrNull(&elt); if (!video) { return false; } @@ -1788,19 +1788,19 @@ bool WebGLContext::TexImageFromVideoElem nsRefPtr<mozilla::layers::Image> srcImage = container->LockCurrentImage(); WebGLTexture* tex = activeBoundTextureForTexImageTarget(texImageTarget); const WebGLTexture::ImageInfo& info = tex->ImageInfoAt(texImageTarget, 0); bool dimensionsMatch = info.Width() == srcImage->GetSize().width && info.Height() == srcImage->GetSize().height; if (!dimensionsMatch) { // we need to allocation - gl->fTexImage2D(texImageTarget, level, internalformat, srcImage->GetSize().width, srcImage->GetSize().height, 0, format, type, nullptr); + gl->fTexImage2D(texImageTarget.get(), level, internalformat, srcImage->GetSize().width, srcImage->GetSize().height, 0, format, type, nullptr); } - bool ok = gl->BlitHelper()->BlitImageToTexture(srcImage.get(), srcImage->GetSize(), tex->GLName(), texImageTarget, mPixelStoreFlipY); + bool ok = gl->BlitHelper()->BlitImageToTexture(srcImage.get(), srcImage->GetSize(), tex->GLName(), texImageTarget.get(), mPixelStoreFlipY); if (ok) { tex->SetImageInfo(texImageTarget, level, srcImage->GetSize().width, srcImage->GetSize().height, format, type, WebGLImageDataStatus::InitializedImageData); tex->Bind(TexImageTargetToTexTarget(texImageTarget)); } srcImage = nullptr; container->UnlockCurrentImage(); return ok; }
--- a/dom/canvas/WebGLContext.h +++ b/dom/canvas/WebGLContext.h @@ -12,16 +12,17 @@ #include "mozilla/LinkedList.h" #include "mozilla/UniquePtr.h" #include "mozilla/WeakPtr.h" #include "GLDefs.h" #include "WebGLActiveInfo.h" #include "WebGLObjectModel.h" #include "WebGLRenderbuffer.h" +#include "WebGLStrongTypes.h" #include <stdarg.h> #include "nsTArray.h" #include "nsCycleCollectionNoteChild.h" #include "nsIDOMWebGLRenderingContext.h" #include "nsICanvasRenderingContextInternal.h" #include "mozilla/dom/HTMLCanvasElement.h" @@ -118,17 +119,17 @@ struct WebGLContextOptions { bool depth; bool stencil; bool premultipliedAlpha; bool antialias; bool preserveDrawingBuffer; }; // From WebGLContextUtils -GLenum TexImageTargetToTexTarget(GLenum texImageTarget); +TexTarget TexImageTargetToTexTarget(TexImageTarget texImageTarget); class WebGLContext : public nsIDOMWebGLRenderingContext, public nsICanvasRenderingContextInternal, public nsSupportsWeakReference, public WebGLRectangleObject, public nsWrapperCache, public SupportsWeakPtr<WebGLContext> @@ -219,28 +220,27 @@ public: * keep consistency with how errors are reported from WebGL. */ static const char *EnumName(GLenum glenum); bool IsTextureFormatCompressed(GLenum format); void DummyFramebufferOperation(const char *info); - WebGLTexture* activeBoundTextureForTarget(GLenum texTarget) const { - MOZ_ASSERT(texTarget == LOCAL_GL_TEXTURE_2D || texTarget == LOCAL_GL_TEXTURE_CUBE_MAP); + WebGLTexture* activeBoundTextureForTarget(const TexTarget texTarget) const { return texTarget == LOCAL_GL_TEXTURE_2D ? mBound2DTextures[mActiveTexture] : mBoundCubeMapTextures[mActiveTexture]; } /* Use this function when you have the texture image target, for example: * GL_TEXTURE_2D, GL_TEXTURE_CUBE_MAP_[POSITIVE|NEGATIVE]_[X|Y|Z], and * not the actual texture binding target: GL_TEXTURE_2D or GL_TEXTURE_CUBE_MAP. */ - WebGLTexture* activeBoundTextureForTexImageTarget(GLenum texImgTarget) const { - const GLenum texTarget = TexImageTargetToTexTarget(texImgTarget); + WebGLTexture* activeBoundTextureForTexImageTarget(const TexImageTarget texImgTarget) const { + const TexTarget texTarget = TexImageTargetToTexTarget(texImgTarget); return activeBoundTextureForTarget(texTarget); } already_AddRefed<CanvasLayer> GetCanvasLayer(nsDisplayListBuilder* aBuilder, CanvasLayer *aOldLayer, LayerManager *aManager) MOZ_OVERRIDE; // Note that 'clean' here refers to its invalidation state, not the @@ -460,43 +460,46 @@ public: GLenum type, const Nullable<dom::ArrayBufferView> &pixels, ErrorResult& rv); void TexImage2D(GLenum target, GLint level, GLenum internalformat, GLenum format, GLenum type, dom::ImageData* pixels, ErrorResult& rv); // Allow whatever element types the bindings are willing to pass // us in TexImage2D - bool TexImageFromVideoElement(GLenum texImageTarget, GLint level, + bool TexImageFromVideoElement(TexImageTarget texImageTarget, GLint level, GLenum internalformat, GLenum format, GLenum type, mozilla::dom::Element& image); template<class ElementType> - void TexImage2D(GLenum texImageTarget, GLint level, + void TexImage2D(GLenum rawTexImgTarget, GLint level, GLenum internalformat, GLenum format, GLenum type, ElementType& elt, ErrorResult& rv) { if (IsContextLost()) return; - const GLenum target = TexImageTargetToTexTarget(texImageTarget); - if (target == LOCAL_GL_NONE) - return ErrorInvalidEnumInfo("texImage2D: target", target); + auto dims = 2; + + if (!ValidateTexImageTarget(dims, rawTexImgTarget, WebGLTexImageFunc::TexImage)) + return ErrorInvalidEnumInfo("texSubImage2D: target", rawTexImgTarget); + + const TexImageTarget texImageTarget(rawTexImgTarget); if (!ValidateTexImageFormatAndType(format, type, WebGLTexImageFunc::TexImage)) return; if (level < 0) return ErrorInvalidValue("texImage2D: level is negative"); const int32_t maxLevel = MaxTextureLevelForTexImageTarget(texImageTarget); if (level > maxLevel) return ErrorInvalidValue("texImage2D: level %d is too large, max is %d", level, maxLevel); - WebGLTexture* tex = activeBoundTextureForTarget(target); + WebGLTexture* tex = activeBoundTextureForTexImageTarget(texImageTarget); if (!tex) return ErrorInvalidOperation("no texture is bound to this target"); // Trying to handle the video by GPU directly first if (TexImageFromVideoElement(texImageTarget, level, internalformat, format, type, elt)) { return; } @@ -531,26 +534,27 @@ public: const Nullable<dom::ArrayBufferView> &pixels, ErrorResult& rv); void TexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, GLenum format, GLenum type, dom::ImageData* pixels, ErrorResult& rv); // Allow whatever element types the bindings are willing to pass // us in TexSubImage2D template<class ElementType> - void TexSubImage2D(GLenum texImageTarget, GLint level, + void TexSubImage2D(GLenum rawTexImageTarget, GLint level, GLint xoffset, GLint yoffset, GLenum format, GLenum type, ElementType& elt, ErrorResult& rv) { if (IsContextLost()) return; - const GLenum target = TexImageTargetToTexTarget(texImageTarget); - if (target == LOCAL_GL_NONE) - return ErrorInvalidEnumInfo("texSubImage2D: target", texImageTarget); + if (!ValidateTexImageTarget(2, rawTexImageTarget, WebGLTexImageFunc::TexSubImage)) + return ErrorInvalidEnumInfo("texSubImage2D: target", rawTexImageTarget); + + const TexImageTarget texImageTarget(rawTexImageTarget); if (!ValidateTexImageFormatAndType(format, type, WebGLTexImageFunc::TexImage)) return; if (level < 0) return ErrorInvalidValue("texSubImage2D: level is negative"); const int32_t maxLevel = MaxTextureLevelForTexImageTarget(texImageTarget); @@ -1083,35 +1087,35 @@ protected: bool ValidateAttribIndex(GLuint index, const char *info); bool ValidateStencilParamsForDrawCall(); bool ValidateGLSLVariableName(const nsAString& name, const char *info); bool ValidateGLSLCharacter(char16_t c); bool ValidateGLSLString(const nsAString& string, const char *info); bool ValidateCopyTexImage(GLenum format, WebGLTexImageFunc func); - bool ValidateTexImage(GLuint dims, GLenum target, + bool ValidateTexImage(GLuint dims, TexImageTarget texImageTarget, GLint level, GLint internalFormat, GLint xoffset, GLint yoffset, GLint zoffset, GLint width, GLint height, GLint depth, GLint border, GLenum format, GLenum type, WebGLTexImageFunc func); bool ValidateTexImageTarget(GLuint dims, GLenum target, WebGLTexImageFunc func); bool ValidateTexImageFormat(GLenum format, WebGLTexImageFunc func); bool ValidateTexImageType(GLenum type, WebGLTexImageFunc func); bool ValidateTexImageFormatAndType(GLenum format, GLenum type, WebGLTexImageFunc func); - bool ValidateTexImageSize(GLenum target, GLint level, + bool ValidateTexImageSize(TexImageTarget target, GLint level, GLint width, GLint height, GLint depth, WebGLTexImageFunc func); bool ValidateTexSubImageSize(GLint x, GLint y, GLint z, GLsizei width, GLsizei height, GLsizei depth, GLsizei baseWidth, GLsizei baseHeight, GLsizei baseDepth, WebGLTexImageFunc func); - bool ValidateCompTexImageSize(GLenum target, GLint level, GLenum format, + bool ValidateCompTexImageSize(GLint level, GLenum format, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLsizei levelWidth, GLsizei levelHeight, WebGLTexImageFunc func); bool ValidateCompTexImageDataSize(GLint level, GLenum format, GLsizei width, GLsizei height, uint32_t byteLength, WebGLTexImageFunc func); @@ -1119,23 +1123,23 @@ protected: static uint32_t GetBitsPerTexel(GLenum format, GLenum type); void Invalidate(); void DestroyResourcesAndContext(); void MakeContextCurrent() const; // helpers - void TexImage2D_base(GLenum target, GLint level, GLenum internalformat, + void TexImage2D_base(TexImageTarget target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLsizei srcStrideOrZero, GLint border, GLenum format, GLenum type, void *data, uint32_t byteLength, int jsArrayType, WebGLTexelFormat srcFormat, bool srcPremultiplied); - void TexSubImage2D_base(GLenum target, GLint level, + void TexSubImage2D_base(TexImageTarget target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLsizei srcStrideOrZero, GLenum format, GLenum type, void *pixels, uint32_t byteLength, int jsArrayType, WebGLTexelFormat srcFormat, bool srcPremultiplied); void TexParameter_base(GLenum target, GLenum pname, GLint *intParamPtr, GLfloat *floatParamPtr); @@ -1163,17 +1167,17 @@ protected: { return SurfaceFromElement(&aElement); } nsresult SurfaceFromElementResultToImageSurface(nsLayoutUtils::SurfaceFromElementResult& res, RefPtr<gfx::DataSourceSurface>& imageOut, WebGLTexelFormat *format); - void CopyTexSubImage2D_base(GLenum target, + void CopyTexSubImage2D_base(TexImageTarget texImageTarget, GLint level, GLenum internalformat, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, @@ -1195,39 +1199,34 @@ protected: bool ValidateObjectAllowDeleted(const char* info, ObjectType *aObject); private: // Like ValidateObject, but only for cases when aObject is known // to not be null already. template<class ObjectType> bool ValidateObjectAssumeNonNull(const char* info, ObjectType *aObject); protected: - int32_t MaxTextureSizeForTarget(GLenum target) const { - MOZ_ASSERT(target == LOCAL_GL_TEXTURE_2D || - (target >= LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X && - target <= LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z), - "Invalid target enum"); + int32_t MaxTextureSizeForTarget(TexTarget target) const { return (target == LOCAL_GL_TEXTURE_2D) ? mGLMaxTextureSize : mGLMaxCubeMapTextureSize; } - int32_t MaxTextureLevelForTexImageTarget(GLenum texImageTarget) const { - const GLenum target = TexImageTargetToTexTarget(texImageTarget); - MOZ_ASSERT(target == LOCAL_GL_TEXTURE_2D || target == LOCAL_GL_TEXTURE_CUBE_MAP); + int32_t MaxTextureLevelForTexImageTarget(TexImageTarget texImageTarget) const { + const TexTarget target = TexImageTargetToTexTarget(texImageTarget); return (target == LOCAL_GL_TEXTURE_2D) ? mGLMaxTextureSizeLog2 : mGLMaxCubeMapTextureSizeLog2; } /** like glBufferData but if the call may change the buffer size, checks any GL error generated * by this glBufferData call and returns it */ GLenum CheckedBufferData(GLenum target, GLsizeiptr size, const GLvoid *data, GLenum usage); /** like glTexImage2D but if the call may change the texture size, checks any GL error generated * by this glTexImage2D call and returns it */ - GLenum CheckedTexImage2D(GLenum target, + GLenum CheckedTexImage2D(TexImageTarget texImageTarget, GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, const GLvoid *data);
--- a/dom/canvas/WebGLContextGL.cpp +++ b/dom/canvas/WebGLContextGL.cpp @@ -210,46 +210,49 @@ WebGLContext::BindRenderbuffer(GLenum ta } else { gl->fBindRenderbuffer(target, 0); } mBoundRenderbuffer = wrb; } void -WebGLContext::BindTexture(GLenum target, WebGLTexture *newTex) +WebGLContext::BindTexture(GLenum rawTarget, WebGLTexture *newTex) { if (IsContextLost()) return; if (!ValidateObjectAllowDeletedOrNull("bindTexture", newTex)) return; - if (newTex) { - // silently ignore a deleted texture - if (newTex->IsDeleted()) - return; - - if (newTex->Target() != LOCAL_GL_NONE && newTex->Target() != target) - return ErrorInvalidOperation("bindTexture: this texture has already been bound to a different target"); - } - + // Need to check rawTarget first before comparing against newTex->Target() as + // newTex->Target() returns a TexTarget, which will assert on invalid value. WebGLRefPtr<WebGLTexture>* currentTexPtr = nullptr; - - switch (target) { + switch (rawTarget) { case LOCAL_GL_TEXTURE_2D: currentTexPtr = &mBound2DTextures[mActiveTexture]; break; case LOCAL_GL_TEXTURE_CUBE_MAP: currentTexPtr = &mBoundCubeMapTextures[mActiveTexture]; break; default: - return ErrorInvalidEnumInfo("bindTexture: target", target); + return ErrorInvalidEnumInfo("bindTexture: target", rawTarget); } + if (newTex) { + // silently ignore a deleted texture + if (newTex->IsDeleted()) + return; + + if (newTex->HasEverBeenBound() && newTex->Target() != rawTarget) + return ErrorInvalidOperation("bindTexture: this texture has already been bound to a different target"); + } + + const TexTarget target(rawTarget); + WebGLTextureFakeBlackStatus currentTexFakeBlackStatus = WebGLTextureFakeBlackStatus::NotNeeded; if (*currentTexPtr) { currentTexFakeBlackStatus = (*currentTexPtr)->ResolvedFakeBlackStatus(); } WebGLTextureFakeBlackStatus newTexFakeBlackStatus = WebGLTextureFakeBlackStatus::NotNeeded; if (newTex) { newTexFakeBlackStatus = newTex->ResolvedFakeBlackStatus(); } @@ -260,17 +263,17 @@ WebGLContext::BindTexture(GLenum target, SetFakeBlackStatus(WebGLContextFakeBlackStatus::Unknown); } MakeContextCurrent(); if (newTex) newTex->Bind(target); else - gl->fBindTexture(target, 0 /* == texturename */); + gl->fBindTexture(target.get(), 0 /* == texturename */); } void WebGLContext::BlendEquation(GLenum mode) { if (IsContextLost()) return; if (!ValidateBlendEquationEnum(mode, "blendEquation: mode")) @@ -344,17 +347,17 @@ WebGLContext::CheckFramebufferStatus(GLe if (!mBoundFramebuffer) return LOCAL_GL_FRAMEBUFFER_COMPLETE; return mBoundFramebuffer->CheckFramebufferStatus(); } void -WebGLContext::CopyTexSubImage2D_base(GLenum target, +WebGLContext::CopyTexSubImage2D_base(TexImageTarget texImageTarget, GLint level, GLenum internalformat, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, @@ -364,43 +367,43 @@ WebGLContext::CopyTexSubImage2D_base(GLe GLsizei framebufferWidth = framebufferRect ? framebufferRect->Width() : 0; GLsizei framebufferHeight = framebufferRect ? framebufferRect->Height() : 0; const char* info = sub ? "copyTexSubImage2D" : "copyTexImage2D"; WebGLTexImageFunc func = sub ? WebGLTexImageFunc::CopyTexSubImage : WebGLTexImageFunc::CopyTexImage; // TODO: This changes with color_buffer_float. Reassess when the // patch lands. - if (!ValidateTexImage(2, target, level, internalformat, + if (!ValidateTexImage(2, texImageTarget, level, internalformat, xoffset, yoffset, 0, width, height, 0, 0, internalformat, LOCAL_GL_UNSIGNED_BYTE, func)) { return; } if (!ValidateCopyTexImage(internalformat, func)) return; if (!mBoundFramebuffer) ClearBackbufferIfNeeded(); MakeContextCurrent(); - WebGLTexture *tex = activeBoundTextureForTexImageTarget(target); + WebGLTexture *tex = activeBoundTextureForTexImageTarget(texImageTarget); if (!tex) return ErrorInvalidOperation("%s: no texture is bound to this target"); if (CanvasUtils::CheckSaneSubrectSize(x, y, width, height, framebufferWidth, framebufferHeight)) { if (sub) - gl->fCopyTexSubImage2D(target, level, xoffset, yoffset, x, y, width, height); + gl->fCopyTexSubImage2D(texImageTarget.get(), level, xoffset, yoffset, x, y, width, height); else - gl->fCopyTexImage2D(target, level, internalformat, x, y, width, height, 0); + gl->fCopyTexImage2D(texImageTarget.get(), level, internalformat, x, y, width, height, 0); } else { // the rect doesn't fit in the framebuffer /*** first, we initialize the texture as black ***/ // first, compute the size of the buffer we should allocate to initialize the texture as black @@ -424,20 +427,20 @@ WebGLContext::CopyTexSubImage2D_base(GLe // Hopefully calloc will just mmap zero pages here. void* tempZeroData = calloc(1, bytesNeeded); if (!tempZeroData) return ErrorOutOfMemory("%s: could not allocate %d bytes (for zero fill)", info, bytesNeeded); // now initialize the texture as black if (sub) - gl->fTexSubImage2D(target, level, 0, 0, width, height, + gl->fTexSubImage2D(texImageTarget.get(), level, 0, 0, width, height, internalformat, LOCAL_GL_UNSIGNED_BYTE, tempZeroData); else - gl->fTexImage2D(target, level, internalformat, width, height, + gl->fTexImage2D(texImageTarget.get(), level, internalformat, width, height, 0, internalformat, LOCAL_GL_UNSIGNED_BYTE, tempZeroData); free(tempZeroData); // if we are completely outside of the framebuffer, we can exit now with our black texture if ( x >= framebufferWidth || x+width <= 0 || y >= framebufferHeight || y+height <= 0) @@ -451,146 +454,153 @@ WebGLContext::CopyTexSubImage2D_base(GLe GLsizei actual_width = actual_x_plus_width - actual_x; GLint actual_xoffset = xoffset + actual_x - x; GLint actual_y = clamped(y, 0, framebufferHeight); GLint actual_y_plus_height = clamped(y + height, 0, framebufferHeight); GLsizei actual_height = actual_y_plus_height - actual_y; GLint actual_yoffset = yoffset + actual_y - y; - gl->fCopyTexSubImage2D(target, level, actual_xoffset, actual_yoffset, actual_x, actual_y, actual_width, actual_height); + gl->fCopyTexSubImage2D(texImageTarget.get(), level, actual_xoffset, actual_yoffset, actual_x, actual_y, actual_width, actual_height); } } void -WebGLContext::CopyTexImage2D(GLenum target, +WebGLContext::CopyTexImage2D(GLenum rawTexImgTarget, GLint level, GLenum internalformat, GLint x, GLint y, GLsizei width, GLsizei height, GLint border) { if (IsContextLost()) return; // copyTexImage2D only generates textures with type = UNSIGNED_BYTE const WebGLTexImageFunc func = WebGLTexImageFunc::CopyTexImage; const GLenum format = internalformat; // WebGL/ES Format const GLenum type = LOCAL_GL_UNSIGNED_BYTE; // WebGL/ES Format - if (!ValidateTexImage(2, target, level, format, + if (!ValidateTexImageTarget(2, rawTexImgTarget, WebGLTexImageFunc::CopyTexImage)) + return; + + if (!ValidateTexImage(2, rawTexImgTarget, level, format, 0, 0, 0, width, height, 0, border, format, type, func)) { return; } if (!ValidateCopyTexImage(format, func)) return; if (!mBoundFramebuffer) ClearBackbufferIfNeeded(); + const TexImageTarget texImageTarget(rawTexImgTarget); + // check if the memory size of this texture may change with this call bool sizeMayChange = true; - WebGLTexture* tex = activeBoundTextureForTexImageTarget(target); - if (tex->HasImageInfoAt(target, level)) { - const WebGLTexture::ImageInfo& imageInfo = tex->ImageInfoAt(target, level); + WebGLTexture* tex = activeBoundTextureForTexImageTarget(texImageTarget); + if (tex->HasImageInfoAt(texImageTarget, level)) { + const WebGLTexture::ImageInfo& imageInfo = tex->ImageInfoAt(texImageTarget, level); sizeMayChange = width != imageInfo.Width() || height != imageInfo.Height() || format != imageInfo.WebGLFormat() || type != imageInfo.WebGLType(); } if (sizeMayChange) GetAndFlushUnderlyingGLErrors(); - CopyTexSubImage2D_base(target, level, format, 0, 0, x, y, width, height, false); + CopyTexSubImage2D_base(texImageTarget, level, format, 0, 0, x, y, width, height, false); if (sizeMayChange) { GLenum error = GetAndFlushUnderlyingGLErrors(); if (error) { GenerateWarning("copyTexImage2D generated error %s", ErrorName(error)); return; } } - tex->SetImageInfo(target, level, width, height, format, type, + tex->SetImageInfo(texImageTarget, level, width, height, format, type, WebGLImageDataStatus::InitializedImageData); } void -WebGLContext::CopyTexSubImage2D(GLenum target, +WebGLContext::CopyTexSubImage2D(GLenum rawTexImgTarget, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height) { if (IsContextLost()) return; - switch (target) { + switch (rawTexImgTarget) { case LOCAL_GL_TEXTURE_2D: case LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X: case LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_X: case LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_Y: case LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Y: case LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_Z: case LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z: break; default: - return ErrorInvalidEnumInfo("copyTexSubImage2D: target", target); + return ErrorInvalidEnumInfo("copyTexSubImage2D: target", rawTexImgTarget); } + const TexImageTarget texImageTarget(rawTexImgTarget); + if (level < 0) return ErrorInvalidValue("copyTexSubImage2D: level may not be negative"); - GLsizei maxTextureSize = MaxTextureSizeForTarget(target); + GLsizei maxTextureSize = MaxTextureSizeForTarget(TexImageTargetToTexTarget(texImageTarget)); if (!(maxTextureSize >> level)) return ErrorInvalidValue("copyTexSubImage2D: 2^level exceeds maximum texture size"); if (width < 0 || height < 0) return ErrorInvalidValue("copyTexSubImage2D: width and height may not be negative"); if (xoffset < 0 || yoffset < 0) return ErrorInvalidValue("copyTexSubImage2D: xoffset and yoffset may not be negative"); - WebGLTexture *tex = activeBoundTextureForTexImageTarget(target); + WebGLTexture *tex = activeBoundTextureForTexImageTarget(texImageTarget); if (!tex) return ErrorInvalidOperation("copyTexSubImage2D: no texture bound to this target"); - if (!tex->HasImageInfoAt(target, level)) + if (!tex->HasImageInfoAt(texImageTarget, level)) return ErrorInvalidOperation("copyTexSubImage2D: no texture image previously defined for this level and face"); - const WebGLTexture::ImageInfo &imageInfo = tex->ImageInfoAt(target, level); + const WebGLTexture::ImageInfo &imageInfo = tex->ImageInfoAt(texImageTarget, level); GLsizei texWidth = imageInfo.Width(); GLsizei texHeight = imageInfo.Height(); if (xoffset + width > texWidth || xoffset + width < 0) return ErrorInvalidValue("copyTexSubImage2D: xoffset+width is too large"); if (yoffset + height > texHeight || yoffset + height < 0) return ErrorInvalidValue("copyTexSubImage2D: yoffset+height is too large"); if (!mBoundFramebuffer) ClearBackbufferIfNeeded(); if (imageInfo.HasUninitializedImageData()) { - tex->DoDeferredImageInitialization(target, level); + tex->DoDeferredImageInitialization(texImageTarget, level); } - return CopyTexSubImage2D_base(target, level, imageInfo.WebGLFormat(), xoffset, yoffset, x, y, width, height, true); + return CopyTexSubImage2D_base(texImageTarget, level, imageInfo.WebGLFormat(), xoffset, yoffset, x, y, width, height, true); } already_AddRefed<WebGLProgram> WebGLContext::CreateProgram() { if (IsContextLost()) return nullptr; @@ -687,21 +697,21 @@ WebGLContext::DeleteTexture(WebGLTexture if (mBoundFramebuffer) mBoundFramebuffer->DetachTexture(tex); // Invalidate framebuffer status cache tex->NotifyFBsStatusChanged(); GLuint activeTexture = mActiveTexture; for (int32_t i = 0; i < mGLMaxTextureUnits; i++) { - if ((tex->Target() == LOCAL_GL_TEXTURE_2D && mBound2DTextures[i] == tex) || - (tex->Target() == LOCAL_GL_TEXTURE_CUBE_MAP && mBoundCubeMapTextures[i] == tex)) + if ((mBound2DTextures[i] == tex && tex->Target() == LOCAL_GL_TEXTURE_2D) || + (mBoundCubeMapTextures[i] == tex && tex->Target() == LOCAL_GL_TEXTURE_CUBE_MAP)) { ActiveTexture(LOCAL_GL_TEXTURE0 + i); - BindTexture(tex->Target(), static_cast<WebGLTexture*>(nullptr)); + BindTexture(tex->Target().get(), static_cast<WebGLTexture*>(nullptr)); } } ActiveTexture(LOCAL_GL_TEXTURE0 + activeTexture); tex->RequestDelete(); } void @@ -796,17 +806,24 @@ WebGLContext::FramebufferTexture2D(GLenu GLint level) { if (IsContextLost()) return; if (!mBoundFramebuffer) return ErrorInvalidOperation("framebufferRenderbuffer: cannot modify framebuffer 0"); - return mBoundFramebuffer->FramebufferTexture2D(target, attachment, textarget, tobj, level); + if (textarget != LOCAL_GL_TEXTURE_2D && + (textarget < LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X || + textarget > LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z)) + { + return ErrorInvalidEnumInfo("framebufferTexture2D: invalid texture target", textarget); + } + + return mBoundFramebuffer->FramebufferTexture2D(target, attachment, TexImageTarget(textarget), tobj, level); } void WebGLContext::FrontFace(GLenum mode) { if (IsContextLost()) return; @@ -852,31 +869,34 @@ WebGLContext::GetActiveAttrib(WebGLProgr prog->ReverseMapIdentifier(nsDependentCString(name), &reverseMappedName); nsRefPtr<WebGLActiveInfo> retActiveInfo = new WebGLActiveInfo(attrsize, attrtype, reverseMappedName); return retActiveInfo.forget(); } void -WebGLContext::GenerateMipmap(GLenum target) +WebGLContext::GenerateMipmap(GLenum rawTarget) { if (IsContextLost()) return; - if (!ValidateTextureTargetEnum(target, "generateMipmap")) + if (!ValidateTextureTargetEnum(rawTarget, "generateMipmap")) return; + const TexTarget target(rawTarget); + WebGLTexture *tex = activeBoundTextureForTarget(target); if (!tex) return ErrorInvalidOperation("generateMipmap: No texture is bound to this target."); - GLenum imageTarget = (target == LOCAL_GL_TEXTURE_2D) ? LOCAL_GL_TEXTURE_2D - : LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X; + const TexImageTarget imageTarget = (target == LOCAL_GL_TEXTURE_2D) + ? LOCAL_GL_TEXTURE_2D + : LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X; if (!tex->HasImageInfoAt(imageTarget, 0)) { return ErrorInvalidOperation("generateMipmap: Level zero of texture is not defined."); } if (!tex->IsFirstImagePowerOfTwo()) return ErrorInvalidOperation("generateMipmap: Level zero of texture does not have power-of-two width and height."); @@ -900,21 +920,21 @@ WebGLContext::GenerateMipmap(GLenum targ MakeContextCurrent(); if (gl->WorkAroundDriverBugs()) { // bug 696495 - to work around failures in the texture-mips.html test on various drivers, we // set the minification filter before calling glGenerateMipmap. This should not carry a significant performance // overhead so we do it unconditionally. // // note that the choice of GL_NEAREST_MIPMAP_NEAREST really matters. See Chromium bug 101105. - gl->fTexParameteri(target, LOCAL_GL_TEXTURE_MIN_FILTER, LOCAL_GL_NEAREST_MIPMAP_NEAREST); - gl->fGenerateMipmap(target); - gl->fTexParameteri(target, LOCAL_GL_TEXTURE_MIN_FILTER, tex->MinFilter()); + gl->fTexParameteri(target.get(), LOCAL_GL_TEXTURE_MIN_FILTER, LOCAL_GL_NEAREST_MIPMAP_NEAREST); + gl->fGenerateMipmap(target.get()); + gl->fTexParameteri(target.get(), LOCAL_GL_TEXTURE_MIN_FILTER, tex->MinFilter()); } else { - gl->fGenerateMipmap(target); + gl->fGenerateMipmap(target.get()); } } already_AddRefed<WebGLActiveInfo> WebGLContext::GetActiveUniform(WebGLProgram *prog, uint32_t index) { if (IsContextLost()) return nullptr; @@ -1168,20 +1188,20 @@ WebGLContext::GetFramebufferAttachmentPa case LOCAL_GL_FRAMEBUFFER_ATTACHMENT_OBJECT_TYPE: return JS::NumberValue(uint32_t(LOCAL_GL_TEXTURE)); case LOCAL_GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME: return WebGLObjectAsJSValue(cx, fba.Texture(), rv); case LOCAL_GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_LEVEL: - return JS::Int32Value(fba.TexImageLevel()); + return JS::Int32Value(fba.MipLevel()); case LOCAL_GL_FRAMEBUFFER_ATTACHMENT_TEXTURE_CUBE_MAP_FACE: { - GLenum face = fba.TexImageTarget(); + GLenum face = fba.ImageTarget().get(); if (face == LOCAL_GL_TEXTURE_2D) face = 0; return JS::Int32Value(face); } case LOCAL_GL_FRAMEBUFFER_ATTACHMENT_COMPONENT_TYPE: { if (!IsExtensionEnabled(WebGLExtensionID::EXT_color_buffer_half_float) && !IsExtensionEnabled(WebGLExtensionID::WEBGL_color_buffer_float)) @@ -1194,18 +1214,18 @@ WebGLContext::GetFramebufferAttachmentPa " type of depth-stencil attachments."); return JS::NullValue(); } if (!fba.IsComplete()) return JS::NumberValue(uint32_t(LOCAL_GL_NONE)); uint32_t ret = LOCAL_GL_NONE; - GLenum type = fba.Texture()->ImageInfoAt(fba.TexImageTarget(), - fba.TexImageLevel()).WebGLType(); + GLenum type = fba.Texture()->ImageInfoAt(fba.ImageTarget(), + fba.MipLevel()).WebGLType(); switch (type) { case LOCAL_GL_UNSIGNED_BYTE: case LOCAL_GL_UNSIGNED_SHORT_4_4_4_4: case LOCAL_GL_UNSIGNED_SHORT_5_5_5_1: case LOCAL_GL_UNSIGNED_SHORT_5_6_5: ret = LOCAL_GL_UNSIGNED_NORMALIZED; break; case LOCAL_GL_FLOAT: @@ -1440,32 +1460,34 @@ WebGLContext::GetProgramInfoLog(WebGLPro retval.SetCapacity(k); gl->fGetProgramInfoLog(progname, k, &k, (char*) retval.BeginWriting()); retval.SetLength(k); } // here we have to support all pnames with both int and float params. // See this discussion: // https://www.khronos.org/webgl/public-mailing-list/archives/1008/msg00014.html -void WebGLContext::TexParameter_base(GLenum target, GLenum pname, +void WebGLContext::TexParameter_base(GLenum rawTarget, GLenum pname, GLint *intParamPtr, GLfloat *floatParamPtr) { MOZ_ASSERT(intParamPtr || floatParamPtr); if (IsContextLost()) return; GLint intParam = intParamPtr ? *intParamPtr : GLint(*floatParamPtr); GLfloat floatParam = floatParamPtr ? *floatParamPtr : GLfloat(*intParamPtr); - if (!ValidateTextureTargetEnum(target, "texParameter: target")) + if (!ValidateTextureTargetEnum(rawTarget, "texParameter: target")) return; - WebGLTexture *tex = activeBoundTextureForTarget(target); + const TexTarget texTarget = TexTarget(rawTarget); + + WebGLTexture *tex = activeBoundTextureForTarget(texTarget); if (!tex) return ErrorInvalidOperation("texParameter: no texture is bound to this target"); bool pnameAndParamAreIncompatible = false; bool paramValueInvalid = false; switch (pname) { case LOCAL_GL_TEXTURE_MIN_FILTER: @@ -1541,51 +1563,53 @@ void WebGLContext::TexParameter_base(GLe pname, intParam, intParam); else return ErrorInvalidValue("texParameterf: pname %x and param %g is invalid", pname, floatParam); } MakeContextCurrent(); if (intParamPtr) - gl->fTexParameteri(target, pname, intParam); + gl->fTexParameteri(texTarget.get(), pname, intParam); else - gl->fTexParameterf(target, pname, floatParam); + gl->fTexParameterf(texTarget.get(), pname, floatParam); } JS::Value -WebGLContext::GetTexParameter(GLenum target, GLenum pname) +WebGLContext::GetTexParameter(GLenum rawTarget, GLenum pname) { if (IsContextLost()) return JS::NullValue(); MakeContextCurrent(); - if (!ValidateTextureTargetEnum(target, "getTexParameter: target")) + if (!ValidateTextureTargetEnum(rawTarget, "getTexParameter: target")) return JS::NullValue(); + const TexTarget target(rawTarget); + if (!activeBoundTextureForTarget(target)) { ErrorInvalidOperation("getTexParameter: no texture bound"); return JS::NullValue(); } switch (pname) { case LOCAL_GL_TEXTURE_MIN_FILTER: case LOCAL_GL_TEXTURE_MAG_FILTER: case LOCAL_GL_TEXTURE_WRAP_S: case LOCAL_GL_TEXTURE_WRAP_T: { GLint i = 0; - gl->fGetTexParameteriv(target, pname, &i); + gl->fGetTexParameteriv(target.get(), pname, &i); return JS::NumberValue(uint32_t(i)); } case LOCAL_GL_TEXTURE_MAX_ANISOTROPY_EXT: if (IsExtensionEnabled(WebGLExtensionID::EXT_texture_filter_anisotropic)) { GLfloat f = 0.f; - gl->fGetTexParameterfv(target, pname, &f); + gl->fGetTexParameterfv(target.get(), pname, &f); return JS::DoubleValue(f); } ErrorInvalidEnumInfo("getTexParameter: parameter", pname); break; default: ErrorInvalidEnumInfo("getTexParameter: parameter", pname); @@ -3270,98 +3294,107 @@ WebGLContext::CompileShader(WebGLShader gl->fCompileShader(shadername); GLint ok; gl->fGetShaderiv(shadername, LOCAL_GL_COMPILE_STATUS, &ok); shader->SetCompileStatus(ok); } void -WebGLContext::CompressedTexImage2D(GLenum target, GLint level, GLenum internalformat, +WebGLContext::CompressedTexImage2D(GLenum rawTexImgTarget, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLint border, const ArrayBufferView& view) { if (IsContextLost()) return; const WebGLTexImageFunc func = WebGLTexImageFunc::CompTexImage; - if (!ValidateTexImage(2, target, level, internalformat, + if (!ValidateTexImageTarget(2, rawTexImgTarget, WebGLTexImageFunc::CompTexImage)) + return; + + if (!ValidateTexImage(2, rawTexImgTarget, level, internalformat, 0, 0, 0, width, height, 0, border, internalformat, LOCAL_GL_UNSIGNED_BYTE, func)) { return; } view.ComputeLengthAndData(); uint32_t byteLength = view.Length(); - if (!ValidateCompTexImageDataSize(target, internalformat, width, height, byteLength, func)) { + if (!ValidateCompTexImageDataSize(level, internalformat, width, height, byteLength, func)) { return; } - if (!ValidateCompTexImageSize(target, level, internalformat, 0, 0, - width, height, width, height, func)) + if (!ValidateCompTexImageSize(level, internalformat, 0, 0, width, height, width, height, func)) { return; } + const TexImageTarget texImageTarget(rawTexImgTarget); + MakeContextCurrent(); - gl->fCompressedTexImage2D(target, level, internalformat, width, height, border, byteLength, view.Data()); - WebGLTexture* tex = activeBoundTextureForTexImageTarget(target); + gl->fCompressedTexImage2D(texImageTarget.get(), level, internalformat, width, height, border, byteLength, view.Data()); + WebGLTexture* tex = activeBoundTextureForTexImageTarget(texImageTarget); MOZ_ASSERT(tex); - tex->SetImageInfo(target, level, width, height, internalformat, LOCAL_GL_UNSIGNED_BYTE, + tex->SetImageInfo(texImageTarget, level, width, height, internalformat, LOCAL_GL_UNSIGNED_BYTE, WebGLImageDataStatus::InitializedImageData); } void -WebGLContext::CompressedTexSubImage2D(GLenum target, GLint level, GLint xoffset, +WebGLContext::CompressedTexSubImage2D(GLenum rawTexImgTarget, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, const ArrayBufferView& view) { if (IsContextLost()) return; const WebGLTexImageFunc func = WebGLTexImageFunc::CompTexSubImage; - if (!ValidateTexImage(2, target, + if (!ValidateTexImageTarget(2, rawTexImgTarget, WebGLTexImageFunc::CompTexSubImage)) + return; + + if (!ValidateTexImage(2, rawTexImgTarget, level, format, xoffset, yoffset, 0, width, height, 0, 0, format, LOCAL_GL_UNSIGNED_BYTE, func)) { return; } - WebGLTexture *tex = activeBoundTextureForTexImageTarget(target); + const TexImageTarget texImageTarget(rawTexImgTarget); + + WebGLTexture *tex = activeBoundTextureForTexImageTarget(texImageTarget); MOZ_ASSERT(tex); - WebGLTexture::ImageInfo& levelInfo = tex->ImageInfoAt(target, level); + WebGLTexture::ImageInfo& levelInfo = tex->ImageInfoAt(texImageTarget, level); view.ComputeLengthAndData(); uint32_t byteLength = view.Length(); - if (!ValidateCompTexImageDataSize(target, format, width, height, byteLength, func)) + if (!ValidateCompTexImageDataSize(level, format, width, height, byteLength, func)) return; - if (!ValidateCompTexImageSize(target, level, format, + if (!ValidateCompTexImageSize(level, format, xoffset, yoffset, width, height, levelInfo.Width(), levelInfo.Height(), func)) { return; } if (levelInfo.HasUninitializedImageData()) - tex->DoDeferredImageInitialization(target, level); + tex->DoDeferredImageInitialization(texImageTarget, level); MakeContextCurrent(); - gl->fCompressedTexSubImage2D(target, level, xoffset, yoffset, width, height, format, byteLength, view.Data()); + gl->fCompressedTexSubImage2D(texImageTarget.get(), level, xoffset, yoffset, width, height, format, byteLength, view.Data()); } JS::Value WebGLContext::GetShaderParameter(WebGLShader *shader, GLenum pname) { if (IsContextLost()) return JS::NullValue(); @@ -3538,72 +3571,72 @@ WebGLContext::GetShaderTranslatedSource( } if (!ValidateObject("getShaderTranslatedSource: shader", shader)) return; retval.Assign(shader->TranslatedSource()); } -GLenum WebGLContext::CheckedTexImage2D(GLenum target, +GLenum WebGLContext::CheckedTexImage2D(TexImageTarget texImageTarget, GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, const GLvoid *data) { MOZ_ASSERT(internalFormat == format); - WebGLTexture *tex = activeBoundTextureForTexImageTarget(target); + WebGLTexture *tex = activeBoundTextureForTexImageTarget(texImageTarget); MOZ_ASSERT(tex != nullptr, "no texture bound"); bool sizeMayChange = true; - if (tex->HasImageInfoAt(target, level)) { - const WebGLTexture::ImageInfo& imageInfo = tex->ImageInfoAt(target, level); + if (tex->HasImageInfoAt(texImageTarget, level)) { + const WebGLTexture::ImageInfo& imageInfo = tex->ImageInfoAt(texImageTarget, level); sizeMayChange = width != imageInfo.Width() || height != imageInfo.Height() || format != imageInfo.WebGLFormat() || type != imageInfo.WebGLType(); } // Convert to format and type required by OpenGL 'driver'. GLenum driverType = DriverTypeFromType(gl, type); GLenum driverInternalFormat = LOCAL_GL_NONE; GLenum driverFormat = LOCAL_GL_NONE; DriverFormatsFromFormatAndType(gl, format, type, &driverInternalFormat, &driverFormat); if (sizeMayChange) { GetAndFlushUnderlyingGLErrors(); } - gl->fTexImage2D(target, level, driverInternalFormat, width, height, border, driverFormat, driverType, data); + gl->fTexImage2D(texImageTarget.get(), level, driverInternalFormat, width, height, border, driverFormat, driverType, data); GLenum error = LOCAL_GL_NO_ERROR; if (sizeMayChange) { error = GetAndFlushUnderlyingGLErrors(); } return error; } void -WebGLContext::TexImage2D_base(GLenum target, GLint level, GLenum internalformat, +WebGLContext::TexImage2D_base(TexImageTarget texImageTarget, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLsizei srcStrideOrZero, GLint border, GLenum format, GLenum type, void* data, uint32_t byteLength, int jsArrayType, // a TypedArray format enum, or -1 if not relevant WebGLTexelFormat srcFormat, bool srcPremultiplied) { const WebGLTexImageFunc func = WebGLTexImageFunc::TexImage; - if (!ValidateTexImage(2, target, level, internalformat, + if (!ValidateTexImage(2, texImageTarget, level, internalformat, 0, 0, 0, width, height, 0, border, format, type, func)) { return; } const bool isDepthTexture = format == LOCAL_GL_DEPTH_COMPONENT || @@ -3636,17 +3669,17 @@ WebGLContext::TexImage2D_base(GLenum tar return ErrorInvalidOperation("texImage2D: integer overflow computing the needed buffer size"); uint32_t bytesNeeded = checked_neededByteLength.value(); if (byteLength && byteLength < bytesNeeded) return ErrorInvalidOperation("texImage2D: not enough data for operation (need %d, have %d)", bytesNeeded, byteLength); - WebGLTexture *tex = activeBoundTextureForTexImageTarget(target); + WebGLTexture *tex = activeBoundTextureForTexImageTarget(texImageTarget); if (!tex) return ErrorInvalidOperation("texImage2D: no texture is bound to this target"); MakeContextCurrent(); nsAutoArrayPtr<uint8_t> convertedData; void* pixels = nullptr; @@ -3675,34 +3708,34 @@ WebGLContext::TexImage2D_base(GLenum tar static_cast<uint8_t*>(data), convertedData, actualSrcFormat, srcPremultiplied, dstFormat, mPixelStorePremultiplyAlpha, dstTexelSize); pixels = reinterpret_cast<void*>(convertedData.get()); } imageInfoStatusIfSuccess = WebGLImageDataStatus::InitializedImageData; } - GLenum error = CheckedTexImage2D(target, level, internalformat, width, + GLenum error = CheckedTexImage2D(texImageTarget, level, internalformat, width, height, border, format, type, pixels); if (error) { GenerateWarning("texImage2D generated error %s", ErrorName(error)); return; } // in all of the code paths above, we should have either initialized data, // or allocated data and left it uninitialized, but in any case we shouldn't // have NoImageData at this point. MOZ_ASSERT(imageInfoStatusIfSuccess != WebGLImageDataStatus::NoImageData); - tex->SetImageInfo(target, level, width, height, format, type, imageInfoStatusIfSuccess); + tex->SetImageInfo(texImageTarget, level, width, height, format, type, imageInfoStatusIfSuccess); } void -WebGLContext::TexImage2D(GLenum target, GLint level, +WebGLContext::TexImage2D(GLenum rawTarget, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, const Nullable<ArrayBufferView> &pixels, ErrorResult& rv) { if (IsContextLost()) return; void* data; @@ -3716,58 +3749,67 @@ WebGLContext::TexImage2D(GLenum target, const ArrayBufferView& view = pixels.Value(); view.ComputeLengthAndData(); data = view.Data(); length = view.Length(); jsArrayType = int(JS_GetArrayBufferViewType(view.Obj())); } - return TexImage2D_base(target, level, internalformat, width, height, 0, border, format, type, + if (!ValidateTexImageTarget(2, rawTarget, WebGLTexImageFunc::TexImage)) + return; + + return TexImage2D_base(rawTarget, level, internalformat, width, height, 0, border, format, type, data, length, jsArrayType, WebGLTexelFormat::Auto, false); } void -WebGLContext::TexImage2D(GLenum target, GLint level, +WebGLContext::TexImage2D(GLenum rawTarget, GLint level, GLenum internalformat, GLenum format, GLenum type, ImageData* pixels, ErrorResult& rv) { if (IsContextLost()) return; if (!pixels) { // Spec says to generate an INVALID_VALUE error return ErrorInvalidValue("texImage2D: null ImageData"); } Uint8ClampedArray arr; DebugOnly<bool> inited = arr.Init(pixels->GetDataObject()); MOZ_ASSERT(inited); arr.ComputeLengthAndData(); - return TexImage2D_base(target, level, internalformat, pixels->Width(), + void* pixelData = arr.Data(); + const uint32_t pixelDataLength = arr.Length(); + + if (!ValidateTexImageTarget(2, rawTarget, WebGLTexImageFunc::TexImage)) + return; + + return TexImage2D_base(rawTarget, level, internalformat, pixels->Width(), pixels->Height(), 4*pixels->Width(), 0, - format, type, arr.Data(), arr.Length(), -1, + format, type, pixelData, pixelDataLength, -1, WebGLTexelFormat::RGBA8, false); } void -WebGLContext::TexSubImage2D_base(GLenum target, GLint level, +WebGLContext::TexSubImage2D_base(TexImageTarget texImageTarget, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLsizei srcStrideOrZero, GLenum format, GLenum type, void* data, uint32_t byteLength, int jsArrayType, WebGLTexelFormat srcFormat, bool srcPremultiplied) { const WebGLTexImageFunc func = WebGLTexImageFunc::TexSubImage; - if (!ValidateTexImage(2, target, level, format, + if (!ValidateTexImage(2, texImageTarget, level, format, xoffset, yoffset, 0, width, height, 0, 0, format, type, func)) { return; } if (!ValidateTexInputData(type, jsArrayType, func)) @@ -3792,21 +3834,21 @@ WebGLContext::TexSubImage2D_base(GLenum if (!checked_neededByteLength.isValid()) return ErrorInvalidOperation("texSubImage2D: integer overflow computing the needed buffer size"); uint32_t bytesNeeded = checked_neededByteLength.value(); if (byteLength < bytesNeeded) return ErrorInvalidOperation("texSubImage2D: not enough data for operation (need %d, have %d)", bytesNeeded, byteLength); - WebGLTexture *tex = activeBoundTextureForTexImageTarget(target); - const WebGLTexture::ImageInfo &imageInfo = tex->ImageInfoAt(target, level); + WebGLTexture *tex = activeBoundTextureForTexImageTarget(texImageTarget); + const WebGLTexture::ImageInfo &imageInfo = tex->ImageInfoAt(texImageTarget, level); if (imageInfo.HasUninitializedImageData()) - tex->DoDeferredImageInitialization(target, level); + tex->DoDeferredImageInitialization(texImageTarget, level); MakeContextCurrent(); size_t srcStride = srcStrideOrZero ? srcStrideOrZero : checked_alignedRowSize.value(); uint32_t dstTexelSize = GetBitsPerTexel(format, type) / 8; size_t dstPlainRowSize = dstTexelSize * width; // There are checks above to ensure that this won't overflow. size_t dstStride = RoundedToNextMultipleOf(dstPlainRowSize, mPixelStoreUnpackAlignment).value(); @@ -3830,37 +3872,40 @@ WebGLContext::TexSubImage2D_base(GLenum pixels = reinterpret_cast<void*>(convertedData.get()); } GLenum driverType = DriverTypeFromType(gl, type); GLenum driverInternalFormat = LOCAL_GL_NONE; GLenum driverFormat = LOCAL_GL_NONE; DriverFormatsFromFormatAndType(gl, format, type, &driverInternalFormat, &driverFormat); - gl->fTexSubImage2D(target, level, xoffset, yoffset, width, height, driverFormat, driverType, pixels); + gl->fTexSubImage2D(texImageTarget.get(), level, xoffset, yoffset, width, height, driverFormat, driverType, pixels); } void -WebGLContext::TexSubImage2D(GLenum target, GLint level, +WebGLContext::TexSubImage2D(GLenum rawTarget, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, const Nullable<ArrayBufferView> &pixels, ErrorResult& rv) { if (IsContextLost()) return; if (pixels.IsNull()) return ErrorInvalidValue("texSubImage2D: pixels must not be null!"); const ArrayBufferView& view = pixels.Value(); view.ComputeLengthAndData(); - return TexSubImage2D_base(target, level, xoffset, yoffset, + if (!ValidateTexImageTarget(2, rawTarget, WebGLTexImageFunc::TexSubImage)) + return; + + return TexSubImage2D_base(rawTarget, level, xoffset, yoffset, width, height, 0, format, type, view.Data(), view.Length(), JS_GetArrayBufferViewType(view.Obj()), WebGLTexelFormat::Auto, false); } void WebGLContext::TexSubImage2D(GLenum target, GLint level,
--- a/dom/canvas/WebGLContextUtils.cpp +++ b/dom/canvas/WebGLContextUtils.cpp @@ -51,30 +51,32 @@ FormatHasAlpha(GLenum webGLFormat) return webGLFormat == LOCAL_GL_RGBA || webGLFormat == LOCAL_GL_LUMINANCE_ALPHA || webGLFormat == LOCAL_GL_ALPHA || webGLFormat == LOCAL_GL_RGBA4 || webGLFormat == LOCAL_GL_RGB5_A1 || webGLFormat == LOCAL_GL_SRGB_ALPHA; } -GLenum -TexImageTargetToTexTarget(GLenum texImageTarget) +TexTarget +TexImageTargetToTexTarget(TexImageTarget texImageTarget) { - switch (texImageTarget) { + switch (texImageTarget.get()) { case LOCAL_GL_TEXTURE_2D: return LOCAL_GL_TEXTURE_2D; case LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X: case LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_X: case LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_Y: case LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Y: case LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_Z: case LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z: return LOCAL_GL_TEXTURE_CUBE_MAP; default: + MOZ_ASSERT(false, "Bad texture conversion"); + // Should be caught by the constructor for TexTarget return LOCAL_GL_NONE; } } GLComponents::GLComponents(GLenum format) { mComponents = 0;
--- a/dom/canvas/WebGLContextUtils.h +++ b/dom/canvas/WebGLContextUtils.h @@ -2,16 +2,17 @@ /* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #ifndef WEBGLCONTEXTUTILS_H_ #define WEBGLCONTEXTUTILS_H_ #include "WebGLContext.h" +#include "WebGLStrongTypes.h" #include "mozilla/Assertions.h" #include "mozilla/dom/BindingUtils.h" namespace mozilla { bool IsGLDepthFormat(GLenum webGLFormat); bool IsGLDepthStencilFormat(GLenum webGLFormat); bool FormatHasAlpha(GLenum webGLFormat); @@ -26,17 +27,17 @@ GLenum DriverTypeFromType(gl::GLContext* // For example, cube maps would pass GL_TEXTURE_CUBE_MAP_[POS|NEG]_[X|Y|Z] // instead of just GL_TEXTURE_CUBE_MAP. // // This function converts the texture image target to the texture target a.k.a. // binding location. The returned binding location can be used to check that // the currently bound texture is appropriate for this texImageTarget. // // Returns GL_NONE if passed an invalid texture image target -GLenum TexImageTargetToTexTarget(GLenum texImageTarget); +TexTarget TexImageTargetToTexTarget(TexImageTarget texImageTarget); struct GLComponents { unsigned char mComponents; enum Components { Red = (1 << 0), Green = (1 << 1),
--- a/dom/canvas/WebGLContextValidate.cpp +++ b/dom/canvas/WebGLContextValidate.cpp @@ -144,20 +144,20 @@ IsSubFunc(WebGLTexImageFunc func) func == WebGLTexImageFunc::CopyTexSubImage || func == WebGLTexImageFunc::CompTexSubImage); } /** * returns true is target is a texture cube map target. */ static bool -IsTexImageCubemapTarget(GLenum target) +IsTexImageCubemapTarget(GLenum texImageTarget) { - return (target >= LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X && - target <= LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z); + return (texImageTarget >= LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X && + texImageTarget <= LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z); } /* * Pull data out of the program, post-linking */ bool WebGLProgram::UpdateInfo() { @@ -707,17 +707,17 @@ WebGLContext::ValidateTexImageType(GLenu } /** * Validate texture image sizing extra constraints for * CompressedTex(Sub)?Image. */ // TODO: WebGL 2 bool -WebGLContext::ValidateCompTexImageSize(GLenum target, GLint level, GLenum format, +WebGLContext::ValidateCompTexImageSize(GLint level, GLenum format, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLsizei levelWidth, GLsizei levelHeight, WebGLTexImageFunc func) { // Negative parameters must already have been handled above MOZ_ASSERT(xoffset >= 0 && yoffset >= 0 && width >= 0 && height >= 0); @@ -879,17 +879,17 @@ WebGLContext::ValidateCompTexImageDataSi /** * Validate the width, height, and depth of a texture image, \return * true is valid, false otherwise. * Used by all the (Compressed|Copy)?Tex(Sub)?Image functions. * Target and level must have been validated before calling. */ bool -WebGLContext::ValidateTexImageSize(GLenum target, GLint level, +WebGLContext::ValidateTexImageSize(TexImageTarget texImageTarget, GLint level, GLint width, GLint height, GLint depth, WebGLTexImageFunc func) { MOZ_ASSERT(level >= 0, "level should already be validated"); /* Bug 966630: maxTextureSize >> level runs into "undefined" * behaviour depending on ISA. For example, on Intel shifts * amounts are mod 64 (in 64-bit mode on 64-bit dest) and mod 32 @@ -898,32 +898,32 @@ WebGLContext::ValidateTexImageSize(GLenu * clamping to a shift of 31 bits if level is greater than that * ammount. This will give 0 that if (!maxAllowedSize) is * expecting. */ if (level > 31) level = 31; - const GLuint maxTexImageSize = MaxTextureSizeForTarget(target) >> level; - const bool isCubemapTarget = IsTexImageCubemapTarget(target); + const GLuint maxTexImageSize = MaxTextureSizeForTarget(TexImageTargetToTexTarget(texImageTarget)) >> level; + const bool isCubemapTarget = IsTexImageCubemapTarget(texImageTarget.get()); const bool isSub = IsSubFunc(func); if (!isSub && isCubemapTarget && (width != height)) { /* GL ES Version 2.0.25 - 3.7.1 Texture Image Specification * "When the target parameter to TexImage2D is one of the * six cube map two-dimensional image targets, the error * INVALID_VALUE is generated if the width and height * parameters are not equal." */ ErrorInvalidValue("%s: for cube map, width must equal height", InfoFrom(func)); return false; } - if (target == LOCAL_GL_TEXTURE_2D || isCubemapTarget) + if (texImageTarget == LOCAL_GL_TEXTURE_2D || isCubemapTarget) { /* GL ES Version 2.0.25 - 3.7.1 Texture Image Specification * "If wt and ht are the specified image width and height, * and if either wt or ht are less than zero, then the error * INVALID_VALUE is generated." */ if (width < 0) { ErrorInvalidValue("%s: width must be >= 0", InfoFrom(func)); @@ -973,17 +973,17 @@ WebGLContext::ValidateTexImageSize(GLenu ErrorInvalidValue("%s: level >= 0, height of %d must be a power of two.", InfoFrom(func), height); return false; } } } // TODO: WebGL 2 - if (target == LOCAL_GL_TEXTURE_3D) { + if (texImageTarget == LOCAL_GL_TEXTURE_3D) { if (depth < 0) { ErrorInvalidValue("%s: depth must be >= 0", InfoFrom(func)); return false; } if (!is_pot_assuming_nonnegative(depth)) { ErrorInvalidValue("%s: level >= 0, depth of %d must be a power of two.", InfoFrom(func), depth); @@ -1303,29 +1303,25 @@ WebGLContext::ValidateCopyTexImage(GLenu } /** * Test the gl(Copy|Compressed)?Tex[Sub]?Image[23]() parameters for errors. * Verifies each of the parameters against the WebGL standard and enabled extensions. */ // TODO: Texture dims is here for future expansion in WebGL 2.0 bool -WebGLContext::ValidateTexImage(GLuint dims, GLenum target, +WebGLContext::ValidateTexImage(GLuint dims, TexImageTarget texImageTarget, GLint level, GLint internalFormat, GLint xoffset, GLint yoffset, GLint zoffset, GLint width, GLint height, GLint depth, GLint border, GLenum format, GLenum type, WebGLTexImageFunc func) { const char* info = InfoFrom(func); - /* Check target */ - if (!ValidateTexImageTarget(dims, target, func)) - return false; - /* Check level */ if (level < 0) { ErrorInvalidValue("%s: level must be >= 0", info); return false; } /* Check border */ if (border != 0) { @@ -1352,39 +1348,39 @@ WebGLContext::ValidateTexImage(GLuint di // TODO: Not sure if this is a bit of over kill. if (BaseTexFormat(internalFormat) == LOCAL_GL_NONE) { MOZ_ASSERT(false); ErrorInvalidValue("%s:", info); return false; } /* Check texture image size */ - if (!ValidateTexImageSize(target, level, width, height, 0, func)) + if (!ValidateTexImageSize(texImageTarget, level, width, height, 0, func)) return false; /* 5.14.8 Texture objects - WebGL Spec. * "If an attempt is made to call these functions with no * WebGLTexture bound (see above), an INVALID_OPERATION error * is generated." */ - WebGLTexture* tex = activeBoundTextureForTexImageTarget(target); + WebGLTexture* tex = activeBoundTextureForTexImageTarget(texImageTarget); if (!tex) { ErrorInvalidOperation("%s: no texture is bound to target %s", - info, WebGLContext::EnumName(target)); + info, WebGLContext::EnumName(texImageTarget.get())); return false; } if (IsSubFunc(func)) { - if (!tex->HasImageInfoAt(target, level)) { + if (!tex->HasImageInfoAt(texImageTarget, level)) { ErrorInvalidOperation("%s: no texture image previously defined for target %s at level %d", - info, WebGLContext::EnumName(target), level); + info, WebGLContext::EnumName(texImageTarget.get()), level); return false; } - const WebGLTexture::ImageInfo& imageInfo = tex->ImageInfoAt(target, level); + const WebGLTexture::ImageInfo& imageInfo = tex->ImageInfoAt(texImageTarget, level); if (!ValidateTexSubImageSize(xoffset, yoffset, zoffset, width, height, depth, imageInfo.Width(), imageInfo.Height(), 0, func)) { return false; } @@ -1396,17 +1392,17 @@ WebGLContext::ValidateTexImage(GLuint di { ErrorInvalidOperation("%s: format or type doesn't match the existing texture", info); return false; } } /* Additional checks for depth textures */ - if (target != LOCAL_GL_TEXTURE_2D && + if (texImageTarget != LOCAL_GL_TEXTURE_2D && (format == LOCAL_GL_DEPTH_COMPONENT || format == LOCAL_GL_DEPTH_STENCIL)) { ErrorInvalidOperation("%s: with format of %s target must be TEXTURE_2D", info, WebGLContext::EnumName(format)); return false; }
--- a/dom/canvas/WebGLFramebuffer.cpp +++ b/dom/canvas/WebGLFramebuffer.cpp @@ -19,17 +19,17 @@ using namespace mozilla::gl; JSObject* WebGLFramebuffer::WrapObject(JSContext* cx) { return dom::WebGLFramebufferBinding::Wrap(cx, this); } WebGLFramebuffer::WebGLFramebuffer(WebGLContext* context) - : WebGLBindableName() + : WebGLBindableName<GLenum>() , WebGLContextBoundObject(context) , mStatus(0) , mDepthAttachment(LOCAL_GL_DEPTH_ATTACHMENT) , mStencilAttachment(LOCAL_GL_STENCIL_ATTACHMENT) , mDepthStencilAttachment(LOCAL_GL_DEPTH_STENCIL_ATTACHMENT) { SetIsDOMBinding(); mContext->MakeContextCurrent(); @@ -37,16 +37,17 @@ WebGLFramebuffer::WebGLFramebuffer(WebGL mContext->mFramebuffers.insertBack(this); mColorAttachments.SetLength(1); mColorAttachments[0].mAttachmentPoint = LOCAL_GL_COLOR_ATTACHMENT0; } WebGLFramebuffer::Attachment::Attachment(GLenum aAttachmentPoint) : mAttachmentPoint(aAttachmentPoint) + , mTexImageTarget(LOCAL_GL_NONE) , mNeedsFinalize(false) {} WebGLFramebuffer::Attachment::~Attachment() {} void WebGLFramebuffer::Attachment::Reset() @@ -79,19 +80,19 @@ WebGLFramebuffer::Attachment::HasAlpha() GLenum WebGLFramebuffer::GetFormatForAttachment(const WebGLFramebuffer::Attachment& attachment) const { MOZ_ASSERT(attachment.IsDefined()); MOZ_ASSERT(attachment.Texture() || attachment.Renderbuffer()); if (attachment.Texture()) { const WebGLTexture& tex = *attachment.Texture(); - MOZ_ASSERT(tex.HasImageInfoAt(tex.Target(), 0)); + MOZ_ASSERT(tex.HasImageInfoAt(attachment.ImageTarget(), 0)); - const WebGLTexture::ImageInfo& imgInfo = tex.ImageInfoAt(tex.Target(), 0); + const WebGLTexture::ImageInfo& imgInfo = tex.ImageInfoAt(attachment.ImageTarget(), 0); return imgInfo.WebGLFormat(); } if (attachment.Renderbuffer()) return attachment.Renderbuffer()->InternalFormat(); return LOCAL_GL_NONE; } @@ -125,17 +126,17 @@ WebGLFramebuffer::Attachment::IsReadable // If we arrive here Attachment isn't correct setup because it has // no texture nor render buffer pointer. MOZ_ASSERT(false, "Should not get here."); return false; } void -WebGLFramebuffer::Attachment::SetTexImage(WebGLTexture* tex, GLenum target, GLint level) +WebGLFramebuffer::Attachment::SetTexImage(WebGLTexture* tex, TexImageTarget target, GLint level) { mTexturePtr = tex; mRenderbufferPtr = nullptr; mTexImageTarget = target; mTexImageLevel = level; mNeedsFinalize = true; } @@ -390,24 +391,28 @@ WebGLFramebuffer::Attachment::FinalizeAt return; } MOZ_ASSERT(HasImage()); if (Texture()) { MOZ_ASSERT(gl == Texture()->Context()->gl); + const GLenum imageTarget = ImageTarget().get(); + const GLint mipLevel = MipLevel(); + const GLuint glName = Texture()->GLName(); + if (attachmentLoc == LOCAL_GL_DEPTH_STENCIL_ATTACHMENT) { gl->fFramebufferTexture2D(LOCAL_GL_FRAMEBUFFER, LOCAL_GL_DEPTH_ATTACHMENT, - TexImageTarget(), Texture()->GLName(), TexImageLevel()); + imageTarget, glName, mipLevel); gl->fFramebufferTexture2D(LOCAL_GL_FRAMEBUFFER, LOCAL_GL_STENCIL_ATTACHMENT, - TexImageTarget(), Texture()->GLName(), TexImageLevel()); + imageTarget, glName, mipLevel); } else { gl->fFramebufferTexture2D(LOCAL_GL_FRAMEBUFFER, attachmentLoc, - TexImageTarget(), Texture()->GLName(), TexImageLevel()); + imageTarget, glName, mipLevel); } return; } if (Renderbuffer()) { Renderbuffer()->FramebufferRenderbuffer(attachmentLoc); return; } @@ -495,38 +500,31 @@ WebGLFramebuffer::FramebufferRenderbuffe wrb->AttachTo(this, attachment); a->SetRenderbuffer(wrb); } void WebGLFramebuffer::FramebufferTexture2D(GLenum target, GLenum attachment, - GLenum textarget, + TexImageTarget texImageTarget, WebGLTexture* wtex, GLint level) { MOZ_ASSERT(mContext->mBoundFramebuffer == this); if (!mContext->ValidateObjectAllowNull("framebufferTexture2D: texture", wtex)) return; if (target != LOCAL_GL_FRAMEBUFFER) return mContext->ErrorInvalidEnumInfo("framebufferTexture2D: target", target); - if (textarget != LOCAL_GL_TEXTURE_2D && - (textarget < LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X || - textarget > LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z)) - { - return mContext->ErrorInvalidEnumInfo("framebufferTexture2D: invalid texture target", textarget); - } - if (wtex) { bool isTexture2D = wtex->Target() == LOCAL_GL_TEXTURE_2D; - bool isTexTarget2D = textarget == LOCAL_GL_TEXTURE_2D; + bool isTexTarget2D = texImageTarget == LOCAL_GL_TEXTURE_2D; if (isTexture2D != isTexTarget2D) { return mContext->ErrorInvalidOperation("framebufferTexture2D: mismatched texture and texture target"); } } if (level != 0) return mContext->ErrorInvalidValue("framebufferTexture2D: level must be 0"); @@ -550,17 +548,17 @@ WebGLFramebuffer::FramebufferTexture2D(G a->Texture()->DetachFrom(this, attachment); else if (a->Renderbuffer()) a->Renderbuffer()->DetachFrom(this, attachment); // Attach new if (wtex) wtex->AttachTo(this, attachment); - a->SetTexImage(wtex, textarget, level); + a->SetTexImage(wtex, texImageTarget, level); } WebGLFramebuffer::Attachment* WebGLFramebuffer::GetAttachmentOrNull(GLenum attachment) { if (attachment == LOCAL_GL_DEPTH_STENCIL_ATTACHMENT) return &mDepthStencilAttachment;
--- a/dom/canvas/WebGLFramebuffer.h +++ b/dom/canvas/WebGLFramebuffer.h @@ -3,84 +3,85 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #ifndef WEBGLFRAMEBUFFER_H_ #define WEBGLFRAMEBUFFER_H_ #include "WebGLBindableName.h" #include "WebGLObjectModel.h" +#include "WebGLStrongTypes.h" #include "nsWrapperCache.h" #include "mozilla/LinkedList.h" namespace mozilla { class WebGLFramebufferAttachable; class WebGLTexture; class WebGLRenderbuffer; namespace gl { class GLContext; } class WebGLFramebuffer MOZ_FINAL : public nsWrapperCache - , public WebGLBindableName + , public WebGLBindableName<GLenum> , public WebGLRefCountedObject<WebGLFramebuffer> , public LinkedListElement<WebGLFramebuffer> , public WebGLContextBoundObject , public SupportsWeakPtr<WebGLFramebuffer> { public: MOZ_DECLARE_REFCOUNTED_TYPENAME(WebGLFramebuffer) explicit WebGLFramebuffer(WebGLContext* context); struct Attachment { // deleting a texture or renderbuffer immediately detaches it WebGLRefPtr<WebGLTexture> mTexturePtr; WebGLRefPtr<WebGLRenderbuffer> mRenderbufferPtr; GLenum mAttachmentPoint; - GLenum mTexImageTarget; + TexImageTarget mTexImageTarget; GLint mTexImageLevel; mutable bool mNeedsFinalize; explicit Attachment(GLenum aAttachmentPoint = LOCAL_GL_COLOR_ATTACHMENT0); ~Attachment(); bool IsDefined() const { return Texture() || Renderbuffer(); } bool IsDeleteRequested() const; bool HasAlpha() const; bool IsReadableFloat() const; - void SetTexImage(WebGLTexture* tex, GLenum target, GLint level); + void SetTexImage(WebGLTexture* tex, TexImageTarget target, GLint level); void SetRenderbuffer(WebGLRenderbuffer* rb); const WebGLTexture* Texture() const { return mTexturePtr; } WebGLTexture* Texture() { return mTexturePtr; } const WebGLRenderbuffer* Renderbuffer() const { return mRenderbufferPtr; } WebGLRenderbuffer* Renderbuffer() { return mRenderbufferPtr; } - GLenum TexImageTarget() const { + TexImageTarget ImageTarget() const { return mTexImageTarget; } - GLint TexImageLevel() const { + GLint MipLevel() const { return mTexImageLevel; } bool HasUninitializedImageData() const; void SetImageDataStatus(WebGLImageDataStatus x); void Reset(); @@ -96,17 +97,17 @@ public: void FramebufferRenderbuffer(GLenum target, GLenum attachment, GLenum rbtarget, WebGLRenderbuffer* wrb); void FramebufferTexture2D(GLenum target, GLenum attachment, - GLenum textarget, + TexImageTarget texImageTarget, WebGLTexture* wtex, GLint level); private: void DetachAttachment(WebGLFramebuffer::Attachment& attachment); void DetachAllAttachments(); const WebGLRectangleObject& GetAnyRectObject() const; Attachment* GetAttachmentOrNull(GLenum attachment);
--- a/dom/canvas/WebGLRenderbuffer.cpp +++ b/dom/canvas/WebGLRenderbuffer.cpp @@ -38,17 +38,17 @@ NeedsDepthStencilEmu(GLContext* gl, GLen } JSObject* WebGLRenderbuffer::WrapObject(JSContext *cx) { return dom::WebGLRenderbufferBinding::Wrap(cx, this); } WebGLRenderbuffer::WebGLRenderbuffer(WebGLContext *context) - : WebGLBindableName() + : WebGLBindableName<GLenum>() , WebGLContextBoundObject(context) , mPrimaryRB(0) , mSecondaryRB(0) , mInternalFormat(0) , mInternalFormatForGL(0) , mImageDataStatus(WebGLImageDataStatus::NoImageData) { SetIsDOMBinding();
--- a/dom/canvas/WebGLRenderbuffer.h +++ b/dom/canvas/WebGLRenderbuffer.h @@ -13,17 +13,17 @@ #include "nsWrapperCache.h" #include "mozilla/LinkedList.h" namespace mozilla { class WebGLRenderbuffer MOZ_FINAL : public nsWrapperCache - , public WebGLBindableName + , public WebGLBindableName<GLenum> , public WebGLRefCountedObject<WebGLRenderbuffer> , public LinkedListElement<WebGLRenderbuffer> , public WebGLRectangleObject , public WebGLContextBoundObject , public WebGLFramebufferAttachable { public: explicit WebGLRenderbuffer(WebGLContext* context);
--- a/dom/canvas/WebGLSampler.cpp +++ b/dom/canvas/WebGLSampler.cpp @@ -8,18 +8,17 @@ #include "GLContext.h" #include "mozilla/dom/WebGL2RenderingContextBinding.h" using namespace mozilla; WebGLSampler::WebGLSampler(WebGLContext* context) - : WebGLBindableName() - , WebGLContextBoundObject(context) + : WebGLContextBoundObject(context) { SetIsDOMBinding(); MOZ_CRASH("Not Implemented."); } WebGLSampler::~WebGLSampler() {}
--- a/dom/canvas/WebGLSampler.h +++ b/dom/canvas/WebGLSampler.h @@ -11,17 +11,17 @@ #include "nsWrapperCache.h" #include "mozilla/LinkedList.h" namespace mozilla { class WebGLSampler MOZ_FINAL - : public WebGLBindableName + : public WebGLBindableName<GLenum> , public nsWrapperCache , public WebGLRefCountedObject<WebGLSampler> , public LinkedListElement<WebGLSampler> , public WebGLContextBoundObject { friend class WebGLContext2; public:
new file mode 100644 --- /dev/null +++ b/dom/canvas/WebGLStrongTypes.h @@ -0,0 +1,152 @@ + +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ + +#ifndef WEBGLSTRONGTYPES_H_ +#define WEBGLSTRONGTYPES_H_ + +#include "GLDefs.h" +#include "mozilla/Assertions.h" +#include "mozilla/ArrayUtils.h" + +// Usage: +// =========== +// +// To create a new type from a set of GLenums do the following: +// +// STRONG_GLENUM_BEGIN(TypeName) +// Enum1, +// Enum2, +// ... +// STRONG_GLENUM_END() +// +// where TypeName is the name you want to give the type. Now simply use TypeName +// instead of GLenum. +// +// ~~~~~~~~~~~~~~~~ +// Important Notes: +// ~~~~~~~~~~~~~~~~ +// +// Boolean operators (==, !=) are provided in an effort to prevent some mistakes +// when using constants. For example we want to make sure that GL_ENUM_X is +// a valid value for the type in code like: +// +// if (myNewType == LOCAL_GL_SOME_ENUM) +// ... +// +// The operators will assert that LOCAL_GL_SOME_ENUM is a value that myNewType +// can have. +// +// ---- +// +// A get() method is provided to allow access to the underlying GLenum. This +// method should ideally only be called when passing parameters to the gl->fXXXX +// functions, and be used very minimally everywhere else. +// +// Definitely XXX - DO NOT DO - XXX: +// +// if (myNewType.get() == LOCAL_GL_SOME_ENUM) +// ... +// +// As that undermines the debug checks that were implemented in the ==, and != +// operators. If you see code like this it should be treated with suspicion. +// +// Background: +// =========== +// +// This macro is the first step in an effort to make the WebGL code safer. +// Many of the different functions take GLenum as their parameter which leads +// to bugs because of subtle differences in the enums purpose. For example there +// are two types of 'texture targets'. One is the texture binding locations: +// +// GL_TEXTURE_2D +// GL_TEXTURE_CUBE_MAP +// +// Yet, this is not the same as texture image targets: +// +// GL_TEXTURE_2D +// GL_TEXTURE_CUBE_MAP_POSITIVE_X +// GL_TEXTURE_CUBE_MAP_NEGATIVE_X +// GL_TEXTURE_CUBE_MAP_POSITIVE_Y +// ... +// +// This subtle distinction has already led to many bugs in the texture code +// because of invalid assumptions about what type goes where. The macro below +// is an attempt at fixing this by providing a small wrapper around GLenum that +// validates its values. +// +#ifdef DEBUG + +template<size_t N> +static bool +IsValueInArr(GLenum value, const GLenum (&arr)[N]) +{ + for (size_t i = 0; i < N; ++i) { + if (value == arr[i]) + return true; + } + + return false; +} + +#endif + +#define STRONG_GLENUM_BEGIN(NAME) \ + class NAME { \ + private: \ + GLenum mValue; \ + public: \ + MOZ_CONSTEXPR NAME(const NAME& other) \ + : mValue(other.mValue) { } \ + \ + bool operator==(const NAME& other) const { \ + return mValue == other.mValue; \ + } \ + \ + bool operator!=(const NAME& other) const { \ + return mValue != other.mValue; \ + } \ + \ + GLenum get() const { \ + MOZ_ASSERT(mValue != LOCAL_GL_NONE); \ + return mValue; \ + } \ + \ + NAME(GLenum val) \ + : mValue(val) \ + { \ + const GLenum validValues[] = { + +#define STRONG_GLENUM_END() \ + }; \ + (void)validValues; \ + MOZ_ASSERT(IsValueInArr(mValue, validValues)); \ + } \ + }; + +/****************************************************************************** + * Add your types after this comment + *****************************************************************************/ + +STRONG_GLENUM_BEGIN(TexImageTarget) + LOCAL_GL_NONE, + LOCAL_GL_TEXTURE_2D, + LOCAL_GL_TEXTURE_3D, + LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X, + LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_X, + LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_Y, + LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Y, + LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_Z, + LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, +STRONG_GLENUM_END() + +STRONG_GLENUM_BEGIN(TexTarget) + LOCAL_GL_NONE, + LOCAL_GL_TEXTURE_2D, + LOCAL_GL_TEXTURE_3D, + LOCAL_GL_TEXTURE_CUBE_MAP, +STRONG_GLENUM_END() + +#endif
--- a/dom/canvas/WebGLTexture.cpp +++ b/dom/canvas/WebGLTexture.cpp @@ -18,17 +18,17 @@ using namespace mozilla; JSObject* WebGLTexture::WrapObject(JSContext *cx) { return dom::WebGLTextureBinding::Wrap(cx, this); } WebGLTexture::WebGLTexture(WebGLContext *context) - : WebGLBindableName() + : WebGLBindableName<TexTarget>() , WebGLContextBoundObject(context) , mMinFilter(LOCAL_GL_NEAREST_MIPMAP_LINEAR) , mMagFilter(LOCAL_GL_LINEAR) , mWrapS(LOCAL_GL_REPEAT) , mWrapT(LOCAL_GL_REPEAT) , mFacesCount(0) , mMaxLevelWithCustomImages(0) , mHaveGeneratedMipmap(false) @@ -71,17 +71,17 @@ WebGLTexture::MemoryUsage() const { for(size_t level = 0; level <= mMaxLevelWithCustomImages; level++) result += ImageInfoAtFace(face, level).MemoryUsage(); } } return result; } bool -WebGLTexture::DoesTexture2DMipmapHaveAllLevelsConsistentlyDefined(GLenum texImageTarget) const { +WebGLTexture::DoesTexture2DMipmapHaveAllLevelsConsistentlyDefined(TexImageTarget texImageTarget) const { if (mHaveGeneratedMipmap) return true; // We want a copy here so we can modify it temporarily. ImageInfo expected = ImageInfoAt(texImageTarget, 0); // checks if custom level>0 images are all defined up to the highest level defined // and have the expected dimensions @@ -98,51 +98,50 @@ WebGLTexture::DoesTexture2DMipmapHaveAll return true; } // if we're here, we've exhausted all levels without finding a 1x1 image return false; } void -WebGLTexture::Bind(GLenum aTarget) { +WebGLTexture::Bind(TexTarget aTexTarget) { // this function should only be called by bindTexture(). // it assumes that the GL context is already current. bool firstTimeThisTextureIsBound = !HasEverBeenBound(); if (firstTimeThisTextureIsBound) { - BindTo(aTarget); - } else if (aTarget != Target()) { + BindTo(aTexTarget); + } else if (aTexTarget != Target()) { mContext->ErrorInvalidOperation("bindTexture: this texture has already been bound to a different target"); // very important to return here before modifying texture state! This was the place when I lost a whole day figuring // very strange 'invalid write' crashes. return; } GLuint name = GLName(); - GLenum target = Target(); - mContext->gl->fBindTexture(target, name); + mContext->gl->fBindTexture(aTexTarget.get(), name); if (firstTimeThisTextureIsBound) { - mFacesCount = (mTarget == LOCAL_GL_TEXTURE_2D) ? 1 : 6; + mFacesCount = (aTexTarget == LOCAL_GL_TEXTURE_2D) ? 1 : 6; EnsureMaxLevelWithCustomImagesAtLeast(0); SetFakeBlackStatus(WebGLTextureFakeBlackStatus::Unknown); // thanks to the WebKit people for finding this out: GL_TEXTURE_WRAP_R is not // present in GLES 2, but is present in GL and it seems as if for cube maps // we need to set it to GL_CLAMP_TO_EDGE to get the expected GLES behavior. if (mTarget == LOCAL_GL_TEXTURE_CUBE_MAP && !mContext->gl->IsGLES()) - mContext->gl->fTexParameteri(mTarget, LOCAL_GL_TEXTURE_WRAP_R, LOCAL_GL_CLAMP_TO_EDGE); + mContext->gl->fTexParameteri(aTexTarget.get(), LOCAL_GL_TEXTURE_WRAP_R, LOCAL_GL_CLAMP_TO_EDGE); } } void -WebGLTexture::SetImageInfo(GLenum aTexImageTarget, GLint aLevel, +WebGLTexture::SetImageInfo(TexImageTarget aTexImageTarget, GLint aLevel, GLsizei aWidth, GLsizei aHeight, GLenum aFormat, GLenum aType, WebGLImageDataStatus aStatus) { MOZ_ASSERT(TexImageTargetToTexTarget(aTexImageTarget) == mTarget); if (TexImageTargetToTexTarget(aTexImageTarget) != mTarget) return; EnsureMaxLevelWithCustomImagesAtLeast(aLevel); @@ -222,31 +221,29 @@ WebGLTexture::IsCubeComplete() const { if (mTarget != LOCAL_GL_TEXTURE_CUBE_MAP) return false; const ImageInfo &first = ImageInfoAt(LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X, 0); if (!first.IsPositive() || !first.IsSquare()) return false; return AreAllLevel0ImageInfosEqual(); } -static GLenum +static TexImageTarget GLCubeMapFaceById(int id) { - GLenum result = LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X + id; - MOZ_ASSERT(result >= LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X && - result <= LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z); - return result; + // Correctness is checked by the constructor for TexImageTarget + return TexImageTarget(LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X + id); } bool WebGLTexture::IsMipmapCubeComplete() const { if (!IsCubeComplete()) // in particular, this checks that this is a cube map return false; for (int i = 0; i < 6; i++) { - GLenum face = GLCubeMapFaceById(i); + const TexImageTarget face = GLCubeMapFaceById(i); if (!DoesTexture2DMipmapHaveAllLevelsConsistentlyDefined(face)) return false; } return true; } WebGLTextureFakeBlackStatus WebGLTexture::ResolvedFakeBlackStatus() { @@ -274,31 +271,31 @@ WebGLTexture::ResolvedFakeBlackStatus() { if (DoesMinFilterRequireMipmap()) { if (!IsMipmapTexture2DComplete()) { mContext->GenerateWarning ("%s is a 2D texture, with a minification filter requiring a mipmap, " "and is not mipmap complete (as defined in section 3.7.10).", msg_rendering_as_black); mFakeBlackStatus = WebGLTextureFakeBlackStatus::IncompleteTexture; - } else if (!ImageInfoAt(mTarget, 0).IsPowerOfTwo()) { + } else if (!ImageInfoBase().IsPowerOfTwo()) { mContext->GenerateWarning ("%s is a 2D texture, with a minification filter requiring a mipmap, " "and either its width or height is not a power of two.", msg_rendering_as_black); mFakeBlackStatus = WebGLTextureFakeBlackStatus::IncompleteTexture; } } else // no mipmap required { - if (!ImageInfoAt(mTarget, 0).IsPositive()) { + if (!ImageInfoBase().IsPositive()) { mContext->GenerateWarning ("%s is a 2D texture and its width or height is equal to zero.", msg_rendering_as_black); mFakeBlackStatus = WebGLTextureFakeBlackStatus::IncompleteTexture; - } else if (!AreBothWrapModesClampToEdge() && !ImageInfoAt(mTarget, 0).IsPowerOfTwo()) { + } else if (!AreBothWrapModesClampToEdge() && !ImageInfoBase().IsPowerOfTwo()) { mContext->GenerateWarning ("%s is a 2D texture, with a minification filter not requiring a mipmap, " "with its width or height not a power of two, and with a wrap mode " "different from CLAMP_TO_EDGE.", msg_rendering_as_black); mFakeBlackStatus = WebGLTextureFakeBlackStatus::IncompleteTexture; } } } @@ -406,19 +403,19 @@ WebGLTexture::ResolvedFakeBlackStatus() if (hasAnyInitializedImageData) { // The texture contains some initialized image data, and some uninitialized image data. // In this case, we have no choice but to initialize all image data now. Fortunately, // in this case we know that we can't be dealing with a depth texture per WEBGL_depth_texture // and ANGLE_depth_texture (which allow only one image per texture) so we can assume that // glTexImage2D is able to upload data to images. for (size_t level = 0; level <= mMaxLevelWithCustomImages; ++level) { for (size_t face = 0; face < mFacesCount; ++face) { - GLenum imageTarget = mTarget == LOCAL_GL_TEXTURE_2D - ? LOCAL_GL_TEXTURE_2D - : LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X + face; + TexImageTarget imageTarget = mTarget == LOCAL_GL_TEXTURE_2D + ? LOCAL_GL_TEXTURE_2D + : LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X + face; const ImageInfo& imageInfo = ImageInfoAt(imageTarget, level); if (imageInfo.mImageDataStatus == WebGLImageDataStatus::UninitializedImageData) { DoDeferredImageInitialization(imageTarget, level); } } } mFakeBlackStatus = WebGLTextureFakeBlackStatus::NotNeeded; } else { @@ -456,17 +453,17 @@ ClearByMask(WebGLContext* context, GLbit context->ForceClearFramebufferWithDefaultValues(mask, colorAttachmentsMask); return true; } // `mask` from glClear. static bool ClearWithTempFB(WebGLContext* context, GLuint tex, - GLenum texImageTarget, GLint level, + TexImageTarget texImageTarget, GLint level, GLenum baseInternalFormat, GLsizei width, GLsizei height) { if (texImageTarget != LOCAL_GL_TEXTURE_2D) return false; gl::GLContext* gl = context->GL(); MOZ_ASSERT(gl->IsCurrent()); @@ -480,32 +477,32 @@ ClearWithTempFB(WebGLContext* context, G case LOCAL_GL_LUMINANCE_ALPHA: case LOCAL_GL_ALPHA: case LOCAL_GL_RGB: case LOCAL_GL_RGBA: case LOCAL_GL_BGR: case LOCAL_GL_BGRA: mask = LOCAL_GL_COLOR_BUFFER_BIT; gl->fFramebufferTexture2D(LOCAL_GL_FRAMEBUFFER, LOCAL_GL_COLOR_ATTACHMENT0, - texImageTarget, tex, level); + texImageTarget.get(), tex, level); break; case LOCAL_GL_DEPTH_COMPONENT: mask = LOCAL_GL_DEPTH_BUFFER_BIT; gl->fFramebufferTexture2D(LOCAL_GL_FRAMEBUFFER, LOCAL_GL_DEPTH_ATTACHMENT, - texImageTarget, tex, level); + texImageTarget.get(), tex, level); break; case LOCAL_GL_DEPTH_STENCIL: mask = LOCAL_GL_DEPTH_BUFFER_BIT | LOCAL_GL_STENCIL_BUFFER_BIT; gl->fFramebufferTexture2D(LOCAL_GL_FRAMEBUFFER, LOCAL_GL_DEPTH_ATTACHMENT, - texImageTarget, tex, level); + texImageTarget.get(), tex, level); gl->fFramebufferTexture2D(LOCAL_GL_FRAMEBUFFER, LOCAL_GL_STENCIL_ATTACHMENT, - texImageTarget, tex, level); + texImageTarget.get(), tex, level); break; default: return false; } MOZ_ASSERT(mask); if (ClearByMask(context, mask)) @@ -532,17 +529,17 @@ ClearWithTempFB(WebGLContext* context, G mask |= LOCAL_GL_COLOR_BUFFER_BIT; // Last chance! return ClearByMask(context, mask); } void -WebGLTexture::DoDeferredImageInitialization(GLenum imageTarget, GLint level) +WebGLTexture::DoDeferredImageInitialization(TexImageTarget imageTarget, GLint level) { const ImageInfo& imageInfo = ImageInfoAt(imageTarget, level); MOZ_ASSERT(imageInfo.mImageDataStatus == WebGLImageDataStatus::UninitializedImageData); mContext->MakeContextCurrent(); // Try to clear with glCLear. GLenum format = imageInfo.mWebGLFormat; @@ -553,17 +550,17 @@ WebGLTexture::DoDeferredImageInitializat imageTarget, level, format, imageInfo.mHeight, imageInfo.mWidth); if (cleared) { SetImageDataStatus(imageTarget, level, WebGLImageDataStatus::InitializedImageData); return; } // That didn't work. Try uploading zeros then. - gl::ScopedBindTexture autoBindTex(mContext->gl, GLName(), mTarget); + gl::ScopedBindTexture autoBindTex(mContext->gl, GLName(), mTarget.get()); uint32_t texelsize = WebGLTexelConversions::TexelBytesForFormat(texelformat); CheckedUint32 checked_byteLength = WebGLContext::GetImageSize( imageInfo.mHeight, imageInfo.mWidth, texelsize, mContext->mPixelStoreUnpackAlignment); @@ -573,17 +570,17 @@ WebGLTexture::DoDeferredImageInitializat gl::GLContext* gl = mContext->gl; GLenum driverType = DriverTypeFromType(gl, type); GLenum driverInternalFormat = LOCAL_GL_NONE; GLenum driverFormat = LOCAL_GL_NONE; DriverFormatsFromFormatAndType(gl, format, type, &driverInternalFormat, &driverFormat); mContext->GetAndFlushUnderlyingGLErrors(); - gl->fTexImage2D(imageTarget, level, driverInternalFormat, + gl->fTexImage2D(imageTarget.get(), level, driverInternalFormat, imageInfo.mWidth, imageInfo.mHeight, 0, driverFormat, driverType, zeros); GLenum error = mContext->GetAndFlushUnderlyingGLErrors(); if (error) { // Should only be OUT_OF_MEMORY. Anyway, there's no good way to recover from this here. printf_stderr("Error: 0x%4x\n", error); MOZ_CRASH(); // errors on texture upload have been related to video memory exposure in the past.
--- a/dom/canvas/WebGLTexture.h +++ b/dom/canvas/WebGLTexture.h @@ -4,16 +4,17 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #ifndef WEBGLTEXTURE_H_ #define WEBGLTEXTURE_H_ #include "WebGLBindableName.h" #include "WebGLFramebufferAttachable.h" #include "WebGLObjectModel.h" +#include "WebGLStrongTypes.h" #include "nsWrapperCache.h" #include "mozilla/CheckedInt.h" #include "mozilla/LinkedList.h" #include <algorithm> namespace mozilla { @@ -23,17 +24,17 @@ inline bool is_pot_assuming_nonnegative( { return x && (x & (x-1)) == 0; } // NOTE: When this class is switched to new DOM bindings, update the (then-slow) // WrapObject calls in GetParameter and GetFramebufferAttachmentParameter. class WebGLTexture MOZ_FINAL : public nsWrapperCache - , public WebGLBindableName + , public WebGLBindableName<TexTarget> , public WebGLRefCountedObject<WebGLTexture> , public LinkedListElement<WebGLTexture> , public WebGLContextBoundObject , public WebGLFramebufferAttachable { public: explicit WebGLTexture(WebGLContext* aContext); @@ -124,53 +125,47 @@ public: GLenum mWebGLFormat; //!< This is the WebGL/GLES format GLenum mWebGLType; //!< This is the WebGL/GLES type WebGLImageDataStatus mImageDataStatus; friend class WebGLTexture; }; private: - static size_t FaceForTarget(GLenum target) { - // Call this out explicitly: - MOZ_ASSERT(target != LOCAL_GL_TEXTURE_CUBE_MAP); - MOZ_ASSERT(target == LOCAL_GL_TEXTURE_2D || - (target >= LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X && - target <= LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z)); - return target == LOCAL_GL_TEXTURE_2D ? 0 : target - LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X; + static size_t FaceForTarget(TexImageTarget texImageTarget) { + if (texImageTarget == LOCAL_GL_TEXTURE_2D) + return 0; + + return texImageTarget.get() - LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X; } ImageInfo& ImageInfoAtFace(size_t face, GLint level) { MOZ_ASSERT(face < mFacesCount, "wrong face index, must be 0 for TEXTURE_2D and at most 5 for cube maps"); // no need to check level as a wrong value would be caught by ElementAt(). return mImageInfos.ElementAt(level * mFacesCount + face); } const ImageInfo& ImageInfoAtFace(size_t face, GLint level) const { return const_cast<const ImageInfo&>( const_cast<WebGLTexture*>(this)->ImageInfoAtFace(face, level) ); } public: - ImageInfo& ImageInfoAt(GLenum imageTarget, GLint level) { - MOZ_ASSERT(imageTarget); - + ImageInfo& ImageInfoAt(TexImageTarget imageTarget, GLint level) { size_t face = FaceForTarget(imageTarget); return ImageInfoAtFace(face, level); } - const ImageInfo& ImageInfoAt(GLenum imageTarget, GLint level) const { + const ImageInfo& ImageInfoAt(TexImageTarget imageTarget, GLint level) const { return const_cast<WebGLTexture*>(this)->ImageInfoAt(imageTarget, level); } - bool HasImageInfoAt(GLenum imageTarget, GLint level) const { - MOZ_ASSERT(imageTarget); - + bool HasImageInfoAt(TexImageTarget imageTarget, GLint level) const { size_t face = FaceForTarget(imageTarget); CheckedUint32 checked_index = CheckedUint32(level) * mFacesCount + face; return checked_index.isValid() && checked_index.value() < mImageInfos.Length() && ImageInfoAt(imageTarget, level).mImageDataStatus != WebGLImageDataStatus::NoImageData; } ImageInfo& ImageInfoBase() { @@ -178,29 +173,29 @@ public: } const ImageInfo& ImageInfoBase() const { return ImageInfoAtFace(0, 0); } int64_t MemoryUsage() const; - void SetImageDataStatus(GLenum imageTarget, GLint level, WebGLImageDataStatus newStatus) { + void SetImageDataStatus(TexImageTarget imageTarget, GLint level, WebGLImageDataStatus newStatus) { MOZ_ASSERT(HasImageInfoAt(imageTarget, level)); ImageInfo& imageInfo = ImageInfoAt(imageTarget, level); // there is no way to go from having image data to not having any MOZ_ASSERT(newStatus != WebGLImageDataStatus::NoImageData || imageInfo.mImageDataStatus == WebGLImageDataStatus::NoImageData); if (imageInfo.mImageDataStatus != newStatus) { SetFakeBlackStatus(WebGLTextureFakeBlackStatus::Unknown); } imageInfo.mImageDataStatus = newStatus; } - void DoDeferredImageInitialization(GLenum imageTarget, GLint level); + void DoDeferredImageInitialization(TexImageTarget imageTarget, GLint level); protected: GLenum mMinFilter, mMagFilter, mWrapS, mWrapT; size_t mFacesCount, mMaxLevelWithCustomImages; nsTArray<ImageInfo> mImageInfos; @@ -217,23 +212,23 @@ protected: return (mMagFilter == LOCAL_GL_NEAREST) && (mMinFilter == LOCAL_GL_NEAREST || mMinFilter == LOCAL_GL_NEAREST_MIPMAP_NEAREST); } bool AreBothWrapModesClampToEdge() const { return mWrapS == LOCAL_GL_CLAMP_TO_EDGE && mWrapT == LOCAL_GL_CLAMP_TO_EDGE; } - bool DoesTexture2DMipmapHaveAllLevelsConsistentlyDefined(GLenum texImageTarget) const; + bool DoesTexture2DMipmapHaveAllLevelsConsistentlyDefined(TexImageTarget texImageTarget) const; public: - void Bind(GLenum aTarget); + void Bind(TexTarget aTexTarget); - void SetImageInfo(GLenum aTarget, GLint aLevel, + void SetImageInfo(TexImageTarget aTarget, GLint aLevel, GLsizei aWidth, GLsizei aHeight, GLenum aFormat, GLenum aType, WebGLImageDataStatus aStatus); void SetMinFilter(GLenum aMinFilter) { mMinFilter = aMinFilter; SetFakeBlackStatus(WebGLTextureFakeBlackStatus::Unknown); } void SetMagFilter(GLenum aMagFilter) {
--- a/dom/canvas/WebGLTransformFeedback.cpp +++ b/dom/canvas/WebGLTransformFeedback.cpp @@ -8,18 +8,17 @@ #include "GLContext.h" #include "mozilla/dom/WebGL2RenderingContextBinding.h" using namespace mozilla; WebGLTransformFeedback::WebGLTransformFeedback(WebGLContext* context) - : WebGLBindableName() - , WebGLContextBoundObject(context) + : WebGLContextBoundObject(context) { SetIsDOMBinding(); MOZ_CRASH("Not Implemented."); } WebGLTransformFeedback::~WebGLTransformFeedback() {}
--- a/dom/canvas/WebGLTransformFeedback.h +++ b/dom/canvas/WebGLTransformFeedback.h @@ -11,17 +11,17 @@ #include "nsWrapperCache.h" #include "mozilla/LinkedList.h" namespace mozilla { class WebGLTransformFeedback MOZ_FINAL - : public WebGLBindableName + : public WebGLBindableName<GLenum> , public nsWrapperCache , public WebGLRefCountedObject<WebGLTransformFeedback> , public LinkedListElement<WebGLTransformFeedback> , public WebGLContextBoundObject { friend class WebGLContext; public:
--- a/dom/canvas/WebGLVertexArray.cpp +++ b/dom/canvas/WebGLVertexArray.cpp @@ -15,17 +15,17 @@ using namespace mozilla; JSObject* WebGLVertexArray::WrapObject(JSContext *cx) { return dom::WebGLVertexArrayBinding::Wrap(cx, this); } WebGLVertexArray::WebGLVertexArray(WebGLContext* context) - : WebGLBindableName() + : WebGLBindableName<GLenum>() , WebGLContextBoundObject(context) { SetIsDOMBinding(); context->mVertexArrays.insertBack(this); } WebGLVertexArray* WebGLVertexArray::Create(WebGLContext* context)
--- a/dom/canvas/WebGLVertexArray.h +++ b/dom/canvas/WebGLVertexArray.h @@ -16,17 +16,17 @@ #include "mozilla/LinkedList.h" namespace mozilla { class WebGLVertexArrayFake; class WebGLVertexArray : public nsWrapperCache - , public WebGLBindableName + , public WebGLBindableName<GLenum> , public WebGLRefCountedObject<WebGLVertexArray> , public LinkedListElement<WebGLVertexArray> , public WebGLContextBoundObject { // ----------------------------------------------------------------------------- // PUBLIC public: static WebGLVertexArray* Create(WebGLContext* context);
--- a/dom/canvas/moz.build +++ b/dom/canvas/moz.build @@ -48,17 +48,16 @@ UNIFIED_SOURCES += [ 'WebGL2ContextQueries.cpp', 'WebGL2ContextSamplers.cpp', 'WebGL2ContextSync.cpp', 'WebGL2ContextTextures.cpp', 'WebGL2ContextTransformFeedback.cpp', 'WebGL2ContextUniforms.cpp', 'WebGL2ContextVAOs.cpp', 'WebGLActiveInfo.cpp', - 'WebGLBindableName.cpp', 'WebGLBuffer.cpp', 'WebGLContext.cpp', 'WebGLContextAsyncQueries.cpp', 'WebGLContextBuffers.cpp', 'WebGLContextDraw.cpp', 'WebGLContextExtensions.cpp', 'WebGLContextFramebufferOperations.cpp', 'WebGLContextGL.cpp',
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/failing_tests_android.txt +++ /dev/null @@ -1,17 +0,0 @@ -conformance/extensions/oes-texture-float.html -conformance/extensions/oes-vertex-array-object.html -conformance/glsl/functions/glsl-function-abs.html -conformance/glsl/functions/glsl-function-faceforward.html -conformance/glsl/functions/glsl-function-sign.html -conformance/glsl/functions/glsl-function-smoothstep-float.html -conformance/glsl/functions/glsl-function-step-float.html -conformance/glsl/functions/glsl-function-step-gentype.html -conformance/limits/gl-max-texture-dimensions.html -conformance/limits/gl-min-textures.html -conformance/rendering/draw-elements-out-of-bounds.html -conformance/state/gl-get-calls.html -conformance/textures/tex-image-with-format-and-type.html -conformance/textures/tex-sub-image-2d.html -conformance/textures/texture-mips.html -conformance/textures/texture-npot.html -conformance/textures/texture-size-cube-maps.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/failing_tests_android_nvidia.txt +++ /dev/null @@ -1,8 +0,0 @@ -# Failures for our Tegra 2 slaves. - -conformance/extensions/oes-standard-derivatives.html -conformance/glsl/misc/shared.html -conformance/misc/null-object-behaviour.html -conformance/textures/texture-mips.html -conformance/textures/texture-npot.html -conformance/textures/texture-npot-video.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/failing_tests_android_x86.txt +++ /dev/null @@ -1,5 +0,0 @@ -# Failures for our android x86 and arm emulator test environments. - -conformance/extensions/oes-texture-float.html -conformance/programs/get-active-test.html -conformance/textures/texture-npot.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/failing_tests_linux.txt +++ /dev/null @@ -1,5 +0,0 @@ -conformance/misc/uninitialized-test.html -conformance/programs/gl-get-active-attribute.html -conformance/textures/texture-mips.html -conformance/uniforms/gl-uniform-bool.html -conformance/renderbuffers/framebuffer-object-attachment.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/failing_tests_linux_mesa.txt +++ /dev/null @@ -1,3 +0,0 @@ -conformance/textures/texture-size-cube-maps.html -conformance/extensions/oes-texture-float.html -conformance/glsl/functions/glsl-function-sin.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/failing_tests_linux_nvidia.txt +++ /dev/null @@ -1,5 +0,0 @@ -conformance/misc/uninitialized-test.html -conformance/programs/gl-get-active-attribute.html -conformance/textures/texture-mips.html -conformance/uniforms/gl-uniform-bool.html -conformance/renderbuffers/framebuffer-object-attachment.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/failing_tests_mac.txt +++ /dev/null @@ -1,1 +0,0 @@ -conformance/glsl/misc/glsl-function-nodes.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/failing_tests_mac_mtnlion.txt +++ /dev/null @@ -1,4 +0,0 @@ -conformance/glsl/functions/glsl-function-smoothstep-gentype.html -conformance/glsl/variables/gl-pointcoord.html -conformance/limits/gl-max-texture-dimensions.html -conformance/textures/texture-size.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/failing_tests_windows_msbasicrender.txt +++ /dev/null @@ -1,3 +0,0 @@ -conformance/renderbuffers/framebuffer-object-attachment.html -conformance/state/gl-object-get-calls.html -conformance/more/functions/isTests.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/mochitest-conformance-files.ini +++ /dev/null @@ -1,476 +0,0 @@ -[DEFAULT] -support-files = - conformance/00_readme.txt - conformance/00_test_list.txt - conformance/LICENSE_CHROMIUM - conformance/attribs/00_test_list.txt - conformance/attribs/gl-enable-vertex-attrib.html - conformance/attribs/gl-vertex-attrib-zero-issues.html - conformance/attribs/gl-vertex-attrib.html - conformance/attribs/gl-vertexattribpointer-offsets.html - conformance/attribs/gl-vertexattribpointer.html - conformance/buffers/00_test_list.txt - conformance/buffers/buffer-bind-test.html - conformance/buffers/buffer-data-array-buffer.html - conformance/buffers/index-validation-copies-indices.html - conformance/buffers/index-validation-crash-with-buffer-sub-data.html - conformance/buffers/index-validation-verifies-too-many-indices.html - conformance/buffers/index-validation-with-resized-buffer.html - conformance/buffers/index-validation.html - conformance/canvas/00_test_list.txt - conformance/canvas/buffer-offscreen-test.html - conformance/canvas/buffer-preserve-test.html - conformance/canvas/canvas-test.html - conformance/canvas/canvas-zero-size.html - conformance/canvas/drawingbuffer-static-canvas-test.html - conformance/canvas/drawingbuffer-test.html - conformance/canvas/viewport-unchanged-upon-resize.html - conformance/context/00_test_list.txt - conformance/context/constants.html - conformance/context/context-attribute-preserve-drawing-buffer.html - conformance/context/context-attributes-alpha-depth-stencil-antialias.html - conformance/context/context-lost-restored.html - conformance/context/context-lost.html - conformance/context/context-type-test.html - conformance/context/incorrect-context-object-behaviour.html - conformance/context/methods.html - conformance/context/premultiplyalpha-test.html - conformance/context/resource-sharing-test.html - conformance/extensions/00_test_list.txt - conformance/extensions/ext-sRGB.html - conformance/extensions/ext-texture-filter-anisotropic.html - conformance/extensions/ext-shader-texture-lod.html - conformance/extensions/oes-standard-derivatives.html - conformance/extensions/oes-texture-float.html - conformance/extensions/oes-vertex-array-object.html - conformance/extensions/webgl-compressed-texture-etc1.html - conformance/extensions/webgl-compressed-texture-s3tc.html - conformance/extensions/webgl-debug-renderer-info.html - conformance/extensions/webgl-debug-shaders.html - conformance/extensions/webgl-depth-texture.html - conformance/glsl/00_test_list.txt - conformance/glsl/functions/00_test_list.txt - conformance/glsl/functions/glsl-function-abs.html - conformance/glsl/functions/glsl-function-acos.html - conformance/glsl/functions/glsl-function-asin.html - conformance/glsl/functions/glsl-function-atan-xy.html - conformance/glsl/functions/glsl-function-atan.html - conformance/glsl/functions/glsl-function-ceil.html - conformance/glsl/functions/glsl-function-clamp-float.html - conformance/glsl/functions/glsl-function-clamp-gentype.html - conformance/glsl/functions/glsl-function-cos.html - conformance/glsl/functions/glsl-function-cross.html - conformance/glsl/functions/glsl-function-distance.html - conformance/glsl/functions/glsl-function-dot.html - conformance/glsl/functions/glsl-function-faceforward.html - conformance/glsl/functions/glsl-function-floor.html - conformance/glsl/functions/glsl-function-fract.html - conformance/glsl/functions/glsl-function-length.html - conformance/glsl/functions/glsl-function-lessThan.html - conformance/glsl/functions/glsl-function-max-float.html - conformance/glsl/functions/glsl-function-max-gentype.html - conformance/glsl/functions/glsl-function-min-float.html - conformance/glsl/functions/glsl-function-min-gentype.html - conformance/glsl/functions/glsl-function-mix-float.html - conformance/glsl/functions/glsl-function-mix-gentype.html - conformance/glsl/functions/glsl-function-mod-float.html - conformance/glsl/functions/glsl-function-mod-gentype.html - conformance/glsl/functions/glsl-function-normalize.html - conformance/glsl/functions/glsl-function-reflect.html - conformance/glsl/functions/glsl-function-refract.html - conformance/glsl/functions/glsl-function-sign.html - conformance/glsl/functions/glsl-function-sin.html - conformance/glsl/functions/glsl-function-smoothstep-float.html - conformance/glsl/functions/glsl-function-smoothstep-gentype.html - conformance/glsl/functions/glsl-function-step-float.html - conformance/glsl/functions/glsl-function-step-gentype.html - conformance/glsl/functions/glsl-function.html - conformance/glsl/implicit/00_test_list.txt - conformance/glsl/implicit/add_int_float.vert.html - conformance/glsl/implicit/add_int_mat2.vert.html - conformance/glsl/implicit/add_int_mat3.vert.html - conformance/glsl/implicit/add_int_mat4.vert.html - conformance/glsl/implicit/add_int_vec2.vert.html - conformance/glsl/implicit/add_int_vec3.vert.html - conformance/glsl/implicit/add_int_vec4.vert.html - conformance/glsl/implicit/add_ivec2_vec2.vert.html - conformance/glsl/implicit/add_ivec3_vec3.vert.html - conformance/glsl/implicit/add_ivec4_vec4.vert.html - conformance/glsl/implicit/assign_int_to_float.vert.html - conformance/glsl/implicit/assign_ivec2_to_vec2.vert.html - conformance/glsl/implicit/assign_ivec3_to_vec3.vert.html - conformance/glsl/implicit/assign_ivec4_to_vec4.vert.html - conformance/glsl/implicit/construct_struct.vert.html - conformance/glsl/implicit/divide_int_float.vert.html - conformance/glsl/implicit/divide_int_mat2.vert.html - conformance/glsl/implicit/divide_int_mat3.vert.html - conformance/glsl/implicit/divide_int_mat4.vert.html - conformance/glsl/implicit/divide_int_vec2.vert.html - conformance/glsl/implicit/divide_int_vec3.vert.html - conformance/glsl/implicit/divide_int_vec4.vert.html - conformance/glsl/implicit/divide_ivec2_vec2.vert.html - conformance/glsl/implicit/divide_ivec3_vec3.vert.html - conformance/glsl/implicit/divide_ivec4_vec4.vert.html - conformance/glsl/implicit/equal_int_float.vert.html - conformance/glsl/implicit/equal_ivec2_vec2.vert.html - conformance/glsl/implicit/equal_ivec3_vec3.vert.html - conformance/glsl/implicit/equal_ivec4_vec4.vert.html - conformance/glsl/implicit/function_int_float.vert.html - conformance/glsl/implicit/function_ivec2_vec2.vert.html - conformance/glsl/implicit/function_ivec3_vec3.vert.html - conformance/glsl/implicit/function_ivec4_vec4.vert.html - conformance/glsl/implicit/greater_than.vert.html - conformance/glsl/implicit/greater_than_equal.vert.html - conformance/glsl/implicit/less_than.vert.html - conformance/glsl/implicit/less_than_equal.vert.html - conformance/glsl/implicit/multiply_int_float.vert.html - conformance/glsl/implicit/multiply_int_mat2.vert.html - conformance/glsl/implicit/multiply_int_mat3.vert.html - conformance/glsl/implicit/multiply_int_mat4.vert.html - conformance/glsl/implicit/multiply_int_vec2.vert.html - conformance/glsl/implicit/multiply_int_vec3.vert.html - conformance/glsl/implicit/multiply_int_vec4.vert.html - conformance/glsl/implicit/multiply_ivec2_vec2.vert.html - conformance/glsl/implicit/multiply_ivec3_vec3.vert.html - conformance/glsl/implicit/multiply_ivec4_vec4.vert.html - conformance/glsl/implicit/not_equal_int_float.vert.html - conformance/glsl/implicit/not_equal_ivec2_vec2.vert.html - conformance/glsl/implicit/not_equal_ivec3_vec3.vert.html - conformance/glsl/implicit/not_equal_ivec4_vec4.vert.html - conformance/glsl/implicit/subtract_int_float.vert.html - conformance/glsl/implicit/subtract_int_mat2.vert.html - conformance/glsl/implicit/subtract_int_mat3.vert.html - conformance/glsl/implicit/subtract_int_mat4.vert.html - conformance/glsl/implicit/subtract_int_vec2.vert.html - conformance/glsl/implicit/subtract_int_vec3.vert.html - conformance/glsl/implicit/subtract_int_vec4.vert.html - conformance/glsl/implicit/subtract_ivec2_vec2.vert.html - conformance/glsl/implicit/subtract_ivec3_vec3.vert.html - conformance/glsl/implicit/subtract_ivec4_vec4.vert.html - conformance/glsl/implicit/ternary_int_float.vert.html - conformance/glsl/implicit/ternary_ivec2_vec2.vert.html - conformance/glsl/implicit/ternary_ivec3_vec3.vert.html - conformance/glsl/implicit/ternary_ivec4_vec4.vert.html - conformance/glsl/matrices/00_test_list.txt - conformance/glsl/matrices/glsl-mat4-to-mat3.html - conformance/glsl/misc/00_test_list.txt - conformance/glsl/misc/attrib-location-length-limits.html - conformance/glsl/misc/embedded-struct-definitions-forbidden.html - conformance/glsl/misc/glsl-2types-of-textures-on-same-unit.html - conformance/glsl/misc/glsl-function-nodes.html - conformance/glsl/misc/glsl-long-variable-names.html - conformance/glsl/misc/glsl-vertex-branch.html - conformance/glsl/misc/include.vs - conformance/glsl/misc/non-ascii-comments.vert.html - conformance/glsl/misc/non-ascii.vert.html - conformance/glsl/misc/re-compile-re-link.html - conformance/glsl/misc/shader-with-256-character-identifier.frag.html - conformance/glsl/misc/shader-with-257-character-identifier.frag.html - conformance/glsl/misc/shader-with-_webgl-identifier.vert.html - conformance/glsl/misc/shader-with-arbitrary-indexing.frag.html - conformance/glsl/misc/shader-with-arbitrary-indexing.vert.html - conformance/glsl/misc/shader-with-attrib-array.vert.html - conformance/glsl/misc/shader-with-attrib-struct.vert.html - conformance/glsl/misc/shader-with-clipvertex.vert.html - conformance/glsl/misc/shader-with-comma-assignment.html - conformance/glsl/misc/shader-with-comma-conditional-assignment.html - conformance/glsl/misc/shader-with-conditional-scoping.html - conformance/glsl/misc/shader-with-default-precision.frag.html - conformance/glsl/misc/shader-with-default-precision.vert.html - conformance/glsl/misc/shader-with-define-line-continuation.frag.html - conformance/glsl/misc/shader-with-dfdx-no-ext.frag.html - conformance/glsl/misc/shader-with-dfdx.frag.html - conformance/glsl/misc/shader-with-do-scoping.html - conformance/glsl/misc/shader-with-error-directive.html - conformance/glsl/misc/shader-with-explicit-int-cast.vert.html - conformance/glsl/misc/shader-with-float-return-value.frag.html - conformance/glsl/misc/shader-with-for-loop.html - conformance/glsl/misc/shader-with-for-scoping.html - conformance/glsl/misc/shader-with-frag-depth.frag.html - conformance/glsl/misc/shader-with-function-recursion.frag.html - conformance/glsl/misc/shader-with-function-scoped-struct.html - conformance/glsl/misc/shader-with-functional-scoping.html - conformance/glsl/misc/shader-with-glcolor.vert.html - conformance/glsl/misc/shader-with-gles-1.frag.html - conformance/glsl/misc/shader-with-gles-symbol.frag.html - conformance/glsl/misc/shader-with-glprojectionmatrix.vert.html - conformance/glsl/misc/shader-with-hex-int-constant-macro.html - conformance/glsl/misc/shader-with-implicit-vec3-to-vec4-cast.vert.html - conformance/glsl/misc/shader-with-include.vert.html - conformance/glsl/misc/shader-with-int-return-value.frag.html - conformance/glsl/misc/shader-with-invalid-identifier.frag.html - conformance/glsl/misc/shader-with-ivec2-return-value.frag.html - conformance/glsl/misc/shader-with-ivec3-return-value.frag.html - conformance/glsl/misc/shader-with-ivec4-return-value.frag.html - conformance/glsl/misc/shader-with-limited-indexing.frag.html - conformance/glsl/misc/shader-with-line-directive.html - conformance/glsl/misc/shader-with-long-line.html - conformance/glsl/misc/shader-with-non-ascii-error.frag.html - conformance/glsl/misc/shader-with-precision.frag.html - conformance/glsl/misc/shader-with-quoted-error.frag.html - conformance/glsl/misc/shader-with-undefined-preprocessor-symbol.frag.html - conformance/glsl/misc/shader-with-uniform-in-loop-condition.vert.html - conformance/glsl/misc/shader-with-vec2-return-value.frag.html - conformance/glsl/misc/shader-with-vec3-return-value.frag.html - conformance/glsl/misc/shader-with-vec4-return-value.frag.html - conformance/glsl/misc/shader-with-vec4-vec3-vec4-conditional.html - conformance/glsl/misc/shader-with-version-100.frag.html - conformance/glsl/misc/shader-with-version-100.vert.html - conformance/glsl/misc/shader-with-version-120.vert.html - conformance/glsl/misc/shader-with-version-130.vert.html - conformance/glsl/misc/shader-with-webgl-identifier.vert.html - conformance/glsl/misc/shader-without-precision.frag.html - conformance/glsl/misc/shared.html - conformance/glsl/misc/struct-nesting-exceeds-maximum.html - conformance/glsl/misc/struct-nesting-under-maximum.html - conformance/glsl/misc/uniform-location-length-limits.html - conformance/glsl/reserved/00_test_list.txt - conformance/glsl/reserved/_webgl_field.vert.html - conformance/glsl/reserved/_webgl_function.vert.html - conformance/glsl/reserved/_webgl_struct.vert.html - conformance/glsl/reserved/_webgl_variable.vert.html - conformance/glsl/reserved/webgl_field.vert.html - conformance/glsl/reserved/webgl_function.vert.html - conformance/glsl/reserved/webgl_struct.vert.html - conformance/glsl/reserved/webgl_variable.vert.html - conformance/glsl/samplers/00_test_list.txt - conformance/glsl/samplers/glsl-function-texture2d-bias.html - conformance/glsl/samplers/glsl-function-texture2dlod.html - conformance/glsl/samplers/glsl-function-texture2dproj.html - conformance/glsl/variables/00_test_list.txt - conformance/glsl/variables/gl-fragcoord.html - conformance/glsl/variables/gl-frontfacing.html - conformance/glsl/variables/gl-pointcoord.html - conformance/limits/00_test_list.txt - conformance/limits/gl-max-texture-dimensions.html - conformance/limits/gl-min-attribs.html - conformance/limits/gl-min-textures.html - conformance/limits/gl-min-uniforms.html - conformance/misc/00_test_list.txt - conformance/misc/bad-arguments-test.html - conformance/misc/delayed-drawing.html - conformance/misc/error-reporting.html - conformance/misc/functions-returning-strings.html - conformance/misc/instanceof-test.html - conformance/misc/invalid-passed-params.html - conformance/misc/is-object.html - conformance/misc/null-object-behaviour.html - conformance/misc/object-deletion-behaviour.html - conformance/misc/shader-precision-format.html - conformance/misc/type-conversion-test.html - conformance/misc/uninitialized-test.html - conformance/misc/webgl-specific.html - conformance/more/00_test_list.txt - conformance/more/README.md - conformance/more/all_tests.html - conformance/more/all_tests_linkonly.html - conformance/more/all_tests_sequential.html - conformance/more/conformance/argGenerators-A.js - conformance/more/conformance/argGenerators-B1.js - conformance/more/conformance/argGenerators-B2.js - conformance/more/conformance/argGenerators-B3.js - conformance/more/conformance/argGenerators-B4.js - conformance/more/conformance/argGenerators-C.js - conformance/more/conformance/argGenerators-D_G.js - conformance/more/conformance/argGenerators-G_I.js - conformance/more/conformance/argGenerators-L_S.js - conformance/more/conformance/argGenerators-S_V.js - conformance/more/conformance/badArgsArityLessThanArgc.html - conformance/more/conformance/constants.html - conformance/more/conformance/fuzzTheAPI.html - conformance/more/conformance/getContext.html - conformance/more/conformance/methods.html - conformance/more/conformance/quickCheckAPI-A.html - conformance/more/conformance/quickCheckAPI-B1.html - conformance/more/conformance/quickCheckAPI-B2.html - conformance/more/conformance/quickCheckAPI-B3.html - conformance/more/conformance/quickCheckAPI-B4.html - conformance/more/conformance/quickCheckAPI-C.html - conformance/more/conformance/quickCheckAPI-D_G.html - conformance/more/conformance/quickCheckAPI-G_I.html - conformance/more/conformance/quickCheckAPI-L_S.html - conformance/more/conformance/quickCheckAPI-S_V.html - conformance/more/conformance/quickCheckAPI.js - conformance/more/conformance/quickCheckAPIBadArgs.html - conformance/more/conformance/webGLArrays.html - conformance/more/demos/opengl_web.html - conformance/more/demos/video.html - conformance/more/functions/bindBuffer.html - conformance/more/functions/bindBufferBadArgs.html - conformance/more/functions/bindFramebufferLeaveNonZero.html - conformance/more/functions/bufferData.html - conformance/more/functions/bufferDataBadArgs.html - conformance/more/functions/bufferSubData.html - conformance/more/functions/bufferSubDataBadArgs.html - conformance/more/functions/copyTexImage2D.html - conformance/more/functions/copyTexImage2DBadArgs.html - conformance/more/functions/copyTexSubImage2D.html - conformance/more/functions/copyTexSubImage2DBadArgs.html - conformance/more/functions/deleteBufferBadArgs.html - conformance/more/functions/drawArrays.html - conformance/more/functions/drawArraysOutOfBounds.html - conformance/more/functions/drawElements.html - conformance/more/functions/drawElementsBadArgs.html - conformance/more/functions/isTests.html - conformance/more/functions/readPixels.html - conformance/more/functions/readPixelsBadArgs.html - conformance/more/functions/texImage2D.html - conformance/more/functions/texImage2DBadArgs.html - conformance/more/functions/texImage2DHTML.html - conformance/more/functions/texImage2DHTMLBadArgs.html - conformance/more/functions/texSubImage2D.html - conformance/more/functions/texSubImage2DBadArgs.html - conformance/more/functions/texSubImage2DHTML.html - conformance/more/functions/texSubImage2DHTMLBadArgs.html - conformance/more/functions/uniformMatrix.html - conformance/more/functions/uniformMatrixBadArgs.html - conformance/more/functions/uniformf.html - conformance/more/functions/uniformfArrayLen1.html - conformance/more/functions/uniformfBadArgs.html - conformance/more/functions/uniformi.html - conformance/more/functions/uniformiBadArgs.html - conformance/more/functions/vertexAttrib.html - conformance/more/functions/vertexAttribBadArgs.html - conformance/more/functions/vertexAttribPointer.html - conformance/more/functions/vertexAttribPointerBadArgs.html - conformance/more/glsl/arrayOutOfBounds.html - conformance/more/glsl/longLoops.html - conformance/more/glsl/uniformOutOfBounds.html - conformance/more/glsl/unusedAttribsUniforms.html - conformance/more/index.html - conformance/more/performance/CPUvsGPU.html - conformance/more/performance/bandwidth.html - conformance/more/performance/jsGCPause.html - conformance/more/performance/jsMatrixMult.html - conformance/more/performance/jsToGLOverhead.html - conformance/more/unit.css - conformance/more/unit.js - conformance/more/util.js - conformance/programs/00_test_list.txt - conformance/programs/get-active-test.html - conformance/programs/gl-bind-attrib-location-test.html - conformance/programs/gl-get-active-attribute.html - conformance/programs/gl-get-active-uniform.html - conformance/programs/gl-getshadersource.html - conformance/programs/gl-shader-test.html - conformance/programs/invalid-UTF-16.html - conformance/programs/program-test.html - conformance/reading/00_test_list.txt - conformance/reading/read-pixels-pack-alignment.html - conformance/reading/read-pixels-test.html - conformance/renderbuffers/00_test_list.txt - conformance/renderbuffers/framebuffer-object-attachment.html - conformance/renderbuffers/framebuffer-test.html - conformance/renderbuffers/renderbuffer-initialization.html - conformance/rendering/00_test_list.txt - conformance/rendering/draw-arrays-out-of-bounds.html - conformance/rendering/draw-elements-out-of-bounds.html - conformance/rendering/gl-clear.html - conformance/rendering/gl-drawelements.html - conformance/rendering/gl-scissor-test.html - conformance/rendering/line-loop-tri-fan.html - conformance/rendering/more-than-65536-indices.html - conformance/rendering/point-size.html - conformance/rendering/triangle.html - conformance/resources/3x3.png - conformance/resources/blue-1x1.jpg - conformance/resources/boolUniformShader.vert - conformance/resources/bug-32888-texture.png - conformance/resources/floatUniformShader.vert - conformance/resources/fragmentShader.frag - conformance/resources/glsl-conformance-test.js - conformance/resources/glsl-feature-tests.css - conformance/resources/glsl-generator.js - conformance/resources/gray-ramp-256-with-128-alpha.png - conformance/resources/gray-ramp-256.png - conformance/resources/gray-ramp-default-gamma.png - conformance/resources/gray-ramp-gamma0.1.png - conformance/resources/gray-ramp-gamma1.0.png - conformance/resources/gray-ramp-gamma2.0.png - conformance/resources/gray-ramp-gamma4.0.png - conformance/resources/gray-ramp-gamma9.0.png - conformance/resources/gray-ramp.png - conformance/resources/green-2x2-16bit.png - conformance/resources/intArrayUniformShader.vert - conformance/resources/intUniformShader.vert - conformance/resources/matUniformShader.vert - conformance/resources/noopUniformShader.frag - conformance/resources/noopUniformShader.vert - conformance/resources/npot-video.mp4 - conformance/resources/npot-video.theora.ogv - conformance/resources/npot-video.webmvp8.webm - conformance/resources/pnglib.js - conformance/resources/red-green.mp4 - conformance/resources/red-green.png - conformance/resources/red-green.theora.ogv - conformance/resources/red-green.webmvp8.webm - conformance/resources/red-indexed.png - conformance/resources/samplerUniformShader.frag - conformance/resources/small-square-with-cie-rgb-profile.png - conformance/resources/small-square-with-colormatch-profile.png - conformance/resources/small-square-with-colorspin-profile.jpg - conformance/resources/small-square-with-colorspin-profile.png - conformance/resources/small-square-with-e-srgb-profile.png - conformance/resources/small-square-with-smpte-c-profile.png - conformance/resources/small-square-with-srgb-iec61966-2.1-profile.png - conformance/resources/structUniformShader.vert - conformance/resources/vertexShader.vert - conformance/resources/webgl-test-utils.js - conformance/resources/webgl-test.js - conformance/resources/zero-alpha.png - conformance/state/00_test_list.txt - conformance/state/gl-enable-enum-test.html - conformance/state/gl-enum-tests.html - conformance/state/gl-get-calls.html - conformance/state/gl-geterror.html - conformance/state/gl-getstring.html - conformance/state/gl-object-get-calls.html - conformance/textures/00_test_list.txt - conformance/textures/compressed-tex-image.html - conformance/textures/copy-tex-image-and-sub-image-2d.html - conformance/textures/gl-pixelstorei.html - conformance/textures/gl-teximage.html - conformance/textures/origin-clean-conformance.html - conformance/textures/tex-image-and-sub-image-2d-with-array-buffer-view.html - conformance/textures/tex-image-and-sub-image-2d-with-canvas.html - conformance/textures/tex-image-and-sub-image-2d-with-image-data.html - conformance/textures/tex-image-and-sub-image-2d-with-image.html - conformance/textures/tex-image-and-sub-image-2d-with-video.html - conformance/textures/tex-image-and-uniform-binding-bugs.html - conformance/textures/tex-image-with-format-and-type.html - conformance/textures/tex-image-with-invalid-data.html - conformance/textures/tex-input-validation.html - conformance/textures/tex-sub-image-2d-bad-args.html - conformance/textures/tex-sub-image-2d.html - conformance/textures/texparameter-test.html - conformance/textures/texture-active-bind-2.html - conformance/textures/texture-active-bind.html - conformance/textures/texture-clear.html - conformance/textures/texture-complete.html - conformance/textures/texture-formats-test.html - conformance/textures/texture-mips.html - conformance/textures/texture-npot-video.html - conformance/textures/texture-npot.html - conformance/textures/texture-size-cube-maps.html - conformance/textures/texture-size.html - conformance/textures/texture-transparent-pixels-initialized.html - conformance/typedarrays/00_test_list.txt - conformance/typedarrays/array-buffer-crash.html - conformance/typedarrays/array-buffer-view-crash.html - conformance/typedarrays/array-unit-tests.html - conformance/uniforms/00_test_list.txt - conformance/uniforms/gl-uniform-arrays.html - conformance/uniforms/gl-uniform-bool.html - conformance/uniforms/gl-uniformmatrix4fv.html - conformance/uniforms/gl-unknown-uniform.html - conformance/uniforms/null-uniform-location.html - conformance/uniforms/uniform-location.html - conformance/uniforms/uniform-samplers-test.html - resources/cors-util.js - resources/desktop-gl-constants.js - resources/js-test-pre.js - resources/js-test-style.css - resources/opengl_logo.jpg - resources/thunderbird-logo-64x64.png - resources/webgl-logo.png - resources/webgl-test-harness.js
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/mochitest.ini +++ /dev/null @@ -1,22 +0,0 @@ -[DEFAULT] -skip-if = e10s -support-files = - 00_test_list.txt - failing_tests_android.txt - failing_tests_android_nvidia.txt - failing_tests_android_x86.txt - failing_tests_linux.txt - failing_tests_linux_mesa.txt - failing_tests_linux_nvidia.txt - failing_tests_mac.txt - failing_tests_mac_mtnlion.txt - failing_tests_windows.txt - failing_tests_windows_msbasicrender.txt - skipped_tests_android.txt - skipped_tests_android_x86.txt - skipped_tests_linux_mesa.txt - skipped_tests_win_vista.txt - skipped_tests_winxp.txt - -[test_webgl_conformance_test_suite.html] -skip-if = buildapp == 'mulet' || buildapp == 'b2g' # bug 865443- separate suite - the non_conf* tests pass except for one on armv6 tests
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/skipped_tests_android.txt +++ /dev/null @@ -1,14 +0,0 @@ -conformance/misc/uninitialized-test.html -conformance/renderbuffers/framebuffer-object-attachment.html -conformance/textures/texture-size.html -conformance/more/conformance/quickCheckAPI-A.html -conformance/more/conformance/quickCheckAPI-B1.html -conformance/more/conformance/quickCheckAPI-B2.html -conformance/more/conformance/quickCheckAPI-B3.html -conformance/more/conformance/quickCheckAPI-B4.html -conformance/more/conformance/quickCheckAPIBadArgs.html -conformance/more/conformance/quickCheckAPI-C.html -conformance/more/conformance/quickCheckAPI-D_G.html -conformance/more/conformance/quickCheckAPI-G_I.html -conformance/more/conformance/quickCheckAPI-L_S.html -conformance/more/conformance/quickCheckAPI-S_V.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/skipped_tests_android_x86.txt +++ /dev/null @@ -1,35 +0,0 @@ -conformance/extensions/oes-vertex-array-object.html -conformance/glsl/functions/glsl-function-abs.html -conformance/glsl/functions/glsl-function-faceforward.html -conformance/glsl/functions/glsl-function-sign.html -conformance/glsl/functions/glsl-function-sin.html -conformance/glsl/functions/glsl-function-step-float.html -conformance/glsl/functions/glsl-function-step-gentype.html -conformance/glsl/functions/glsl-function-smoothstep-float.html -conformance/limits/gl-max-texture-dimensions.html -conformance/limits/gl-min-textures.html -conformance/misc/error-reporting.html -conformance/misc/object-deletion-behaviour.html -conformance/misc/type-conversion-test.html -conformance/reading/read-pixels-test.html -conformance/renderbuffers/framebuffer-object-attachment.html -conformance/textures/gl-teximage.html -conformance/textures/origin-clean-conformance.html -conformance/textures/tex-image-and-sub-image-2d-with-image.html -conformance/textures/tex-image-and-sub-image-2d-with-video.html -conformance/textures/tex-image-and-sub-image-2d-with-array-buffer-view.html -conformance/textures/texture-mips.html -conformance/textures/texture-npot-video.html -conformance/textures/texture-size.html -conformance/textures/texture-size-cube-maps.html -conformance/more/conformance/quickCheckAPI-A.html -conformance/more/conformance/quickCheckAPI-B1.html -conformance/more/conformance/quickCheckAPI-B2.html -conformance/more/conformance/quickCheckAPI-B3.html -conformance/more/conformance/quickCheckAPI-B4.html -conformance/more/conformance/quickCheckAPIBadArgs.html -conformance/more/conformance/quickCheckAPI-C.html -conformance/more/conformance/quickCheckAPI-D_G.html -conformance/more/conformance/quickCheckAPI-G_I.html -conformance/more/conformance/quickCheckAPI-L_S.html -conformance/more/conformance/quickCheckAPI-S_V.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/skipped_tests_linux.txt +++ /dev/null @@ -1,11 +0,0 @@ -conformance/more/conformance/quickCheckAPI-A.html -conformance/more/conformance/quickCheckAPI-B1.html -conformance/more/conformance/quickCheckAPI-B2.html -conformance/more/conformance/quickCheckAPI-B3.html -conformance/more/conformance/quickCheckAPI-B4.html -conformance/more/conformance/quickCheckAPIBadArgs.html -conformance/more/conformance/quickCheckAPI-C.html -conformance/more/conformance/quickCheckAPI-D_G.html -conformance/more/conformance/quickCheckAPI-G_I.html -conformance/more/conformance/quickCheckAPI-L_S.html -conformance/more/conformance/quickCheckAPI-S_V.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/skipped_tests_linux_mesa.txt +++ /dev/null @@ -1,15 +0,0 @@ -conformance/limits/gl-max-texture-dimensions.html -conformance/misc/type-conversion-test.html -conformance/reading/read-pixels-test.html -conformance/textures/texture-mips.html -conformance/more/conformance/quickCheckAPI-A.html -conformance/more/conformance/quickCheckAPI-B1.html -conformance/more/conformance/quickCheckAPI-B2.html -conformance/more/conformance/quickCheckAPI-B3.html -conformance/more/conformance/quickCheckAPI-B4.html -conformance/more/conformance/quickCheckAPIBadArgs.html -conformance/more/conformance/quickCheckAPI-C.html -conformance/more/conformance/quickCheckAPI-D_G.html -conformance/more/conformance/quickCheckAPI-G_I.html -conformance/more/conformance/quickCheckAPI-L_S.html -conformance/more/conformance/quickCheckAPI-S_V.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/skipped_tests_win_vista.txt +++ /dev/null @@ -1,2 +0,0 @@ -conformance/textures/tex-image-and-sub-image-2d-with-video.html -conformance/textures/texture-npot-video.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/skipped_tests_winxp.txt +++ /dev/null @@ -1,3 +0,0 @@ -conformance/more/conformance/quickCheckAPI-B2.html -conformance/more/conformance/quickCheckAPI-B3.html -conformance/more/functions/bufferSubDataBadArgs.html
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/test_webgl_conformance_test_suite.html +++ /dev/null @@ -1,653 +0,0 @@ -<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" - "http://www.w3.org/TR/html4/loose.dtd"> -<html> -<head> -<title> -Mochitest version of the WebGL Conformance Test Suite -</title> -<script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script> -<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/> -<script type="text/javascript" src="resources/webgl-test-harness.js"></script> -<script> - -var CONFORMANCE_TEST_VERSION = "1.0.1 (beta)"; - -var OPTIONS = { - version: CONFORMANCE_TEST_VERSION -}; - -/** - * This is copied from webgl-test-harness.js where it is defined as a private function, not accessible to us (argh!) - * - * Loads text from an external file. This function is synchronous. - * @param {string} url The url of the external file. - * @return {string} the loaded text if the request is synchronous. - */ - var loadTextFileSynchronous = function (url) { - var error = 'loadTextFileSynchronous failed to load url "' + url + '"'; - var request; - if (window.XMLHttpRequest) { - request = new XMLHttpRequest(); - if (request.overrideMimeType) { - request.overrideMimeType('text/plain'); - } - } else { - throw 'XMLHttpRequest is disabled'; - } - request.open('GET', url, false); - request.send(null); - if (request.readyState != 4) { - throw error; - } - if (request.status >= 400) { - // Error response, probably a 404. - throw 'Error: request.status: ' + request.status; - } - return request.responseText; - }; - -SimpleTest.waitForExplicitFinish(); - -function detectDriverInfo() { - const Cc = SpecialPowers.Cc; - const Ci = SpecialPowers.Ci; - var doc = Cc["@mozilla.org/xmlextras/domparser;1"].createInstance(Ci.nsIDOMParser).parseFromString("<html/>", "text/html"); - - var canvas = doc.createElement("canvas"); - canvas.width = 1; - canvas.height = 1; - - var type = ""; - var gl; - try { - gl = canvas.getContext("experimental-webgl"); - } catch(e) { - ok(false, "Failed to create a WebGL context for getting driver info."); - return ["", ""] - } - var ext = gl.getExtension("WEBGL_debug_renderer_info"); - // this extension is unconditionally available to chrome. No need to check. - - var webglRenderer = gl.getParameter(ext.UNMASKED_RENDERER_WEBGL); - var webglVendor = gl.getParameter(ext.UNMASKED_VENDOR_WEBGL); - return [webglVendor, webglRenderer]; -} - -function start() { - var OS_WINDOWS = 'windows'; - var OS_MAC = 'mac'; - var OS_LINUX = 'linux'; - var OS_ANDROID = 'android'; - - var GLDRIVER_MESA = 'mesa'; - var GLDRIVER_NVIDIA = 'nvidia'; - var GLDRIVER_X86EMULATOR = 'android x86 emulator'; - var GLDRIVER_MSBASICRENDER = 'Microsoft Basic Render Driver'; - - var kOS = null; - var kOSVersion = null; - var kGLDriver = null; - - if (navigator.platform.indexOf('Win') == 0) { - kOS = OS_WINDOWS; - - // code borrowed from browser/modules/test/browser_taskbar_preview.js - var version = SpecialPowers.Services.sysinfo.getProperty('version'); - kOSVersion = parseFloat(version); - // Version 6.0 is Vista, 6.1 is 7. - } else if (navigator.platform.indexOf('Mac') == 0) { - kOS = OS_MAC; - - var versionMatch = /Mac OS X (\d+.\d+)/.exec(navigator.userAgent); - kOSVersion = versionMatch ? parseFloat(versionMatch[1]) : null; - } else if (navigator.appVersion.indexOf('Android') != -1) { - kOS = OS_ANDROID; - } else if (navigator.platform.indexOf('Linux') == 0) { - // Must be checked after android, as android also has a 'Linux' platform string. - kOS = OS_LINUX; - } - - var glVendor, glRenderer; - [glVendor, glRenderer] = detectDriverInfo(); - info('GL vendor: ' + glVendor); - info('GL renderer: ' + glRenderer); - - if (glRenderer.contains('Android Emulator')) { - kGLDriver = GLDRIVER_X86EMULATOR; - } else if (glRenderer.contains('llvmpipe')) { - kGLDriver = GLDRIVER_MESA; - } else if (glVendor.contains('NVIDIA')) { - kGLDriver = GLDRIVER_NVIDIA; - } else if (glRenderer.contains(GLDRIVER_MSBASICRENDER)) { - kGLDriver = GLDRIVER_MSBASICRENDER; - } - - if (kOS) { - info('OS detected as: ' + kOS); - info(' Version: ' + kOSVersion); - } else { - info('OS not detected.'); - info(' `platform`: ' + navigator.platform); - info(' `appVersion`: ' + navigator.appVersion); - info(' `userAgent`: ' + navigator.userAgent); - } - if (kGLDriver) { - info('GL driver detected as: ' + kGLDriver); - } else { - info('GL driver not detected.'); - } - - var requestLongerTimeoutLen = 3; - if (kOS == OS_ANDROID) - requestLongerTimeoutLen = 6; - - function getEnv(env) { - var envsvc = SpecialPowers.Cc["@mozilla.org/process/environment;1"].getService(SpecialPowers.Ci.nsIEnvironment); - var val = envsvc.get(env); - if (val == "") - return null; - return val; - } - - var reportType = WebGLTestHarnessModule.TestHarness.reportType; - - var Page = function(reporter, url) { - this.reporter = reporter; - this.url = url; - this.totalTests = 0; - this.totalSuccessful = 0; - this.totalTimeouts = 0; - - var li = reporter.localDoc.createElement('li'); - var div = reporter.localDoc.createElement('div'); - var a = reporter.localDoc.createElement('a'); - a.href = url; - var node = reporter.localDoc.createTextNode(url); - a.appendChild(node); - div.appendChild(a); - li.setAttribute('class', 'testpage'); - li.appendChild(div); - var ul = reporter.localDoc.createElement('ul'); - var node = reporter.localDoc.createTextNode(''); - li.appendChild(ul); - div.appendChild(node); - this.totalsElem = node; - this.resultElem = ul; - this.elem = li; - }; - - /** - * Indicates whether this test page results are not to be ignored. - */ - Page.prototype.shouldBeAccountedFor = function() { - return testsToIgnore.indexOf(this.url) == -1; - } - - /** - * Indicates whether all this test page results are expected not to fail, - * if not ignored. - */ - Page.prototype.isExpectedToFullyPass = function() { - return this.shouldBeAccountedFor() && - testsExpectedToFail.indexOf(this.url) == -1; - } - - /** - * Returns log message with added test page url. - */ - Page.prototype.logMsg = function(msg) { - return '[' + this.url + '] ' + msg; - } - - /** - * Reports an individual test result of test page. - */ - Page.prototype.addResult = function(msg, success) { - ++this.totalTests; - if (success === undefined) { - ++this.totalTimeouts; - var result = "timeout"; - var css = "timeout"; - // only few timeouts are actually caught here --- most are caught in finishPage(). - if (this.isExpectedToFullyPass()) { - ok(false, this.logMsg('Test timed out'), msg); - } else { - todo(false, this.logMsg('Test timed out'), msg); - } - } else if (success) { - ++this.totalSuccessful; - var result = "success"; - var css = "success"; - if (this.shouldBeAccountedFor()) { - ok(true, this.logMsg('Test passed'), msg); - } else { - todo(false, this.logMsg('Test passed, but is ignored'), msg); - } - // Don't report individual success to UI, to keep it light. - return; - } else { - var result = "failed"; - var css = "fail"; - if (this.isExpectedToFullyPass()) { - ok(false, this.logMsg('Test failed'), msg); - } else { - todo(false, this.logMsg('Test failed'), msg); - } - } - - var node = this.reporter.localDoc.createTextNode(result + ': ' + msg); - var li = this.reporter.localDoc.createElement('li'); - li.appendChild(node); - li.setAttribute('class', css); - this.resultElem.appendChild(li); - }; - - Page.prototype.startPage = function() { - this.totalTests = 0; - this.totalSuccessful = 0; - this.totalTimeouts = 0; - // remove previous results. - while (this.resultElem.hasChildNodes()) { - this.resultElem.removeChild(this.resultElem.childNodes[0]); - } - this.totalsElem.textContent = ''; - return true; - }; - - /** - * Reports test page result summary. - */ - Page.prototype.finishPage = function(success) { - var msg = ' (' + this.totalSuccessful + ' of ' + - this.totalTests + ' passed)'; - if (success === undefined) { - var css = 'testpagetimeout'; - msg = '(*timeout*)'; - ++this.totalTests; - ++this.totalTimeouts; - // Most timeouts are only caught here --- though a few are (already) caught in addResult(). - if (this.isExpectedToFullyPass()) { - ok(false, this.logMsg('Timeout in this test page')); - } else { - todo(false, this.logMsg('Timeout in this test page')); - } - } else if (this.totalSuccessful != this.totalTests) { - var css = 'testpagefail'; - var totalFailed = this.totalTests - this.totalTimeouts - this.totalSuccessful; - if (this.isExpectedToFullyPass()) { - ok(false, this.logMsg("(WebGL test error) " + totalFailed + ' failure(s) and ' + this.totalTimeouts + ' timeout(s)')); - } else { - todo(false, this.logMsg("(WebGL test error) " + totalFailed + ' failure(s) and ' + this.totalTimeouts + ' timeout(s)')); - } - } else { - var css = 'testpagesuccess'; - if (this.isExpectedToFullyPass()) { - ok(true, this.logMsg('All ' + this.totalSuccessful + ' test(s) passed')); - } else { - if (this.shouldBeAccountedFor()) { - todo(true, this.logMsg('Test page expected to fail, but all ' + this.totalSuccessful + ' tests passed')); - } else { - todo(false, this.logMsg('All ' + this.totalSuccessful + ' test(s) passed, but test page is ignored')); - } - } - } - this.elem.setAttribute('class', css); - this.totalsElem.textContent = msg; - }; - - var Reporter = function() { - this.localDoc = document; - - this.fullResultsElem = document.getElementById("results-default"); - - this.resultElem = document.getElementById("results"); - var node = this.localDoc.createTextNode(''); - this.fullResultsElem.appendChild(node); - this.fullResultsNode = node; - this.iframe = document.getElementById("testframe"); - this.currentPageElem = null; - this.totalPages = 0; - this.pagesByURL = {}; - this.currentPage = null; - this.totalTests = 0; - this.totalSuccessful = 0; - this.totalTimeouts = 0; - }; - - Reporter.prototype.runTest = function(url) { - var page = this.pagesByURL[url]; - page.startPage(); - this.currentPage = page; - this.iframe.src = url; - return result; - }; - - Reporter.prototype.addPage = function(url) { - this.currentPage = new Page(this, url, this.resultElem); - this.resultElem.appendChild(this.currentPage.elem); - ++this.totalPages; - this.pagesByURL[url] = this.currentPage; - }; - - Reporter.prototype.startPage = function(url) { - if (testsToSkip.indexOf(url) != -1) { - info("[" + url + "] (WebGL mochitest) Skipping test page"); - return false; - } - info("[" + url + "] (WebGL mochitest) Starting test page"); - - // Calling garbageCollect before each test page fixes intermittent failures with - // out-of-memory errors, often failing to create a WebGL context. - // The explanation is that the JS engine keeps unreferenced WebGL contexts around - // for too long before GCing (bug 617453), so that during this mochitest dozens of unreferenced - // WebGL contexts can accumulate at a given time. - SpecialPowers.DOMWindowUtils.cycleCollect(); - SpecialPowers.DOMWindowUtils.garbageCollect(); - SpecialPowers.DOMWindowUtils.garbageCollect(); - - var page = this.pagesByURL[url]; - this.currentPage = page; - statusTextNode.textContent = 'Running URL: ' + url; - expectedtofailTextNode.textContent = testsExpectedToFail.length + - ' test pages are expected to fail out of ' + - this.totalPages; - ignoredtestsTextNode.textContent = testsToIgnore.length + - ' test pages have their results ignored'; - return page.startPage(); - }; - - Reporter.prototype.displayStats = function() { - var totalFailed = this.totalTests - this.totalTimeouts - this.totalSuccessful; - this.fullResultsNode.textContent = - this.totalSuccessful + ' passed, ' + - totalFailed + ' failed, ' + - this.totalTimeouts + ' timed out'; - }; - - Reporter.prototype.addResult = function(msg, success) { - if (this.currentPage != null) { - this.currentPage.addResult(msg, success); - } - }; - - Reporter.prototype.finishPage = function(success) { - if (this.currentPage != null) { - this.currentPage.finishPage(success); // must call that first, since this is where totalTimeouts is computed - this.totalTests += this.currentPage.totalTests; - this.totalSuccessful += this.currentPage.totalSuccessful; - this.totalTimeouts += this.currentPage.totalTimeouts; - this.currentPage = null; - this.displayStats(); - } - }; - - Reporter.prototype.finishedTestSuite = function() { - statusTextNode.textContent = 'Finished'; - SimpleTest.finish(); - } - - Reporter.prototype.ready = function() { - statusTextNode.textContent = 'Loaded test lists. Starting tests...'; - window.webglTestHarness.runTests(); - } - - Reporter.prototype.reportFunc = function(type, msg, success) { - switch (type) { - case reportType.ADD_PAGE: - return this.addPage(msg); - case reportType.READY: - return this.ready(); - case reportType.START_PAGE: - return this.startPage(msg); - case reportType.TEST_RESULT: - return this.addResult(msg, success); - case reportType.FINISH_PAGE: - return this.finishPage(success); - case reportType.FINISHED_ALL_TESTS: - this.finishedTestSuite(); - return true; - default: - throw 'unhandled'; - break; - } - }; - - var getURLOptions = function(obj) { - var s = window.location.href; - var q = s.indexOf("?"); - var e = s.indexOf("#"); - if (e < 0) { - e = s.length; - } - var query = s.substring(q + 1, e); - var pairs = query.split("&"); - for (var ii = 0; ii < pairs.length; ++ii) { - var keyValue = pairs[ii].split("="); - var key = keyValue[0]; - var value = decodeURIComponent(keyValue[1]); - obj[key] = value; - } - }; - - getURLOptions(OPTIONS); - - function runTestSuite() { - var reporter = new Reporter(); - - // try to create a dummy WebGL context, just to catch context creation failures once here, - // rather than having them result in 100's of failures (one in each test page) - var ctx; - try { - ctx = document.getElementById("webglcheck-default") - .getContext("experimental-webgl"); - } catch(e) {} - if (!ctx) { - var errmsg = "Can't create a WebGL context"; - reporter.fullResultsNode.textContent = errmsg; - // Workaround for SeaMonkey tinderboxes which don't support WebGL. - if (navigator.userAgent.match(/ SeaMonkey\//)) - todo(false, errmsg + " (This is expected on SeaMonkey (tinderboxes).)"); - else if (SpecialPowers.getBoolPref("webgl.disabled")) - todo(false, errmsg + " (This is expected on when WebGL is disabled)"); - else - ok(false, errmsg); - reporter.finishedTestSuite(); - return; - } - - statusTextNode.textContent = 'Loading test lists...'; - var iframe = document.getElementById("testframe"); - var testHarness = new WebGLTestHarnessModule.TestHarness( - iframe, - '00_test_list.txt', - function(type, msg, success) { - return reporter.reportFunc(type, msg, success); - }, - OPTIONS); - // Make timeout delay much higher when running under valgrind. - testHarness.setTimeoutDelay(20000); - window.webglTestHarness = testHarness; - } - - SimpleTest.requestLongerTimeout(requestLongerTimeoutLen); - SimpleTest.requestFlakyTimeout("We're embedding the WebGL test harness, which uses timeouts internally, so we have to abide. :("); - - var statusElem = document.getElementById("status"); - var statusTextNode = document.createTextNode(''); - statusElem.appendChild(statusTextNode); - - var expectedtofailElem = document.getElementById("expectedtofail"); - var expectedtofailTextNode = document.createTextNode(''); - expectedtofailElem.appendChild(expectedtofailTextNode); - - var ignoredtestsElem = document.getElementById("ignoredtests"); - var ignoredtestsTextNode = document.createTextNode(''); - ignoredtestsElem.appendChild(ignoredtestsTextNode); - - // Windows uses the ANGLE library for rendering. Until everything is perfect, this means a different set of - // failing tests. It's easier to do a platform check for Windows than for ANGLE itself. - // Moreover, we currently also have different tests failing on Mac and on Linux, - // presumably due to differences in the drivers. - var failingTestsFilename = null; - var skippedTestsFilename = null; - switch (kOS) { - case OS_WINDOWS: { - if (kGLDriver == GLDRIVER_MSBASICRENDER) { - failingTestsFilename = 'failing_tests_windows_msbasicrender.txt'; - } else { - failingTestsFilename = 'failing_tests_windows.txt'; - } - - if (kOSVersion >= 6.0) // 6.0 is Vista - skippedTestsFilename = 'skipped_tests_win_vista.txt' - else // XP - skippedTestsFilename = 'skipped_tests_winxp.txt'; - - break; - } - case OS_MAC: { - if (kOSVersion == 10.8) - failingTestsFilename = 'failing_tests_mac_mtnlion.txt'; - else - failingTestsFilename = 'failing_tests_mac.txt'; - - break; - } - case OS_LINUX: { - switch (kGLDriver) { - case GLDRIVER_MESA: - failingTestsFilename = 'failing_tests_linux_mesa.txt'; - skippedTestsFilename = 'skipped_tests_linux_mesa.txt'; - break; - case GLDRIVER_NVIDIA: - failingTestsFilename = 'failing_tests_linux_nvidia.txt'; - break; - default: - failingTestsFilename = 'failing_tests_linux.txt'; - skippedTestsFilename = 'skipped_tests_linux.txt'; - break; - } - break; - } - case OS_ANDROID: { - switch (kGLDriver) { - case GLDRIVER_NVIDIA: - failingTestsFilename = 'failing_tests_android_nvidia.txt'; - skippedTestsFilename = 'skipped_tests_android.txt'; - break; - case GLDRIVER_X86EMULATOR: - failingTestsFilename = 'failing_tests_android_x86.txt'; - skippedTestsFilename = 'skipped_tests_android_x86.txt'; - break; - default: - failingTestsFilename = 'failing_tests_android.txt'; - skippedTestsFilename = 'skipped_tests_android.txt'; - break; - } - break; - } - } - - info('Failing tests file: ' + failingTestsFilename); - info('Skipped tests file: ' + skippedTestsFilename); - - function LoadNewlineSepFile(filename) { - var lines; - try { - lines = loadTextFileSynchronous(filename) - .replace(/\r/g, '') // convert to unix line breaks - .split('\n'); - } - catch(e) { - // Request failed for some reason. - ok(false, 'Loading \'' + filename + '\' failed: ' + e); - return []; - } - - // Remove comments and trim whitespace. - var retLines = []; - for (var i = 0; i < lines.length; i++) { - var line = lines[i]; - line = line.split('#', 1)[0].trim(); - if (!line.length) - continue; - - retLines.push(line); - } - - return retLines; - }; - - var testsExpectedToFail = []; - if (failingTestsFilename) - testsExpectedToFail = LoadNewlineSepFile(failingTestsFilename); - - var testsToSkip = []; - if (skippedTestsFilename) - testsToSkip = LoadNewlineSepFile(skippedTestsFilename); - - var testsToIgnore = []; - - info('Tests to fail: ' + testsExpectedToFail.length + (testsExpectedToFail.length ? ':' : '')); - for (var i = 0; i < testsExpectedToFail.length; i++) { - var test = testsExpectedToFail[i]; - info(' ' + test); - } - info('Tests to skip: ' + testsToSkip.length + (testsToSkip.length ? ':' : '')); - for (var i = 0; i < testsToSkip.length; i++) { - var test = testsToSkip[i]; - info(' ' + test); - } - info('Tests to ignore: ' + testsToIgnore.length + (testsToIgnore.length ? ':' : '')); - for (var i = 0; i < testsToIgnore.length; i++) { - var test = testsToIgnore[i]; - info(' ' + test); - } - - runTestSuite(); -} - -</script> -</head> -<body onload="start();"> -<p id="display"></p> -<div id="content" style="display: none"> - -</div> -<table border="2px"> - <tr style="height: 500px;"> - <td style="width: 500px;"> - <iframe id="testframe" scrolling="no" width="500px" height="500px"></iframe> - </td> - <td> - <table> - <tr> - <td><h4>WebGL Conformance Test Runner</h4></td> - </tr> - <tr> - <td> - <div style="border: 1px"> - <b>Status:</b> <div><span id="status"></span></div><br /> - <b>Results:</b> - <div><span id="results-default"></span></div> - <br /> - <div><span id="expectedtofail"></span></div> - <br /> - <div><span id="ignoredtests"></span></div> - </div> - </td> - </tr> - </table> - </td> - </tr> - <tr> - <td colspan="2"> - <div style="text-align: left; width: 100%; height: 100%; overflow: auto;"> - <div><ul id="results"></ul></div> - </div> - </td> - </tr> -</table> -<canvas id="webglcheck-default" style="display: none;"></canvas> -</body> -</html>
deleted file mode 100644 --- a/dom/canvas/test/webgl-conformance/writemanifest.py +++ /dev/null @@ -1,37 +0,0 @@ -#!/usr/bin/env python -# -# This Source Code Form is subject to the terms of the Mozilla Public -# License, v. 2.0. If a copy of the MPL was not distributed with this -# file, You can obtain one at http://mozilla.org/MPL/2.0/. -# -# Write a Mochitest manifest for WebGL conformance test files. - -import os -from itertools import chain - -CONFORMANCE_DIRS = [ - "conformance", - "resources", -] - -def listfiles(dir, rel): - """List all files in dir recursively, yielding paths - relative to rel. - """ - for root, folders, files in os.walk(dir): - for f in files: - yield os.path.relpath(os.path.join(root, f), rel) - -def writemanifest(): - script_dir = os.path.dirname(__file__) - list_dirs = [os.path.join(script_dir, d) for d in CONFORMANCE_DIRS] - with open(os.path.join(script_dir, 'mochitest-conformance-files.ini'), 'w') as f: - f.write("""[DEFAULT] -support-files = - %s -""" % "\n ".join(sorted(chain.from_iterable(listfiles(d, script_dir) - for d in list_dirs)))) - -if __name__ == '__main__': - writemanifest() -
--- a/dom/plugins/ipc/PluginProcessParent.h +++ b/dom/plugins/ipc/PluginProcessParent.h @@ -6,17 +6,16 @@ #ifndef dom_plugins_PluginProcessParent_h #define dom_plugins_PluginProcessParent_h 1 #include "mozilla/Attributes.h" #include "base/basictypes.h" #include "base/file_path.h" -#include "base/scoped_ptr.h" #include "base/thread.h" #include "base/waitable_event.h" #include "chrome/common/child_process_host.h" #include "mozilla/ipc/GeckoChildProcessHost.h" namespace mozilla { namespace plugins {
--- a/ipc/chromium/moz.build +++ b/ipc/chromium/moz.build @@ -45,17 +45,16 @@ UNIFIED_SOURCES += [ 'src/base/lazy_instance.cc', 'src/base/lock.cc', 'src/base/logging.cc', 'src/base/message_loop.cc', 'src/base/message_pump_default.cc', 'src/base/non_thread_safe.cc', 'src/base/pickle.cc', 'src/base/rand_util.cc', - 'src/base/ref_counted.cc', 'src/base/revocable_store.cc', 'src/base/scoped_temp_dir.cc', 'src/base/string_piece.cc', 'src/base/string_util.cc', 'src/base/thread.cc', 'src/base/thread_collision_warner.cc', 'src/base/time.cc', 'src/base/timer.cc',
deleted file mode 100644 --- a/ipc/chromium/src/base/atomic_ref_count.h +++ /dev/null @@ -1,63 +0,0 @@ -// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -// This is a low level implementation of atomic semantics for reference -// counting. Please use base/ref_counted.h directly instead. - -#ifndef BASE_ATOMIC_REF_COUNT_H_ -#define BASE_ATOMIC_REF_COUNT_H_ - -#include "base/atomicops.h" - -namespace base { - -typedef subtle::Atomic32 AtomicRefCount; - -// Increment a reference count by "increment", which must exceed 0. -inline void AtomicRefCountIncN(volatile AtomicRefCount *ptr, - AtomicRefCount increment) { - subtle::NoBarrier_AtomicIncrement(ptr, increment); -} - -// Decrement a reference count by "decrement", which must exceed 0, -// and return whether the result is non-zero. -// Insert barriers to ensure that state written before the reference count -// became zero will be visible to a thread that has just made the count zero. -inline bool AtomicRefCountDecN(volatile AtomicRefCount *ptr, - AtomicRefCount decrement) { - return subtle::Barrier_AtomicIncrement(ptr, -decrement) != 0; -} - -// Increment a reference count by 1. -inline void AtomicRefCountInc(volatile AtomicRefCount *ptr) { - base::AtomicRefCountIncN(ptr, 1); -} - -// Decrement a reference count by 1 and return whether the result is non-zero. -// Insert barriers to ensure that state written before the reference count -// became zero will be visible to a thread that has just made the count zero. -inline bool AtomicRefCountDec(volatile AtomicRefCount *ptr) { - return base::AtomicRefCountDecN(ptr, 1); -} - -// Return whether the reference count is one. If the reference count is used -// in the conventional way, a refrerence count of 1 implies that the current -// thread owns the reference and no other thread shares it. This call performs -// the test for a reference count of one, and performs the memory barrier -// needed for the owning thread to act on the object, knowing that it has -// exclusive access to the object. -inline bool AtomicRefCountIsOne(volatile AtomicRefCount *ptr) { - return subtle::Acquire_Load(ptr) == 1; -} - -// Return whether the reference count is zero. With conventional object -// referencing counting, the object will be destroyed, so the reference count -// should never be zero. Hence this is generally used for a debug check. -inline bool AtomicRefCountIsZero(volatile AtomicRefCount *ptr) { - return subtle::Acquire_Load(ptr) == 0; -} - -} // namespace base - -#endif // BASE_ATOMIC_REF_COUNT_H_
deleted file mode 100644 --- a/ipc/chromium/src/base/atomic_sequence_num.h +++ /dev/null @@ -1,30 +0,0 @@ -// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_ATOMIC_SEQUENCE_NUM_H_ -#define BASE_ATOMIC_SEQUENCE_NUM_H_ - -#include "base/atomicops.h" -#include "base/basictypes.h" - -namespace base { - -class AtomicSequenceNumber { - public: - AtomicSequenceNumber() : seq_(0) { } - explicit AtomicSequenceNumber(base::LinkerInitialized x) { /* seq_ is 0 */ } - - int GetNext() { - return static_cast<int>( - base::subtle::NoBarrier_AtomicIncrement(&seq_, 1) - 1); - } - - private: - base::subtle::Atomic32 seq_; - DISALLOW_COPY_AND_ASSIGN(AtomicSequenceNumber); -}; - -} // namespace base - -#endif // BASE_ATOMIC_SEQUENCE_NUM_H_
--- a/ipc/chromium/src/base/file_util.h +++ b/ipc/chromium/src/base/file_util.h @@ -22,17 +22,16 @@ #include <stdio.h> #include <stack> #include <string> #include <vector> #include "base/basictypes.h" -#include "base/scoped_ptr.h" #include "base/file_path.h" namespace file_util { //----------------------------------------------------------------------------- // Functions that operate purely on a path string w/o touching the filesystem: // Returns true if the given path ends with a path separator character.
--- a/ipc/chromium/src/base/message_loop.cc +++ b/ipc/chromium/src/base/message_loop.cc @@ -314,17 +314,17 @@ void MessageLoop::PostTask_Helper( } else { DCHECK(delay_ms == 0) << "delay should not be negative"; } // Warning: Don't try to short-circuit, and handle this thread's tasks more // directly, as it could starve handling of foreign threads. Put every task // into this queue. - scoped_refptr<base::MessagePump> pump; + nsRefPtr<base::MessagePump> pump; { AutoLock locked(incoming_queue_lock_); incoming_queue_.push(pending_task); pump = pump_; } // Since the incoming_queue_ may contain a task that destroys this message // loop, we cannot exit incoming_queue_lock_ until we are done with |this|. // We use a stack-based reference to the message pump so that we can call
--- a/ipc/chromium/src/base/message_loop.h +++ b/ipc/chromium/src/base/message_loop.h @@ -4,34 +4,34 @@ #ifndef BASE_MESSAGE_LOOP_H_ #define BASE_MESSAGE_LOOP_H_ #include <deque> #include <queue> #include <string> #include <vector> +#include <map> -#include <map> #include "base/lock.h" #include "base/message_pump.h" #include "base/observer_list.h" -#include "base/ref_counted.h" -#include "base/scoped_ptr.h" #include "base/task.h" #include "base/timer.h" #if defined(OS_WIN) // We need this to declare base::MessagePumpWin::Dispatcher, which we should // really just eliminate. #include "base/message_pump_win.h" #elif defined(OS_POSIX) #include "base/message_pump_libevent.h" #endif +#include "nsAutoPtr.h" + namespace mozilla { namespace ipc { class DoWorkRunnable; } /* namespace ipc */ } /* namespace mozilla */ @@ -410,17 +410,17 @@ public: // Contains delayed tasks, sorted by their 'delayed_run_time' property. DelayedTaskQueue delayed_work_queue_; // A queue of non-nestable tasks that we had to defer because when it came // time to execute them we were in a nested message loop. They will execute // once we're out of nested message loops. TaskQueue deferred_non_nestable_work_queue_; - scoped_refptr<base::MessagePump> pump_; + nsRefPtr<base::MessagePump> pump_; base::ObserverList<DestructionObserver> destruction_observers_; // A recursion block that prevents accidentally running additonal tasks when // insider a (accidentally induced?) nested message pump. bool nestable_tasks_allowed_; bool exception_restoration_;
--- a/ipc/chromium/src/base/message_pump.h +++ b/ipc/chromium/src/base/message_pump.h @@ -1,23 +1,25 @@ // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #ifndef BASE_MESSAGE_PUMP_H_ #define BASE_MESSAGE_PUMP_H_ -#include "base/ref_counted.h" +#include "nsISupportsImpl.h" namespace base { class TimeTicks; -class MessagePump : public RefCountedThreadSafe<MessagePump> { +class MessagePump { public: + NS_INLINE_DECL_THREADSAFE_REFCOUNTING(MessagePump) + // Please see the comments above the Run method for an illustration of how // these delegate methods are used. class Delegate { public: virtual ~Delegate() {} // Called from within Run in response to ScheduleWork or when the message // pump would otherwise call DoDelayedWork. Returns true to indicate that @@ -34,18 +36,16 @@ class MessagePump : public RefCountedThr // calls to this function need to be scheduled. virtual bool DoDelayedWork(TimeTicks* next_delayed_work_time) = 0; // Called from within Run just before the message pump goes to sleep. // Returns true to indicate that idle work was done. virtual bool DoIdleWork() = 0; }; - virtual ~MessagePump() {} - // The Run method is called to enter the message pump's run loop. // // Within the method, the message pump is responsible for processing native // messages as well as for giving cycles to the delegate periodically. The // message pump should take care to mix delegate callbacks with native // message processing so neither type of event starves the other of cycles. // // The anatomy of a typical run loop: @@ -118,13 +118,16 @@ class MessagePump : public RefCountedThr // "reasonably soon", this method can be a no-op to avoid expensive // atomic tests and/or syscalls required for ScheduleWork(). virtual void ScheduleWorkForNestedLoop() { ScheduleWork(); }; // Schedule a DoDelayedWork callback to happen at the specified time, // cancelling any pending DoDelayedWork callback. This method may only be // used on the thread that called Run. virtual void ScheduleDelayedWork(const TimeTicks& delayed_work_time) = 0; + +protected: + virtual ~MessagePump() {}; }; } // namespace base #endif // BASE_MESSAGE_PUMP_H_
--- a/ipc/chromium/src/base/message_pump_glib.h +++ b/ipc/chromium/src/base/message_pump_glib.h @@ -2,18 +2,18 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #ifndef BASE_MESSAGE_PUMP_GLIB_H_ #define BASE_MESSAGE_PUMP_GLIB_H_ #include "base/message_pump.h" #include "base/observer_list.h" -#include "base/scoped_ptr.h" #include "base/time.h" +#include "mozilla/UniquePtr.h" typedef union _GdkEvent GdkEvent; typedef struct _GMainContext GMainContext; typedef struct _GPollFD GPollFD; typedef struct _GSource GSource; namespace base { @@ -123,18 +123,18 @@ class MessagePumpForUI : public MessageP GSource* work_source_; // We use a wakeup pipe to make sure we'll get out of the glib polling phase // when another thread has scheduled us to do some work. There is a glib // mechanism g_main_context_wakeup, but this won't guarantee that our event's // Dispatch() will be called. int wakeup_pipe_read_; int wakeup_pipe_write_; - // Use a scoped_ptr to avoid needing the definition of GPollFD in the header. - scoped_ptr<GPollFD> wakeup_gpollfd_; + // Use an autoptr to avoid needing the definition of GPollFD in the header. + mozilla::UniquePtr<GPollFD> wakeup_gpollfd_; // List of observers. ObserverList<Observer> observers_; DISALLOW_COPY_AND_ASSIGN(MessagePumpForUI); }; } // namespace base
--- a/ipc/chromium/src/base/message_pump_libevent.cc +++ b/ipc/chromium/src/base/message_pump_libevent.cc @@ -8,20 +8,20 @@ #include <fcntl.h> #if defined(ANDROID) || defined(OS_POSIX) #include <unistd.h> #endif #include "eintr_wrapper.h" #include "base/logging.h" #include "base/scoped_nsautorelease_pool.h" -#include "base/scoped_ptr.h" #include "base/time.h" #include "nsDependentSubstring.h" #include "third_party/libevent/event.h" +#include "mozilla/UniquePtr.h" // Lifecycle of struct event // Libevent uses two main data structures: // struct event_base (of which there is one per message pump), and // struct event (of which there is roughly one per socket). // The socket's struct event is created in // MessagePumpLibevent::WatchFileDescriptor(), // is owned by the FileDescriptorWatcher, and is destroyed in @@ -165,21 +165,21 @@ bool MessagePumpLibevent::WatchFileDescr event_mask |= EV_WRITE; } // |should_delete_event| is true if we're modifying an event that's currently // active in |controller|. // If we're modifying an existing event and there's an error then we need to // tell libevent to clean it up via event_delete() before returning. bool should_delete_event = true; - scoped_ptr<event> evt(controller->ReleaseEvent()); + mozilla::UniquePtr<event> evt(controller->ReleaseEvent()); if (evt.get() == NULL) { should_delete_event = false; // Ownership is transferred to the controller. - evt.reset(new event); + evt = mozilla::MakeUnique<event>(); } // Set current interest mask and message pump for this event. event_set(evt.get(), fd, event_mask, OnLibeventNotification, delegate); // Tell libevent which message pump this socket will belong to when we add it. if (event_base_set(event_base_, evt.get()) != 0) { @@ -268,17 +268,17 @@ MessagePumpLibevent::CatchSignal(int sig DCHECK(sig > 0); DCHECK(sigevent); DCHECK(delegate); // TODO if we want to support re-using SignalEvents, this code needs // to jump through the same hoops as WatchFileDescriptor(). Not // needed at present DCHECK(NULL == sigevent->event_); - scoped_ptr<event> evt(new event); + mozilla::UniquePtr<event> evt = mozilla::MakeUnique<event>(); signal_set(evt.get(), sig, OnLibeventSignalNotification, delegate); if (event_base_set(event_base_, evt.get())) return false; if (signal_add(evt.get(), NULL)) return false;
--- a/ipc/chromium/src/base/message_pump_libevent.h +++ b/ipc/chromium/src/base/message_pump_libevent.h @@ -57,17 +57,16 @@ class MessagePumpLibevent : public Messa virtual ~Watcher() {} // Called from MessageLoop::Run when an FD can be read from/written to // without blocking virtual void OnFileCanReadWithoutBlocking(int fd) = 0; virtual void OnFileCanWriteWithoutBlocking(int fd) = 0; }; MessagePumpLibevent(); - virtual ~MessagePumpLibevent(); enum Mode { WATCH_READ = 1 << 0, WATCH_WRITE = 1 << 1, WATCH_READ_WRITE = WATCH_READ | WATCH_WRITE }; // Have the current thread's message loop watch for a a situation in which @@ -134,16 +133,20 @@ class MessagePumpLibevent : public Messa // MessagePump methods: virtual void Run(Delegate* delegate); virtual void Quit(); virtual void ScheduleWork(); virtual void ScheduleDelayedWork(const TimeTicks& delayed_work_time); + protected: + + virtual ~MessagePumpLibevent(); + private: // Risky part of constructor. Returns true on success. bool Init(); // This flag is set to false when Run should return. bool keep_running_;
--- a/ipc/chromium/src/base/message_pump_mac.h +++ b/ipc/chromium/src/base/message_pump_mac.h @@ -27,16 +27,18 @@ // or NSRunLoop-based MessagePump subclass depending on which thread it is // called on. #ifndef BASE_MESSAGE_PUMP_MAC_H_ #define BASE_MESSAGE_PUMP_MAC_H_ #include "base/message_pump.h" +#include "base/basictypes.h" + #include <CoreFoundation/CoreFoundation.h> #include <IOKit/IOKitLib.h> #if defined(__OBJC__) @class NSAutoreleasePool; #else // defined(__OBJC__) class NSAutoreleasePool; #endif // defined(__OBJC__)
--- a/ipc/chromium/src/base/process_util_bsd.cc +++ b/ipc/chromium/src/base/process_util_bsd.cc @@ -13,16 +13,17 @@ #include <string> #include "base/eintr_wrapper.h" #include "base/file_util.h" #include "base/logging.h" #include "base/string_tokenizer.h" #include "base/string_util.h" +#include "mozilla/UniquePtr.h" #if defined(_POSIX_SPAWN) && _POSIX_SPAWN > 0 #define HAVE_POSIX_SPAWN 1 #endif /* * On platforms that are not gonk based, we fall back to an arbitrary * UID. This is generally the UID for user `nobody', albeit it is not @@ -220,17 +221,17 @@ bool LaunchApp(const std::vector<std::st } bool LaunchApp(const std::vector<std::string>& argv, const file_handle_mapping_vector& fds_to_remap, const environment_map& env_vars_to_set, ChildPrivileges privs, bool wait, ProcessHandle* process_handle, ProcessArchitecture arch) { - scoped_array<char*> argv_cstr(new char*[argv.size() + 1]); + mozilla::UniquePtr<char*[]> argv_cstr(new char*[argv.size() + 1]); // Illegal to allocate memory after fork and before execvp InjectiveMultimap fd_shuffle1, fd_shuffle2; fd_shuffle1.reserve(fds_to_remap.size()); fd_shuffle2.reserve(fds_to_remap.size()); pid_t pid = fork(); if (pid < 0) return false;
--- a/ipc/chromium/src/base/process_util_linux.cc +++ b/ipc/chromium/src/base/process_util_linux.cc @@ -15,16 +15,17 @@ #include <sys/wait.h> #include "base/eintr_wrapper.h" #include "base/file_util.h" #include "base/logging.h" #include "base/string_tokenizer.h" #include "base/string_util.h" #include "nsLiteralString.h" +#include "mozilla/UniquePtr.h" #ifdef MOZ_B2G_LOADER #include "ProcessUtils.h" using namespace mozilla::ipc; #endif // MOZ_B2G_LOADER #ifdef MOZ_WIDGET_GONK @@ -202,23 +203,23 @@ bool LaunchApp(const std::vector<std::st */ static bool LaunchAppProcLoader(const std::vector<std::string>& argv, const file_handle_mapping_vector& fds_to_remap, const environment_map& env_vars_to_set, ChildPrivileges privs, ProcessHandle* process_handle) { size_t i; - scoped_array<char*> argv_cstr(new char*[argv.size() + 1]); + mozilla::UniquePtr<char*[]> argv_cstr(new char*[argv.size() + 1]); for (i = 0; i < argv.size(); i++) { argv_cstr[i] = const_cast<char*>(argv[i].c_str()); } argv_cstr[argv.size()] = nullptr; - scoped_array<char*> env_cstr(new char*[env_vars_to_set.size() + 1]); + mozilla::UniquePtr<char*[]> env_cstr(new char*[env_vars_to_set.size() + 1]); i = 0; for (environment_map::const_iterator it = env_vars_to_set.begin(); it != env_vars_to_set.end(); ++it) { env_cstr[i++] = strdup((it->first + "=" + it->second).c_str()); } env_cstr[env_vars_to_set.size()] = nullptr; bool ok = ProcLoaderLoad((const char **)argv_cstr.get(), @@ -256,17 +257,17 @@ bool LaunchApp(const std::vector<std::st static bool beforeFirstNuwaLaunch = true; if (!wait && beforeFirstNuwaLaunch && IsLaunchingNuwa(argv)) { beforeFirstNuwaLaunch = false; return LaunchAppProcLoader(argv, fds_to_remap, env_vars_to_set, privs, process_handle); } #endif // MOZ_B2G_LOADER - scoped_array<char*> argv_cstr(new char*[argv.size() + 1]); + mozilla::UniquePtr<char*[]> argv_cstr(new char*[argv.size() + 1]); // Illegal to allocate memory after fork and before execvp InjectiveMultimap fd_shuffle1, fd_shuffle2; fd_shuffle1.reserve(fds_to_remap.size()); fd_shuffle2.reserve(fds_to_remap.size()); #ifdef HAVE_PR_DUPLICATE_ENVIRONMENT Environment env; env.Merge(env_vars_to_set);
--- a/ipc/chromium/src/base/process_util_posix.cc +++ b/ipc/chromium/src/base/process_util_posix.cc @@ -17,22 +17,23 @@ #include <limits> #include <set> #include "base/basictypes.h" #include "base/eintr_wrapper.h" #include "base/logging.h" #include "base/platform_thread.h" #include "base/process_util.h" -#include "base/scoped_ptr.h" #include "base/sys_info.h" #include "base/time.h" #include "base/waitable_event.h" #include "base/dir_reader_posix.h" +#include "mozilla/UniquePtr.h" + const int kMicrosecondsPerSecond = 1000000; namespace base { ProcessId GetCurrentProcId() { return getpid(); } @@ -96,17 +97,17 @@ typedef unsigned long int rlim_t; class ScopedDIRClose { public: inline void operator()(DIR* x) const { if (x) { closedir(x); } } }; -typedef scoped_ptr_malloc<DIR, ScopedDIRClose> ScopedDIR; +typedef mozilla::UniquePtr<DIR, ScopedDIRClose> ScopedDIR; void CloseSuperfluousFds(const base::InjectiveMultimap& saved_mapping) { // DANGER: no calls to malloc are allowed from now on: // http://crbug.com/36678 #if defined(ANDROID) static const rlim_t kSystemDefaultMaxFds = 1024; static const char kFDDir[] = "/proc/self/fd";
--- a/ipc/chromium/src/base/process_util_win.cc +++ b/ipc/chromium/src/base/process_util_win.cc @@ -9,18 +9,16 @@ #include "base/process_util.h" #include <windows.h> #include <winternl.h> #include <psapi.h> #include "base/histogram.h" #include "base/logging.h" -#include "base/scoped_handle_win.h" -#include "base/scoped_ptr.h" #include "base/win_util.h" #include <algorithm> namespace { // System pagesize. This value remains constant on x86/64 architectures. const int PAGESIZE_KB = 4;
--- a/ipc/chromium/src/base/process_win.cc +++ b/ipc/chromium/src/base/process_win.cc @@ -1,16 +1,15 @@ // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #include "base/process.h" #include "base/logging.h" #include "base/process_util.h" -#include "base/scoped_ptr.h" namespace base { void Process::Close() { if (!process_) return; CloseProcessHandle(process_); process_ = NULL;
deleted file mode 100644 --- a/ipc/chromium/src/base/ref_counted.cc +++ /dev/null @@ -1,88 +0,0 @@ -// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/ref_counted.h" - -#include "base/logging.h" -#include "base/thread_collision_warner.h" - -namespace base { - -namespace subtle { - -RefCountedBase::RefCountedBase() : ref_count_(0) { -#ifndef NDEBUG - in_dtor_ = false; -#endif -} - -RefCountedBase::~RefCountedBase() { -#ifndef NDEBUG - DCHECK(in_dtor_) << "RefCounted object deleted without calling Release()"; -#endif -} - -void RefCountedBase::AddRef() { - // TODO(maruel): Add back once it doesn't assert 500 times/sec. - // Current thread books the critical section "AddRelease" without release it. - // DFAKE_SCOPED_LOCK_THREAD_LOCKED(add_release_); -#ifndef NDEBUG - DCHECK(!in_dtor_); -#endif - ++ref_count_; -} - -bool RefCountedBase::Release() { - // TODO(maruel): Add back once it doesn't assert 500 times/sec. - // Current thread books the critical section "AddRelease" without release it. - // DFAKE_SCOPED_LOCK_THREAD_LOCKED(add_release_); -#ifndef NDEBUG - DCHECK(!in_dtor_); -#endif - if (--ref_count_ == 0) { -#ifndef NDEBUG - in_dtor_ = true; -#endif - return true; - } - return false; -} - -RefCountedThreadSafeBase::RefCountedThreadSafeBase() : ref_count_(0) { -#ifndef NDEBUG - in_dtor_ = false; -#endif -} - -RefCountedThreadSafeBase::~RefCountedThreadSafeBase() { -#ifndef NDEBUG - DCHECK(in_dtor_) << "RefCountedThreadSafe object deleted without " - "calling Release()"; -#endif -} - -void RefCountedThreadSafeBase::AddRef() { -#ifndef NDEBUG - DCHECK(!in_dtor_); -#endif - AtomicRefCountInc(&ref_count_); -} - -bool RefCountedThreadSafeBase::Release() { -#ifndef NDEBUG - DCHECK(!in_dtor_); - DCHECK(!AtomicRefCountIsZero(&ref_count_)); -#endif - if (!AtomicRefCountDec(&ref_count_)) { -#ifndef NDEBUG - in_dtor_ = true; -#endif - return true; - } - return false; -} - -} // namespace subtle - -} // namespace base
deleted file mode 100644 --- a/ipc/chromium/src/base/ref_counted.h +++ /dev/null @@ -1,231 +0,0 @@ -// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef BASE_REF_COUNTED_H_ -#define BASE_REF_COUNTED_H_ - -#include "base/atomic_ref_count.h" -#include "base/thread_collision_warner.h" - -namespace base { - -namespace subtle { - -class RefCountedBase { - protected: - RefCountedBase(); - ~RefCountedBase(); - - void AddRef(); - - // Returns true if the object should self-delete. - bool Release(); - - private: - int ref_count_; -#ifndef NDEBUG - bool in_dtor_; -#endif - - DFAKE_MUTEX(add_release_) - - DISALLOW_COPY_AND_ASSIGN(RefCountedBase); -}; - -class RefCountedThreadSafeBase { - protected: - RefCountedThreadSafeBase(); - ~RefCountedThreadSafeBase(); - - void AddRef(); - - // Returns true if the object should self-delete. - bool Release(); - - private: - AtomicRefCount ref_count_; -#ifndef NDEBUG - bool in_dtor_; -#endif - - DISALLOW_COPY_AND_ASSIGN(RefCountedThreadSafeBase); -}; - - - -} // namespace subtle - -// -// A base class for reference counted classes. Otherwise, known as a cheap -// knock-off of WebKit's RefCounted<T> class. To use this guy just extend your -// class from it like so: -// -// class MyFoo : public base::RefCounted<MyFoo> { -// ... -// }; -// -template <class T> -class RefCounted : public subtle::RefCountedBase { - public: - RefCounted() { } - ~RefCounted() { } - - void AddRef() { - subtle::RefCountedBase::AddRef(); - } - - void Release() { - if (subtle::RefCountedBase::Release()) { - delete static_cast<T*>(this); - } - } - - private: - DISALLOW_COPY_AND_ASSIGN(RefCounted<T>); -}; - -// -// A thread-safe variant of RefCounted<T> -// -// class MyFoo : public base::RefCountedThreadSafe<MyFoo> { -// ... -// }; -// -template <class T> -class RefCountedThreadSafe : public subtle::RefCountedThreadSafeBase { - public: - RefCountedThreadSafe() { } - ~RefCountedThreadSafe() { } - - void AddRef() { - subtle::RefCountedThreadSafeBase::AddRef(); - } - - void Release() { - if (subtle::RefCountedThreadSafeBase::Release()) { - delete static_cast<T*>(this); - } - } - - private: - DISALLOW_COPY_AND_ASSIGN(RefCountedThreadSafe<T>); -}; - -// -// A wrapper for some piece of data so we can place other things in -// scoped_refptrs<>. -// -template<typename T> -class RefCountedData : public base::RefCounted< base::RefCountedData<T> > { - public: - RefCountedData() : data() {} - explicit RefCountedData(const T& in_value) : data(in_value) {} - - T data; -}; - -} // namespace base - -// -// A smart pointer class for reference counted objects. Use this class instead -// of calling AddRef and Release manually on a reference counted object to -// avoid common memory leaks caused by forgetting to Release an object -// reference. Sample usage: -// -// class MyFoo : public RefCounted<MyFoo> { -// ... -// }; -// -// void some_function() { -// scoped_refptr<MyFoo> foo = new MyFoo(); -// foo->Method(param); -// // |foo| is released when this function returns -// } -// -// void some_other_function() { -// scoped_refptr<MyFoo> foo = new MyFoo(); -// ... -// foo = NULL; // explicitly releases |foo| -// ... -// if (foo) -// foo->Method(param); -// } -// -// The above examples show how scoped_refptr<T> acts like a pointer to T. -// Given two scoped_refptr<T> classes, it is also possible to exchange -// references between the two objects, like so: -// -// { -// scoped_refptr<MyFoo> a = new MyFoo(); -// scoped_refptr<MyFoo> b; -// -// b.swap(a); -// // now, |b| references the MyFoo object, and |a| references NULL. -// } -// -// To make both |a| and |b| in the above example reference the same MyFoo -// object, simply use the assignment operator: -// -// { -// scoped_refptr<MyFoo> a = new MyFoo(); -// scoped_refptr<MyFoo> b; -// -// b = a; -// // now, |a| and |b| each own a reference to the same MyFoo object. -// } -// -template <class T> -class scoped_refptr { - public: - scoped_refptr() : ptr_(NULL) { - } - - MOZ_IMPLICIT scoped_refptr(T* p) : ptr_(p) { - if (ptr_) - ptr_->AddRef(); - } - - scoped_refptr(const scoped_refptr<T>& r) : ptr_(r.ptr_) { - if (ptr_) - ptr_->AddRef(); - } - - ~scoped_refptr() { - if (ptr_) - ptr_->Release(); - } - - T* get() const { return ptr_; } - operator T*() const { return ptr_; } - T* operator->() const { return ptr_; } - - scoped_refptr<T>& operator=(T* p) { - // AddRef first so that self assignment should work - if (p) - p->AddRef(); - if (ptr_ ) - ptr_ ->Release(); - ptr_ = p; - return *this; - } - - scoped_refptr<T>& operator=(const scoped_refptr<T>& r) { - return *this = r.ptr_; - } - - void swap(T** pp) { - T* p = ptr_; - ptr_ = *pp; - *pp = p; - } - - void swap(scoped_refptr<T>& r) { - swap(&r.ptr_); - } - - protected: - T* ptr_; -}; - -#endif // BASE_REF_COUNTED_H_
--- a/ipc/chromium/src/base/revocable_store.h +++ b/ipc/chromium/src/base/revocable_store.h @@ -1,32 +1,37 @@ // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #ifndef BASE_REVOCABLE_STORE_H_ #define BASE_REVOCABLE_STORE_H_ -#include "base/ref_counted.h" +#include "base/basictypes.h" +#include "nsISupportsImpl.h" +#include "nsAutoPtr.h" // |RevocableStore| is a container of items that can be removed from the store. class RevocableStore { public: // A |StoreRef| is used to link the |RevocableStore| to its items. There is // one StoreRef per store, and each item holds a reference to it. If the // store wishes to revoke its items, it sets |store_| to null. Items are // permitted to release their reference to the |StoreRef| when they no longer // require the store. - class StoreRef : public base::RefCounted<StoreRef> { + class StoreRef MOZ_FINAL { public: + NS_INLINE_DECL_THREADSAFE_REFCOUNTING(StoreRef) explicit StoreRef(RevocableStore* store) : store_(store) { } void set_store(RevocableStore* store) { store_ = store; } RevocableStore* store() const { return store_; } + protected: + ~StoreRef() {} private: RevocableStore* store_; DISALLOW_EVIL_CONSTRUCTORS(StoreRef); }; // An item in the store. On construction, the object adds itself to the // store. @@ -36,17 +41,17 @@ class RevocableStore { ~Revocable(); // This item has been revoked if it no longer has a pointer to the store. bool revoked() const { return !store_reference_->store(); } private: // We hold a reference to the store through this ref pointer. We release // this reference on destruction. - scoped_refptr<StoreRef> store_reference_; + nsRefPtr<StoreRef> store_reference_; DISALLOW_EVIL_CONSTRUCTORS(Revocable); }; RevocableStore(); ~RevocableStore(); // Revokes all the items in the store. @@ -58,17 +63,17 @@ class RevocableStore { private: friend class Revocable; // Adds an item to the store. To add an item to the store, construct it // with a pointer to the store. void Add(Revocable* item); // This is the reference the unrevoked items in the store hold. - scoped_refptr<StoreRef> owning_reference_; + nsRefPtr<StoreRef> owning_reference_; // The number of unrevoked items in the store. int count_; DISALLOW_EVIL_CONSTRUCTORS(RevocableStore); }; #endif // BASE_REVOCABLE_STORE_H_
deleted file mode 100644 --- a/ipc/chromium/src/base/scoped_ptr.h +++ /dev/null @@ -1,380 +0,0 @@ -// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -// Scopers help you manage ownership of a pointer, helping you easily manage the -// a pointer within a scope, and automatically destroying the pointer at the -// end of a scope. There are two main classes you will use, which coorespond -// to the operators new/delete and new[]/delete[]. -// -// Example usage (scoped_ptr): -// { -// scoped_ptr<Foo> foo(new Foo("wee")); -// } // foo goes out of scope, releasing the pointer with it. -// -// { -// scoped_ptr<Foo> foo; // No pointer managed. -// foo.reset(new Foo("wee")); // Now a pointer is managed. -// foo.reset(new Foo("wee2")); // Foo("wee") was destroyed. -// foo.reset(new Foo("wee3")); // Foo("wee2") was destroyed. -// foo->Method(); // Foo::Method() called. -// foo.get()->Method(); // Foo::Method() called. -// SomeFunc(foo.Release()); // SomeFunc takes owernship, foo no longer -// // manages a pointer. -// foo.reset(new Foo("wee4")); // foo manages a pointer again. -// foo.reset(); // Foo("wee4") destroyed, foo no longer -// // manages a pointer. -// } // foo wasn't managing a pointer, so nothing was destroyed. -// -// Example usage (scoped_array): -// { -// scoped_array<Foo> foo(new Foo[100]); -// foo.get()->Method(); // Foo::Method on the 0th element. -// foo[10].Method(); // Foo::Method on the 10th element. -// } - -#ifndef BASE_SCOPED_PTR_H_ -#define BASE_SCOPED_PTR_H_ - -// This is an implementation designed to match the anticipated future TR2 -// implementation of the scoped_ptr class, and its closely-related brethren, -// scoped_array, scoped_ptr_malloc. - -#include <assert.h> -#include <stdlib.h> -#include <cstddef> - -// A scoped_ptr<T> is like a T*, except that the destructor of scoped_ptr<T> -// automatically deletes the pointer it holds (if any). -// That is, scoped_ptr<T> owns the T object that it points to. -// Like a T*, a scoped_ptr<T> may hold either NULL or a pointer to a T object. -// Also like T*, scoped_ptr<T> is thread-compatible, and once you -// dereference it, you get the threadsafety guarantees of T. -// -// The size of a scoped_ptr is small: -// sizeof(scoped_ptr<C>) == sizeof(C*) -template <class C> -class scoped_ptr { - public: - - // The element type - typedef C element_type; - - // Constructor. Defaults to intializing with NULL. - // There is no way to create an uninitialized scoped_ptr. - // The input parameter must be allocated with new. - explicit scoped_ptr(C* p = NULL) : ptr_(p) { } - - // Destructor. If there is a C object, delete it. - // We don't need to test ptr_ == NULL because C++ does that for us. - ~scoped_ptr() { - enum { type_must_be_complete = sizeof(C) }; - delete ptr_; - } - - // Reset. Deletes the current owned object, if any. - // Then takes ownership of a new object, if given. - // this->reset(this->get()) works. - void reset(C* p = NULL) { - if (p != ptr_) { - enum { type_must_be_complete = sizeof(C) }; - delete ptr_; - ptr_ = p; - } - } - - // Accessors to get the owned object. - // operator* and operator-> will assert() if there is no current object. - C& operator*() const { - assert(ptr_ != NULL); - return *ptr_; - } - C* operator->() const { - assert(ptr_ != NULL); - return ptr_; - } - C* get() const { return ptr_; } - - // Comparison operators. - // These return whether two scoped_ptr refer to the same object, not just to - // two different but equal objects. - bool operator==(C* p) const { return ptr_ == p; } - bool operator!=(C* p) const { return ptr_ != p; } - - // Swap two scoped pointers. - void swap(scoped_ptr& p2) { - C* tmp = ptr_; - ptr_ = p2.ptr_; - p2.ptr_ = tmp; - } - - // Release a pointer. - // The return value is the current pointer held by this object. - // If this object holds a NULL pointer, the return value is NULL. - // After this operation, this object will hold a NULL pointer, - // and will not own the object any more. - C* release() { - C* retVal = ptr_; - ptr_ = NULL; - return retVal; - } - - private: - C* ptr_; - - // Forbid comparison of scoped_ptr types. If C2 != C, it totally doesn't - // make sense, and if C2 == C, it still doesn't make sense because you should - // never have the same object owned by two different scoped_ptrs. - template <class C2> bool operator==(scoped_ptr<C2> const& p2) const; - template <class C2> bool operator!=(scoped_ptr<C2> const& p2) const; - - // Disallow evil constructors - scoped_ptr(const scoped_ptr&); - void operator=(const scoped_ptr&); -}; - -// Free functions -template <class C> -void swap(scoped_ptr<C>& p1, scoped_ptr<C>& p2) { - p1.swap(p2); -} - -template <class C> -bool operator==(C* p1, const scoped_ptr<C>& p2) { - return p1 == p2.get(); -} - -template <class C> -bool operator!=(C* p1, const scoped_ptr<C>& p2) { - return p1 != p2.get(); -} - -// scoped_array<C> is like scoped_ptr<C>, except that the caller must allocate -// with new [] and the destructor deletes objects with delete []. -// -// As with scoped_ptr<C>, a scoped_array<C> either points to an object -// or is NULL. A scoped_array<C> owns the object that it points to. -// scoped_array<T> is thread-compatible, and once you index into it, -// the returned objects have only the threadsafety guarantees of T. -// -// Size: sizeof(scoped_array<C>) == sizeof(C*) -template <class C> -class scoped_array { - public: - - // The element type - typedef C element_type; - - // Constructor. Defaults to intializing with NULL. - // There is no way to create an uninitialized scoped_array. - // The input parameter must be allocated with new []. - explicit scoped_array(C* p = NULL) : array_(p) { } - - // Destructor. If there is a C object, delete it. - // We don't need to test ptr_ == NULL because C++ does that for us. - ~scoped_array() { - enum { type_must_be_complete = sizeof(C) }; - delete[] array_; - } - - // Reset. Deletes the current owned object, if any. - // Then takes ownership of a new object, if given. - // this->reset(this->get()) works. - void reset(C* p = NULL) { - if (p != array_) { - enum { type_must_be_complete = sizeof(C) }; - delete[] array_; - array_ = p; - } - } - - // Get one element of the current object. - // Will assert() if there is no current object, or index i is negative. - C& operator[](std::ptrdiff_t i) const { - assert(i >= 0); - assert(array_ != NULL); - return array_[i]; - } - - // Get a pointer to the zeroth element of the current object. - // If there is no current object, return NULL. - C* get() const { - return array_; - } - - // Comparison operators. - // These return whether two scoped_array refer to the same object, not just to - // two different but equal objects. - bool operator==(C* p) const { return array_ == p; } - bool operator!=(C* p) const { return array_ != p; } - - // Swap two scoped arrays. - void swap(scoped_array& p2) { - C* tmp = array_; - array_ = p2.array_; - p2.array_ = tmp; - } - - // Release an array. - // The return value is the current pointer held by this object. - // If this object holds a NULL pointer, the return value is NULL. - // After this operation, this object will hold a NULL pointer, - // and will not own the object any more. - C* release() { - C* retVal = array_; - array_ = NULL; - return retVal; - } - - private: - C* array_; - - // Forbid comparison of different scoped_array types. - template <class C2> bool operator==(scoped_array<C2> const& p2) const; - template <class C2> bool operator!=(scoped_array<C2> const& p2) const; - - // Disallow evil constructors - scoped_array(const scoped_array&); - void operator=(const scoped_array&); -}; - -// Free functions -template <class C> -void swap(scoped_array<C>& p1, scoped_array<C>& p2) { - p1.swap(p2); -} - -template <class C> -bool operator==(C* p1, const scoped_array<C>& p2) { - return p1 == p2.get(); -} - -template <class C> -bool operator!=(C* p1, const scoped_array<C>& p2) { - return p1 != p2.get(); -} - -// This class wraps the c library function free() in a class that can be -// passed as a template argument to scoped_ptr_malloc below. -class ScopedPtrMallocFree { - public: - inline void operator()(void* x) const { - free(x); - } -}; - -// scoped_ptr_malloc<> is similar to scoped_ptr<>, but it accepts a -// second template argument, the functor used to free the object. - -template<class C, class FreeProc = ScopedPtrMallocFree> -class scoped_ptr_malloc { - public: - - // The element type - typedef C element_type; - - // Constructor. Defaults to intializing with NULL. - // There is no way to create an uninitialized scoped_ptr. - // The input parameter must be allocated with an allocator that matches the - // Free functor. For the default Free functor, this is malloc, calloc, or - // realloc. - explicit scoped_ptr_malloc(C* p = NULL): ptr_(p) {} - - // Destructor. If there is a C object, call the Free functor. - ~scoped_ptr_malloc() { - free_(ptr_); - } - - // Reset. Calls the Free functor on the current owned object, if any. - // Then takes ownership of a new object, if given. - // this->reset(this->get()) works. - void reset(C* p = NULL) { - if (ptr_ != p) { - free_(ptr_); - ptr_ = p; - } - } - - // Get the current object. - // operator* and operator-> will cause an assert() failure if there is - // no current object. - C& operator*() const { - assert(ptr_ != NULL); - return *ptr_; - } - - C* operator->() const { - assert(ptr_ != NULL); - return ptr_; - } - - C* get() const { - return ptr_; - } - - // Comparison operators. - // These return whether a scoped_ptr_malloc and a plain pointer refer - // to the same object, not just to two different but equal objects. - // For compatibility wwith the boost-derived implementation, these - // take non-const arguments. - bool operator==(C* p) const { - return ptr_ == p; - } - - bool operator!=(C* p) const { - return ptr_ != p; - } - - // Swap two scoped pointers. - void swap(scoped_ptr_malloc & b) { - C* tmp = b.ptr_; - b.ptr_ = ptr_; - ptr_ = tmp; - } - - // Release a pointer. - // The return value is the current pointer held by this object. - // If this object holds a NULL pointer, the return value is NULL. - // After this operation, this object will hold a NULL pointer, - // and will not own the object any more. - C* release() { - C* tmp = ptr_; - ptr_ = NULL; - return tmp; - } - - private: - C* ptr_; - - // no reason to use these: each scoped_ptr_malloc should have its own object - template <class C2, class GP> - bool operator==(scoped_ptr_malloc<C2, GP> const& p) const; - template <class C2, class GP> - bool operator!=(scoped_ptr_malloc<C2, GP> const& p) const; - - static FreeProc const free_; - - // Disallow evil constructors - scoped_ptr_malloc(const scoped_ptr_malloc&); - void operator=(const scoped_ptr_malloc&); -}; - -template<class C, class FP> -FP const scoped_ptr_malloc<C, FP>::free_ = FP(); - -template<class C, class FP> inline -void swap(scoped_ptr_malloc<C, FP>& a, scoped_ptr_malloc<C, FP>& b) { - a.swap(b); -} - -template<class C, class FP> inline -bool operator==(C* p, const scoped_ptr_malloc<C, FP>& b) { - return p == b.get(); -} - -template<class C, class FP> inline -bool operator!=(C* p, const scoped_ptr_malloc<C, FP>& b) { - return p != b.get(); -} - -#endif // BASE_SCOPED_PTR_H_
--- a/ipc/chromium/src/base/shared_memory_posix.cc +++ b/ipc/chromium/src/base/shared_memory_posix.cc @@ -9,16 +9,17 @@ #include <sys/mman.h> #include <sys/stat.h> #include <unistd.h> #include "base/file_util.h" #include "base/logging.h" #include "base/platform_thread.h" #include "base/string_util.h" +#include "mozilla/UniquePtr.h" namespace base { SharedMemory::SharedMemory() : mapped_file_(-1), inode_(0), memory_(NULL), read_only_(false), @@ -137,17 +138,17 @@ class ScopedFILEClose { public: inline void operator()(FILE* x) const { if (x) { fclose(x); } } }; -typedef scoped_ptr_malloc<FILE, ScopedFILEClose> ScopedFILE; +typedef mozilla::UniquePtr<FILE, ScopedFILEClose> ScopedFILE; } // Chromium mostly only use the unique/private shmem as specified by // "name == L"". The exception is in the StatsTable. // TODO(jrg): there is no way to "clean up" all unused named shmem if // we restart from a crash. (That isn't a new problem, but it is a problem.) // In case we want to delete it later, it may be useful to save the value
--- a/ipc/chromium/src/base/sys_info_win.cc +++ b/ipc/chromium/src/base/sys_info_win.cc @@ -2,18 +2,18 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #include "base/sys_info.h" #include <windows.h> #include "base/logging.h" -#include "base/scoped_ptr.h" #include "base/string_util.h" +#include "mozilla/UniquePtr.h" namespace base { // static int SysInfo::NumberOfProcessors() { SYSTEM_INFO info; GetSystemInfo(&info); return static_cast<int>(info.dwNumberOfProcessors); @@ -52,17 +52,17 @@ bool SysInfo::HasEnvVar(const wchar_t* v } // static std::wstring SysInfo::GetEnvVar(const wchar_t* var) { DWORD value_length = GetEnvironmentVariable(var, NULL, 0); if (value_length == 0) { return L""; } - scoped_array<wchar_t> value(new wchar_t[value_length]); + mozilla::UniquePtr<wchar_t[]> value(new wchar_t[value_length]); GetEnvironmentVariable(var, value.get(), value_length); return std::wstring(value.get()); } // static std::string SysInfo::OperatingSystemName() { return "Windows NT"; }
--- a/ipc/chromium/src/base/waitable_event.h +++ b/ipc/chromium/src/base/waitable_event.h @@ -11,17 +11,18 @@ #include <windows.h> #endif #if defined(OS_POSIX) #include <list> #include <utility> #include "base/condition_variable.h" #include "base/lock.h" -#include "base/ref_counted.h" +#include "nsISupportsImpl.h" +#include "nsAutoPtr.h" #endif #include "base/message_loop.h" namespace base { // This replaces INFINITE from Win32 static const int kNoTimeout = -1; @@ -135,33 +136,35 @@ class WaitableEvent { // On Windows, one can close a HANDLE which is currently being waited on. The // MSDN documentation says that the resulting behaviour is 'undefined', but // it doesn't crash. However, if we were to include the following members // directly then, on POSIX, one couldn't use WaitableEventWatcher to watch an // event which gets deleted. This mismatch has bitten us several times now, // so we have a kernel of the WaitableEvent, which is reference counted. // WaitableEventWatchers may then take a reference and thus match the Windows // behaviour. - struct WaitableEventKernel : - public RefCountedThreadSafe<WaitableEventKernel> { + struct WaitableEventKernel MOZ_FINAL { public: + NS_INLINE_DECL_THREADSAFE_REFCOUNTING(WaitableEventKernel) WaitableEventKernel(bool manual_reset, bool initially_signaled) : manual_reset_(manual_reset), signaled_(initially_signaled) { } bool Dequeue(Waiter* waiter, void* tag); Lock lock_; const bool manual_reset_; bool signaled_; std::list<Waiter*> waiters_; + protected: + ~WaitableEventKernel() {} }; - scoped_refptr<WaitableEventKernel> kernel_; + nsRefPtr<WaitableEventKernel> kernel_; bool SignalAll(); bool SignalOne(); void Enqueue(Waiter* waiter); // When dealing with arrays of WaitableEvent*, we want to sort by the address // of the WaitableEvent in order to have a globally consistent locking order. // In that case we keep them, in sorted order, in an array of pairs where the
--- a/ipc/chromium/src/base/waitable_event_watcher.h +++ b/ipc/chromium/src/base/waitable_event_watcher.h @@ -7,16 +7,17 @@ #include "build/build_config.h" #if defined(OS_WIN) #include "base/object_watcher.h" #else #include "base/message_loop.h" #include "base/waitable_event.h" +#include "nsAutoPtr.h" #endif namespace base { class Flag; class AsyncWaiter; class AsyncCallbackTask; class WaitableEvent; @@ -136,18 +137,18 @@ class WaitableEventWatcher ObjectWatcher watcher_; #else // --------------------------------------------------------------------------- // Implementation of MessageLoop::DestructionObserver // --------------------------------------------------------------------------- void WillDestroyCurrentMessageLoop(); MessageLoop* message_loop_; - scoped_refptr<Flag> cancel_flag_; + nsRefPtr<Flag> cancel_flag_; AsyncWaiter* waiter_; AsyncCallbackTask* callback_task_; - scoped_refptr<WaitableEvent::WaitableEventKernel> kernel_; + nsRefPtr<WaitableEvent::WaitableEventKernel> kernel_; #endif }; } // namespace base #endif // BASE_WAITABLE_EVENT_WATCHER_H_
--- a/ipc/chromium/src/base/waitable_event_watcher_posix.cc +++ b/ipc/chromium/src/base/waitable_event_watcher_posix.cc @@ -4,16 +4,18 @@ #include "base/waitable_event_watcher.h" #include "base/condition_variable.h" #include "base/lock.h" #include "base/message_loop.h" #include "base/waitable_event.h" +#include "nsISupportsImpl.h" +#include "nsAutoPtr.h" #include "mozilla/Attributes.h" namespace base { // ----------------------------------------------------------------------------- // WaitableEventWatcher (async waits). // // The basic design is that we add an AsyncWaiter to the wait-list of the event. @@ -24,30 +26,33 @@ namespace base { // set when the wait has been canceled. At each stage in the above, we check the // flag before going onto the next stage. Since the wait may only be canceled in // the MessageLoop which runs the Task, we are assured that the delegate cannot // be called after canceling... // ----------------------------------------------------------------------------- // A thread-safe, reference-counted, write-once flag. // ----------------------------------------------------------------------------- -class Flag : public RefCountedThreadSafe<Flag> { +class Flag MOZ_FINAL { public: + NS_INLINE_DECL_THREADSAFE_REFCOUNTING(Flag) Flag() { flag_ = false; } void Set() { AutoLock locked(lock_); flag_ = true; } bool value() const { AutoLock locked(lock_); return flag_; } + protected: + ~Flag() {} private: mutable Lock lock_; bool flag_; }; // ----------------------------------------------------------------------------- // This is an asynchronous waiter which posts a task to a MessageLoop when // fired. An AsyncWaiter may only be in a single wait-list. @@ -80,17 +85,17 @@ class AsyncWaiter MOZ_FINAL : public Wai // See StopWatching for discussion bool Compare(void* tag) { return tag == flag_.get(); } private: MessageLoop *const message_loop_; Task *const cb_task_; - scoped_refptr<Flag> flag_; + nsRefPtr<Flag> flag_; }; // ----------------------------------------------------------------------------- // For async waits we need to make a callback in a MessageLoop thread. We do // this by posting this task, which calls the delegate and keeps track of when // the event is canceled. // ----------------------------------------------------------------------------- class AsyncCallbackTask : public Task { @@ -110,17 +115,17 @@ class AsyncCallbackTask : public Task { flag_->Set(); delegate_->OnWaitableEventSignaled(event_); } // We are deleted by the MessageLoop } private: - scoped_refptr<Flag> flag_; + nsRefPtr<Flag> flag_; WaitableEventWatcher::Delegate *const delegate_; WaitableEvent *const event_; }; WaitableEventWatcher::WaitableEventWatcher() : event_(NULL), message_loop_(NULL), cancel_flag_(NULL),
--- a/ipc/chromium/src/base/win_util.cc +++ b/ipc/chromium/src/base/win_util.cc @@ -4,18 +4,16 @@ #include "base/win_util.h" #include <map> #include <sddl.h> #include "base/logging.h" #include "base/registry.h" -#include "base/scoped_handle.h" -#include "base/scoped_ptr.h" #include "base/singleton.h" #include "base/string_util.h" #include "base/tracked.h" namespace win_util { WinVersion GetWinVersion() { static bool checked_version = false;
--- a/ipc/chromium/src/chrome/common/child_process.h +++ b/ipc/chromium/src/chrome/common/child_process.h @@ -4,18 +4,18 @@ #ifndef CHROME_COMMON_CHILD_PROCESS_H__ #define CHROME_COMMON_CHILD_PROCESS_H__ #include <string> #include <vector> #include "base/basictypes.h" #include "base/message_loop.h" -#include "base/scoped_ptr.h" #include "base/waitable_event.h" +#include "mozilla/UniquePtr.h" class ChildThread; // Base class for child processes of the browser process (i.e. renderer and // plugin host). This is a singleton object for each child process. class ChildProcess { public: @@ -46,17 +46,17 @@ class ChildProcess { void ReleaseProcess(); // Getter for the one ChildProcess object for this process. static ChildProcess* current() { return child_process_; } private: // NOTE: make sure that child_thread_ is listed before shutdown_event_, since // it depends on it (indirectly through IPC::SyncChannel). - scoped_ptr<ChildThread> child_thread_; + mozilla::UniquePtr<ChildThread> child_thread_; int ref_count_; // An event that will be signalled when we shutdown. base::WaitableEvent shutdown_event_; // The singleton instance for this process. static ChildProcess* child_process_;
--- a/ipc/chromium/src/chrome/common/child_process_host.h +++ b/ipc/chromium/src/chrome/common/child_process_host.h @@ -5,20 +5,20 @@ #ifndef CHROME_COMMON_CHILD_PROCESS_HOST_H_ #define CHROME_COMMON_CHILD_PROCESS_HOST_H_ #include "build/build_config.h" #include <list> #include "base/basictypes.h" -#include "base/scoped_ptr.h" #include "base/waitable_event_watcher.h" #include "chrome/common/child_process_info.h" #include "chrome/common/ipc_channel.h" +#include "mozilla/UniquePtr.h" namespace mozilla { namespace ipc { class FileDescriptor; } } class NotificationType; @@ -111,20 +111,20 @@ class ChildProcessHost : }; ListenerHook listener_; // True while we're waiting the channel to be opened. bool opening_channel_; // The IPC::Channel. - scoped_ptr<IPC::Channel> channel_; + mozilla::UniquePtr<IPC::Channel> channel_; // IPC Channel's id. std::wstring channel_id_; // Used to watch the child process handle. base::WaitableEventWatcher watcher_; - scoped_ptr<base::WaitableEvent> process_event_; + mozilla::UniquePtr<base::WaitableEvent> process_event_; }; #endif // CHROME_COMMON_CHILD_PROCESS_HOST_H_
--- a/ipc/chromium/src/chrome/common/child_thread.cc +++ b/ipc/chromium/src/chrome/common/child_thread.cc @@ -84,32 +84,32 @@ void ChildThread::OnMessageReceived(cons } } ChildThread* ChildThread::current() { return ChildProcess::current()->child_thread(); } void ChildThread::Init() { - channel_.reset(new IPC::Channel(channel_name_, - IPC::Channel::MODE_CLIENT, - this)); + channel_ = mozilla::MakeUnique<IPC::Channel>(channel_name_, + IPC::Channel::MODE_CLIENT, + this); #ifdef IPC_MESSAGE_LOG_ENABLED IPC::Logging::current()->SetIPCSender(this); #endif } void ChildThread::CleanUp() { #ifdef IPC_MESSAGE_LOG_ENABLED IPC::Logging::current()->SetIPCSender(NULL); #endif // Need to destruct the SyncChannel to the browser before we go away because // it caches a pointer to this thread. - channel_.reset(); + channel_ = nullptr; } void ChildThread::OnProcessFinalRelease() { if (!check_with_browser_before_shutdown_) { owner_loop_->PostTask(FROM_HERE, new MessageLoop::QuitTask()); return; } }
--- a/ipc/chromium/src/chrome/common/child_thread.h +++ b/ipc/chromium/src/chrome/common/child_thread.h @@ -3,16 +3,17 @@ // found in the LICENSE file. #ifndef CHROME_COMMON_CHILD_THREAD_H_ #define CHROME_COMMON_CHILD_THREAD_H_ #include "base/thread.h" #include "chrome/common/ipc_sync_channel.h" #include "chrome/common/message_router.h" +#include "mozilla/UniquePtr.h" class ResourceDispatcher; // Child processes's background thread should derive from this class. class ChildThread : public IPC::Channel::Listener, public IPC::Message::Sender, public base::Thread { public: @@ -64,17 +65,17 @@ class ChildThread : public IPC::Channel: #ifdef MOZ_NUWA_PROCESS static void MarkThread(); #endif // The message loop used to run tasks on the thread that started this thread. MessageLoop* owner_loop_; std::wstring channel_name_; - scoped_ptr<IPC::Channel> channel_; + mozilla::UniquePtr<IPC::Channel> channel_; // Used only on the background render thread to implement message routing // functionality to the consumers of the ChildThread. MessageRouter router_; Thread::Options options_; // If true, checks with the browser process before shutdown. This avoids race
--- a/ipc/chromium/src/chrome/common/file_descriptor_set_posix.h +++ b/ipc/chromium/src/chrome/common/file_descriptor_set_posix.h @@ -4,27 +4,27 @@ #ifndef CHROME_COMMON_FILE_DESCRIPTOR_SET_POSIX_H_ #define CHROME_COMMON_FILE_DESCRIPTOR_SET_POSIX_H_ #include <vector> #include "base/basictypes.h" #include "base/file_descriptor_posix.h" -#include "base/ref_counted.h" +#include "nsISupportsImpl.h" // ----------------------------------------------------------------------------- // A FileDescriptorSet is an ordered set of POSIX file descriptors. These are // associated with IPC messages so that descriptors can be transmitted over a // UNIX domain socket. // ----------------------------------------------------------------------------- -class FileDescriptorSet : public base::RefCountedThreadSafe<FileDescriptorSet> { +class FileDescriptorSet { public: + NS_INLINE_DECL_THREADSAFE_REFCOUNTING(FileDescriptorSet) FileDescriptorSet(); - ~FileDescriptorSet(); // Mac and Linux both limit the number of file descriptors per message to // slightly more than 250. enum { MAX_DESCRIPTORS_PER_MESSAGE = 250 }; // --------------------------------------------------------------------------- @@ -79,16 +79,18 @@ class FileDescriptorSet : public base::R // Set the contents of the set from the given buffer. This set must be empty // before calling. The auto-close flag is set on all the descriptors so that // unconsumed descriptors are closed on destruction. void SetDescriptors(const int* buffer, unsigned count); // --------------------------------------------------------------------------- private: + ~FileDescriptorSet(); + // A vector of descriptors and close flags. If this message is sent, then // these descriptors are sent as control data. After sending, any descriptors // with a true flag are closed. If this message has been received, then these // are the descriptors which were received and all close flags are true. std::vector<base::FileDescriptor> descriptors_; // This contains the index of the next descriptor which should be consumed. // It's used in a couple of ways. Firstly, at destruction we can check that
--- a/ipc/chromium/src/chrome/common/ipc_channel_posix.cc +++ b/ipc/chromium/src/chrome/common/ipc_channel_posix.cc @@ -17,24 +17,24 @@ #include <string> #include <map> #include "base/command_line.h" #include "base/eintr_wrapper.h" #include "base/lock.h" #include "base/logging.h" #include "base/process_util.h" -#include "base/scoped_ptr.h" #include "base/string_util.h" #include "base/singleton.h" #include "chrome/common/chrome_switches.h" #include "chrome/common/file_descriptor_set_posix.h" #include "chrome/common/ipc_logging.h" #include "chrome/common/ipc_message_utils.h" #include "mozilla/ipc/ProtocolUtils.h" +#include "mozilla/UniquePtr.h" #ifdef MOZ_TASK_TRACER #include "GeckoTaskTracerImpl.h" using namespace mozilla::tasktracer; #endif namespace IPC { @@ -366,19 +366,19 @@ bool Channel::ChannelImpl::CreatePipe(co */ void Channel::ChannelImpl::ResetFileDescriptor(int fd) { NS_ASSERTION(fd > 0 && fd == pipe_, "Invalid file descriptor"); EnqueueHelloMessage(); } bool Channel::ChannelImpl::EnqueueHelloMessage() { - scoped_ptr<Message> msg(new Message(MSG_ROUTING_NONE, - HELLO_MESSAGE_TYPE, - IPC::Message::PRIORITY_NORMAL)); + mozilla::UniquePtr<Message> msg(new Message(MSG_ROUTING_NONE, + HELLO_MESSAGE_TYPE, + IPC::Message::PRIORITY_NORMAL)); if (!msg->WriteInt(base::GetCurrentProcId())) { Close(); return false; } OutputQueuePush(msg.release()); return true; }
--- a/ipc/chromium/src/chrome/common/ipc_channel_posix.h +++ b/ipc/chromium/src/chrome/common/ipc_channel_posix.h @@ -12,16 +12,18 @@ #include <queue> #include <string> #include <vector> #include <list> #include "base/message_loop.h" #include "chrome/common/file_descriptor_set_posix.h" +#include "nsAutoPtr.h" + namespace IPC { // An implementation of ChannelImpl for POSIX systems that works via // socketpairs. See the .cc file for an overview of the implementation. class Channel::ChannelImpl : public MessageLoopForIO::Watcher { public: // Mirror methods of Channel, see ipc_channel.h for description. ChannelImpl(const std::wstring& channel_id, Mode mode, Listener* listener); @@ -141,17 +143,17 @@ class Channel::ChannelImpl : public Mess bool processing_incoming_; // This flag is set after we've closed the channel. bool closed_; #if defined(OS_MACOSX) struct PendingDescriptors { uint32_t id; - scoped_refptr<FileDescriptorSet> fds; + nsRefPtr<FileDescriptorSet> fds; PendingDescriptors() : id(0) { } PendingDescriptors(uint32_t id, FileDescriptorSet *fds) : id(id), fds(fds) { } };
--- a/ipc/chromium/src/chrome/common/ipc_channel_proxy.h +++ b/ipc/chromium/src/chrome/common/ipc_channel_proxy.h @@ -2,18 +2,19 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #ifndef CHROME_COMMON_IPC_CHANNEL_PROXY_H__ #define CHROME_COMMON_IPC_CHANNEL_PROXY_H__ #include <vector> #include "base/lock.h" -#include "base/ref_counted.h" #include "chrome/common/ipc_channel.h" +#include "nsISupportsImpl.h" +#include "nsAutoPtr.h" class MessageLoop; namespace IPC { //----------------------------------------------------------------------------- // IPC::ChannelProxy // @@ -41,19 +42,19 @@ namespace IPC { // // The consumer of IPC::ChannelProxy is responsible for allocating the Thread // instance where the IPC::Channel will be created and operated. // class ChannelProxy : public Message::Sender { public: // A class that receives messages on the thread where the IPC channel is // running. It can choose to prevent the default action for an IPC message. - class MessageFilter : public base::RefCountedThreadSafe<MessageFilter> { + class MessageFilter { public: - virtual ~MessageFilter() {} + NS_INLINE_DECL_THREADSAFE_REFCOUNTING(MessageFilter) // Called on the background thread to provide the filter with access to the // channel. Called when the IPC channel is initialized or when AddFilter // is called if the channel is already initialized. virtual void OnFilterAdded(Channel* channel) {} // Called on the background thread when the filter has been removed from // the ChannelProxy and when the Channel is closing. After a filter is @@ -72,16 +73,18 @@ class ChannelProxy : public Message::Sen // OnFilterRemoved is called immediately after this. virtual void OnChannelClosing() {} // Return true to indicate that the message was handled, or false to let // the message be handled in the default way. virtual bool OnMessageReceived(const Message& message) { return false; } + protected: + virtual ~MessageFilter() {} }; // Initializes a channel proxy. The channel_id and mode parameters are // passed directly to the underlying IPC::Channel. The listener is called on // the thread that creates the ChannelProxy. The filter's OnMessageReceived // method is called on the thread where the IPC::Channel is running. The // filter may be null if the consumer is not interested in handling messages // on the background thread. Any message not handled by the filter will be @@ -129,29 +132,30 @@ class ChannelProxy : public Message::Sen // A subclass uses this constructor if it needs to add more information // to the internal state. If create_pipe_now is true, the pipe is created // immediately. Otherwise it's created on the IO thread. ChannelProxy(const std::wstring& channel_id, Channel::Mode mode, MessageLoop* ipc_thread_loop, Context* context, bool create_pipe_now); // Used internally to hold state that is referenced on the IPC thread. - class Context : public base::RefCountedThreadSafe<Context>, - public Channel::Listener { + class Context : public Channel::Listener { public: + NS_INLINE_DECL_THREADSAFE_REFCOUNTING(Context) Context(Channel::Listener* listener, MessageFilter* filter, MessageLoop* ipc_thread); - virtual ~Context() { } MessageLoop* ipc_message_loop() const { return ipc_message_loop_; } const std::wstring& channel_id() const { return channel_id_; } // Dispatches a message on the listener thread. void OnDispatchMessage(const Message& message); protected: + virtual ~Context() {} + // IPC::Channel::Listener methods: virtual void OnMessageReceived(const Message& message); virtual void OnChannelConnected(int32_t peer_pid); virtual void OnChannelError(); // Like OnMessageReceived but doesn't try the filters. void OnMessageReceivedNoFilter(const Message& message); @@ -179,31 +183,31 @@ class ChannelProxy : public Message::Sen void OnRemoveFilter(MessageFilter* filter); void OnDispatchConnected(); void OnDispatchError(); MessageLoop* listener_message_loop_; Channel::Listener* listener_; // List of filters. This is only accessed on the IPC thread. - std::vector<scoped_refptr<MessageFilter> > filters_; + std::vector<nsRefPtr<MessageFilter> > filters_; MessageLoop* ipc_message_loop_; Channel* channel_; std::wstring channel_id_; int peer_pid_; bool channel_connected_called_; }; Context* context() { return context_; } private: void Init(const std::wstring& channel_id, Channel::Mode mode, MessageLoop* ipc_thread_loop, bool create_pipe_now); // By maintaining this indirection (ref-counted) to our internal state, we // can safely be destroyed while the background thread continues to do stuff // that involves this data. - scoped_refptr<Context> context_; + nsRefPtr<Context> context_; }; } // namespace IPC #endif // CHROME_COMMON_IPC_CHANNEL_PROXY_H__
--- a/ipc/chromium/src/chrome/common/ipc_channel_win.cc +++ b/ipc/chromium/src/chrome/common/ipc_channel_win.cc @@ -196,19 +196,19 @@ bool Channel::ChannelImpl::CreatePipe(co return false; } // Create the Hello message to be sent when Connect is called return EnqueueHelloMessage(); } bool Channel::ChannelImpl::EnqueueHelloMessage() { - scoped_ptr<Message> m(new Message(MSG_ROUTING_NONE, - HELLO_MESSAGE_TYPE, - IPC::Message::PRIORITY_NORMAL)); + mozilla::UniquePtr<Message> m = mozilla::MakeUnique<Message>(MSG_ROUTING_NONE, + HELLO_MESSAGE_TYPE, + IPC::Message::PRIORITY_NORMAL); if (!m->WriteInt(GetCurrentProcessId())) { CloseHandle(pipe_); pipe_ = INVALID_HANDLE_VALUE; return false; } OutputQueuePush(m.release()); return true;
--- a/ipc/chromium/src/chrome/common/ipc_channel_win.h +++ b/ipc/chromium/src/chrome/common/ipc_channel_win.h @@ -6,16 +6,17 @@ #define CHROME_COMMON_IPC_CHANNEL_WIN_H_ #include "chrome/common/ipc_channel.h" #include <queue> #include <string> #include "base/message_loop.h" +#include "mozilla/UniquePtr.h" class NonThreadSafe; namespace IPC { class Channel::ChannelImpl : public MessageLoopForIO::IOHandler { public: // Mirror methods of Channel, see ipc_channel.h for description. @@ -102,16 +103,16 @@ class Channel::ChannelImpl : public Mess // This variable is updated so it matches output_queue_.size(), except we can // read output_queue_length_ from any thread (if we're OK getting an // occasional out-of-date or bogus value). We use output_queue_length_ to // implement Unsound_NumQueuedMessages. size_t output_queue_length_; ScopedRunnableMethodFactory<ChannelImpl> factory_; - scoped_ptr<NonThreadSafe> thread_check_; + mozilla::UniquePtr<NonThreadSafe> thread_check_; DISALLOW_COPY_AND_ASSIGN(ChannelImpl); }; } // namespace IPC #endif // CHROME_COMMON_IPC_CHANNEL_WIN_H_
--- a/ipc/chromium/src/chrome/common/ipc_logging.h +++ b/ipc/chromium/src/chrome/common/ipc_logging.h @@ -9,16 +9,17 @@ #ifdef IPC_MESSAGE_LOG_ENABLED #include "base/lock.h" #include "base/message_loop.h" #include "base/singleton.h" #include "base/waitable_event_watcher.h" #include "chrome/common/ipc_message_utils.h" +#include "mozilla/UniquePtr.h" class MessageLoop; namespace IPC { class Message; // One instance per process. Needs to be created on the main thread (the UI @@ -86,18 +87,18 @@ class Logging : public base::WaitableEve std::wstring GetEventName(int browser_pid, bool enabled); void OnSendLogs(); void Log(const LogData& data); void RegisterWaitForEvent(bool enabled); base::WaitableEventWatcher watcher_; - scoped_ptr<base::WaitableEvent> logging_event_on_; - scoped_ptr<base::WaitableEvent> logging_event_off_; + mozilla::UniquePtr<base::WaitableEvent> logging_event_on_; + mozilla::UniquePtr<base::WaitableEvent> logging_event_off_; bool enabled_; std::vector<LogData> queued_logs_; bool queue_invoke_later_pending_; Message::Sender* sender_; MessageLoop* main_thread_;
--- a/ipc/chromium/src/chrome/common/ipc_message.h +++ b/ipc/chromium/src/chrome/common/ipc_message.h @@ -14,17 +14,17 @@ #include "GeckoTaskTracer.h" #endif #ifndef NDEBUG #define IPC_MESSAGE_LOG_ENABLED #endif #if defined(OS_POSIX) -#include "base/ref_counted.h" +#include "nsAutoPtr.h" #endif namespace base { struct FileDescriptor; } class FileDescriptorSet; @@ -357,17 +357,17 @@ class Message : public Pickle { const Header* header() const { return headerT<Header>(); } void InitLoggingVariables(const char* const name="???"); #if defined(OS_POSIX) // The set of file descriptors associated with this message. - scoped_refptr<FileDescriptorSet> file_descriptor_set_; + nsRefPtr<FileDescriptorSet> file_descriptor_set_; // Ensure that a FileDescriptorSet is allocated void EnsureFileDescriptorSet(); FileDescriptorSet* file_descriptor_set() { EnsureFileDescriptorSet(); return file_descriptor_set_.get(); }
--- a/ipc/chromium/src/chrome/common/ipc_sync_channel.cc +++ b/ipc/chromium/src/chrome/common/ipc_sync_channel.cc @@ -6,16 +6,17 @@ #include "base/lazy_instance.h" #include "base/logging.h" #include "base/thread_local.h" #include "base/message_loop.h" #include "base/waitable_event.h" #include "base/waitable_event_watcher.h" #include "chrome/common/ipc_sync_message.h" +#include "nsISupportsImpl.h" using base::TimeDelta; using base::TimeTicks; using base::WaitableEvent; namespace IPC { // When we're blocked in a Send(), we need to process incoming synchronous // messages right away because it could be blocking our reply (either @@ -29,36 +30,33 @@ namespace IPC { // allows us to dispatch incoming sync messages when blocked. The race // condition is handled because if Send is in the process of being called, it // will check the event. In case the listener thread isn't sending a message, // we queue a task on the listener thread to dispatch the received messages. // The messages are stored in this queue object that's shared among all // SyncChannel objects on the same thread (since one object can receive a // sync message while another one is blocked). -class SyncChannel::ReceivedSyncMsgQueue : - public base::RefCountedThreadSafe<ReceivedSyncMsgQueue> { +class SyncChannel::ReceivedSyncMsgQueue { public: + NS_INLINE_DECL_THREADSAFE_REFCOUNTING(SyncChannel::ReceivedSyncMsgQueue) // Returns the ReceivedSyncMsgQueue instance for this thread, creating one // if necessary. Call RemoveContext on the same thread when done. static ReceivedSyncMsgQueue* AddContext() { // We want one ReceivedSyncMsgQueue per listener thread (i.e. since multiple // SyncChannel objects can block the same thread). ReceivedSyncMsgQueue* rv = lazy_tls_ptr_.Pointer()->Get(); if (!rv) { rv = new ReceivedSyncMsgQueue(); ReceivedSyncMsgQueue::lazy_tls_ptr_.Pointer()->Set(rv); } rv->listener_count_++; return rv; } - ~ReceivedSyncMsgQueue() { - } - // Called on IPC thread when a synchronous message or reply arrives. void QueueMessage(const Message& msg, SyncChannel::SyncContext* context) { bool was_task_pending; { AutoLock auto_lock(message_lock_); was_task_pending = task_pending_; task_pending_ = true; @@ -87,17 +85,17 @@ class SyncChannel::ReceivedSyncMsgQueue task_pending_ = false; } DispatchMessages(); } void DispatchMessages() { while (true) { Message* message; - scoped_refptr<SyncChannel::SyncContext> context; + nsRefPtr<SyncChannel::SyncContext> context; { AutoLock auto_lock(message_lock_); if (message_queue_.empty()) break; message = message_queue_.front().message; context = message_queue_.front().context; message_queue_.pop_front(); @@ -143,31 +141,34 @@ class SyncChannel::ReceivedSyncMsgQueue if (received_replies_[i].context->TryToUnblockListener(message)) { delete message; received_replies_.erase(received_replies_.begin() + i); return; } } } + protected: + ~ReceivedSyncMsgQueue() {} + private: // See the comment in SyncChannel::SyncChannel for why this event is created // as manual reset. ReceivedSyncMsgQueue() : dispatch_event_(true, false), listener_message_loop_(MessageLoop::current()), task_pending_(false), listener_count_(0) { } // Holds information about a queued synchronous message or reply. struct QueuedMessage { QueuedMessage(Message* m, SyncContext* c) : message(m), context(c) { } Message* message; - scoped_refptr<SyncChannel::SyncContext> context; + nsRefPtr<SyncChannel::SyncContext> context; }; typedef std::deque<QueuedMessage> SyncMessageQueue; SyncMessageQueue message_queue_; std::vector<QueuedMessage> received_replies_; // Set when we got a synchronous message that we must respond to as the @@ -363,17 +364,17 @@ bool SyncChannel::Send(Message* message) bool SyncChannel::SendWithTimeout(Message* message, int timeout_ms) { if (!message->is_sync()) { ChannelProxy::Send(message); return true; } // *this* might get deleted in WaitForReply. - scoped_refptr<SyncContext> context(sync_context()); + nsRefPtr<SyncContext> context(sync_context()); if (context->shutdown_event()->IsSignaled()) { delete message; return false; } DCHECK(sync_messages_with_no_timeout_allowed_ || timeout_ms != base::kNoTimeout); SyncMessage* sync_msg = static_cast<SyncMessage*>(message);
--- a/ipc/chromium/src/chrome/common/ipc_sync_channel.h +++ b/ipc/chromium/src/chrome/common/ipc_sync_channel.h @@ -4,22 +4,23 @@ #ifndef CHROME_COMMON_IPC_SYNC_SENDER_H__ #define CHROME_COMMON_IPC_SYNC_SENDER_H__ #include <string> #include <deque> #include "base/basictypes.h" #include "base/lock.h" -#include "base/ref_counted.h" #include "base/scoped_handle.h" #include "base/waitable_event.h" #include "base/waitable_event_watcher.h" #include "chrome/common/ipc_channel_proxy.h" +#include "nsAutoPtr.h" + namespace IPC { class SyncMessage; class MessageReplyDeserializer; // This is similar to IPC::ChannelProxy, with the added feature of supporting // sending synchronous messages. // Note that care must be taken that the lifetime of the ipc_thread argument @@ -118,17 +119,17 @@ class SyncChannel : public ChannelProxy, base::WaitableEvent* done_event; bool send_result; }; typedef std::deque<PendingSyncMsg> PendingSyncMessageQueue; PendingSyncMessageQueue deserializers_; Lock deserializers_lock_; - scoped_refptr<ReceivedSyncMsgQueue> received_sync_msgs_; + nsRefPtr<ReceivedSyncMsgQueue> received_sync_msgs_; base::WaitableEvent* shutdown_event_; base::WaitableEventWatcher shutdown_watcher_; }; private: // WaitableEventWatcher::Delegate implementation. virtual void OnWaitableEventSignaled(base::WaitableEvent* arg);
--- a/ipc/glue/GeckoChildProcessHost.h +++ b/ipc/glue/GeckoChildProcessHost.h @@ -2,17 +2,16 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #ifndef __IPC_GLUE_GECKOCHILDPROCESSHOST_H__ #define __IPC_GLUE_GECKOCHILDPROCESSHOST_H__ #include "base/file_path.h" #include "base/process_util.h" -#include "base/scoped_ptr.h" #include "base/waitable_event.h" #include "chrome/common/child_process_host.h" #include "mozilla/DebugOnly.h" #include "mozilla/ipc/FileDescriptor.h" #include "mozilla/Monitor.h" #include "mozilla/StaticPtr.h"
--- a/js/src/jsgc.cpp +++ b/js/src/jsgc.cpp @@ -3227,17 +3227,17 @@ GCHelperState::finish() // Wait for any lingering background sweeping to finish. waitBackgroundSweepEnd(); if (done) PR_DestroyCondVar(done); } GCHelperState::State -GCHelperState::state() +GCHelperState::state() const { JS_ASSERT(rt->gc.currentThreadOwnsGCLock()); return state_; } void GCHelperState::setState(State state) { @@ -3378,16 +3378,25 @@ GCHelperState::waitBackgroundSweepOrAllo if (state() == ALLOCATING) setState(CANCEL_ALLOCATION); while (state() == SWEEPING || state() == CANCEL_ALLOCATION) waitForBackgroundThread(); if (rt->gc.incrementalState == NO_INCREMENTAL) rt->gc.assertBackgroundSweepingFinished(); } +void +GCHelperState::assertStateIsIdle() const +{ +#ifdef DEBUG + AutoLockGC lock(rt); + JS_ASSERT(state() == IDLE); +#endif +} + /* Must be called with the GC lock taken. */ inline void GCHelperState::startBackgroundAllocationIfIdle() { if (state_ == IDLE) startBackgroundThread(ALLOCATING); } @@ -5533,25 +5542,26 @@ GCRuntime::gcCycle(bool incremental, int // It's ok if threads other than the main thread have suppressGC set, as // they are operating on zones which will not be collected from here. JS_ASSERT(!rt->mainThread.suppressGC); // Assert if this is a GC unsafe region. JS::AutoAssertOnGC::VerifyIsSafeToGC(rt); - /* - * As we about to purge caches and clear the mark bits we must wait for - * any background finalization to finish. We must also wait for the - * background allocation to finish so we can avoid taking the GC lock - * when manipulating the chunks during the GC. - */ - { + // As we about to purge caches and clear the mark bits we must wait for + // any background finalization to finish. We must also wait for the + // background allocation to finish so we can avoid taking the GC lock + // when manipulating the chunks during the GC. + if (incrementalState == NO_INCREMENTAL) { gcstats::AutoPhase ap(stats, gcstats::PHASE_WAIT_BACKGROUND_THREAD); waitBackgroundSweepOrAllocEnd(); + } else { + // The helper thread does not run between incremental slices. + helperState.assertStateIsIdle(); } State prevState = incrementalState; if (!incremental) { /* If non-incremental GC was requested, reset incremental GC. */ resetIncrementalGC("requested"); stats.nonincremental("requested");
--- a/js/src/jsgc.h +++ b/js/src/jsgc.h @@ -989,17 +989,17 @@ class GCHelperState State state_; // Thread which work is being performed on, or null. PRThread *thread; void startBackgroundThread(State newState); void waitForBackgroundThread(); - State state(); + State state() const; void setState(State state); bool sweepFlag; bool shrinkFlag; bool backgroundAllocation; friend class js::gc::ArenaLists; @@ -1037,16 +1037,19 @@ class GCHelperState void startBackgroundShrink(); /* Must be called without the GC lock taken. */ void waitBackgroundSweepEnd(); /* Must be called without the GC lock taken. */ void waitBackgroundSweepOrAllocEnd(); + /* Must be called without the GC lock taken. */ + void assertStateIsIdle() const; + /* Must be called with the GC lock taken. */ void startBackgroundAllocationIfIdle(); bool canBackgroundAllocate() const { return backgroundAllocation; } void disableBackgroundAllocation() {
--- a/netwerk/protocol/ftp/nsFtpConnectionThread.cpp +++ b/netwerk/protocol/ftp/nsFtpConnectionThread.cpp @@ -89,16 +89,17 @@ nsFtpState::nsFtpState() , mInternalError(NS_OK) , mReconnectAndLoginAgain(false) , mCacheConnection(true) , mPort(21) , mAddressChecked(false) , mServerIsIPv6(false) , mUseUTF8(false) , mControlStatus(NS_OK) + , mDoomCache(false) , mDeferredCallbackPending(false) { LOG_ALWAYS(("FTP:(%x) nsFtpState created", this)); // make sure handler stays around NS_ADDREF(gFtpHandler); }
--- a/security/manager/ssl/src/nsNSSComponent.cpp +++ b/security/manager/ssl/src/nsNSSComponent.cpp @@ -698,16 +698,25 @@ static const CipherPref sCipherPrefs[] = static const int32_t OCSP_ENABLED_DEFAULT = 1; static const bool REQUIRE_SAFE_NEGOTIATION_DEFAULT = false; static const bool ALLOW_UNRESTRICTED_RENEGO_DEFAULT = false; static const bool FALSE_START_ENABLED_DEFAULT = true; static const bool NPN_ENABLED_DEFAULT = true; static const bool ALPN_ENABLED_DEFAULT = false; +static void +ConfigureTLSSessionIdentifiers() +{ + bool disableSessionIdentifiers = + Preferences::GetBool("security.ssl.disable_session_identifiers", false); + SSL_OptionSetDefault(SSL_ENABLE_SESSION_TICKETS, !disableSessionIdentifiers); + SSL_OptionSetDefault(SSL_NO_CACHE, disableSessionIdentifiers); +} + namespace { class CipherSuiteChangeObserver : public nsIObserver { public: NS_DECL_ISUPPORTS NS_DECL_NSIOBSERVER @@ -989,17 +998,17 @@ nsNSSComponent::InitializeNSS() return NS_ERROR_UNEXPECTED; } DisableMD5(); // Initialize the certverifier log before calling any functions that library. InitCertVerifierLog(); LoadLoadableRoots(); - SSL_OptionSetDefault(SSL_ENABLE_SESSION_TICKETS, true); + ConfigureTLSSessionIdentifiers(); bool requireSafeNegotiation = Preferences::GetBool("security.ssl.require_safe_negotiation", REQUIRE_SAFE_NEGOTIATION_DEFAULT); SSL_OptionSetDefault(SSL_REQUIRE_SAFE_NEGOTIATION, requireSafeNegotiation); bool allowUnrestrictedRenego = Preferences::GetBool("security.ssl.allow_unrestricted_renego_everywhere__temporarily_available_pref", @@ -1299,16 +1308,18 @@ nsNSSComponent::Observe(nsISupports* aSu } else if (prefName.EqualsLiteral("security.ssl.enable_npn")) { SSL_OptionSetDefault(SSL_ENABLE_NPN, Preferences::GetBool("security.ssl.enable_npn", NPN_ENABLED_DEFAULT)); } else if (prefName.EqualsLiteral("security.ssl.enable_alpn")) { SSL_OptionSetDefault(SSL_ENABLE_ALPN, Preferences::GetBool("security.ssl.enable_alpn", ALPN_ENABLED_DEFAULT)); + } else if (prefName.Equals("security.ssl.disable_session_identifiers")) { + ConfigureTLSSessionIdentifiers(); } else if (prefName.EqualsLiteral("security.OCSP.enabled") || prefName.EqualsLiteral("security.OCSP.require") || prefName.EqualsLiteral("security.OCSP.GET.enabled") || prefName.EqualsLiteral("security.ssl.enable_ocsp_stapling") || prefName.EqualsLiteral("security.cert_pinning.enforcement_level")) { MutexAutoLock lock(mutex); setValidationOptions(false, lock); } else if (prefName.EqualsLiteral("network.ntlm.send-lm-response")) {
--- a/testing/mochitest/mochitest_options.py +++ b/testing/mochitest/mochitest_options.py @@ -738,17 +738,17 @@ class B2GOptions(MochitestOptions): defaults["httpPort"] = DEFAULT_PORTS['http'] defaults["sslPort"] = DEFAULT_PORTS['https'] defaults["logFile"] = "mochitest.log" defaults["autorun"] = True defaults["closeWhenDone"] = True defaults["testPath"] = "" defaults["extensionsToExclude"] = ["specialpowers"] # See dependencies of bug 1038943. - defaults["leakThreshold"] = 5116 + defaults["leakThreshold"] = 5180 self.set_defaults(**defaults) def verifyRemoteOptions(self, options): if options.remoteWebServer == None: if os.name != "nt": options.remoteWebServer = moznetwork.get_ip() else: self.error("You must specify a --remote-webserver=<ip address>")
--- a/xpcom/build/nsXPComInit.cpp +++ b/xpcom/build/nsXPComInit.cpp @@ -126,16 +126,17 @@ extern nsresult nsStringInputStreamConst #include "base/command_line.h" #include "base/message_loop.h" #include "mozilla/ipc/BrowserProcessSubThread.h" #include "mozilla/AvailableMemoryTracker.h" #include "mozilla/ClearOnShutdown.h" #include "mozilla/CountingAllocatorBase.h" #include "mozilla/SystemMemoryReporter.h" +#include "mozilla/UniquePtr.h" #include "mozilla/ipc/GeckoChildProcessHost.h" #ifdef MOZ_VISUAL_EVENT_TRACER #include "mozilla/VisualEventTracer.h" #endif #include "ogg/ogg.h" @@ -517,18 +518,17 @@ NS_InitXPCOM2(nsIServiceManager** aResul sMessageLoop->set_thread_name("Gecko"); // Set experimental values for main thread hangs: // 512ms for transient hangs and 8192ms for permanent hangs sMessageLoop->set_hang_timeouts(512, 8192); } if (XRE_GetProcessType() == GeckoProcessType_Default && !BrowserProcessSubThread::GetMessageLoop(BrowserProcessSubThread::IO)) { - scoped_ptr<BrowserProcessSubThread> ioThread( - new BrowserProcessSubThread(BrowserProcessSubThread::IO)); + UniquePtr<BrowserProcessSubThread> ioThread = MakeUnique<BrowserProcessSubThread>(BrowserProcessSubThread::IO); base::Thread::Options options; options.message_loop_type = MessageLoop::TYPE_IO; if (NS_WARN_IF(!ioThread->StartWithOptions(options))) { return NS_ERROR_FAILURE; } sIOThread = ioThread.release();