[SCM] WebKit Debian packaging branch, debian/experimental, updated. upstream/1.3.3-9427-gc2be6fc

zmo at google.com zmo at google.com
Wed Dec 22 12:56:50 UTC 2010


The following commit has been merged in the debian/experimental branch:
commit 6a8e9d6e2ad208d26abe6960a97746b200a0a096
Author: zmo at google.com <zmo at google.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Date:   Thu Sep 2 17:54:23 2010 +0000

    2010-09-01  Zhenyao Mo  <zmo at google.com>
    
            Reviewed by Kenneth Russell.
    
            Roll ANGLE under webkit to r402
            https://bugs.webkit.org/show_bug.cgi?id=45004
    
            * platform/graphics/mac/GraphicsContext3DMac.mm: Update the code to use newer ANGLE interface.
            (WebCore::GraphicsContext3D::GraphicsContext3D):
    2010-09-01  Zhenyao Mo  <zmo at google.com>
    
            Reviewed by Kenneth Russell.
    
            Roll ANGLE under webkit to r402
            https://bugs.webkit.org/show_bug.cgi?id=45004
    
            * ANGLE.xcodeproj/project.pbxproj:
            * include/GLES2/gl2ext.h:
            * include/GLSLANG/ResourceLimits.h: Removed.
            * include/GLSLANG/ShaderLang.h:
            * src/compiler/BaseTypes.h:
            (getPrecisionString):
            (getBasicString):
            (IsSampler):
            (getQualifierString):
            * src/compiler/Initialize.cpp:
            (BuiltInConstants):
            (IdentifyBuiltIns):
            * src/compiler/Initialize.h:
            * src/compiler/InitializeDll.cpp:
            (InitProcess):
            (DetachProcess):
            (InitThread):
            (DetachThread):
            * src/compiler/InitializeDll.h:
            * src/compiler/InitializeParseContext.h:
            * src/compiler/Intermediate.cpp:
            (GetHigherPrecision):
            (TIntermediate::addBinaryMath):
            (TIntermediate::setAggregateOperator):
            (TIntermediate::addComma):
            (TIntermediate::postProcess):
            (TIntermBinary::promote):
            (CompareStruct):
            * src/compiler/OutputGLSL.cpp:
            (TOutputGLSL::writeFunctionParameters):
            (TOutputGLSL::visitUnary):
            (TOutputGLSL::visitBranch):
            * src/compiler/OutputHLSL.cpp:
            (sh::OutputHLSL::header):
            (sh::OutputHLSL::visitBinary):
            (sh::OutputHLSL::visitAggregate):
            (sh::OutputHLSL::handleExcessiveLoop):
            (sh::OutputHLSL::addConstructor):
            * src/compiler/ParseHelper.cpp:
            (TParseContext::constructorErrorCheck):
            (TParseContext::samplerErrorCheck):
            (TParseContext::paramErrorCheck):
            (TParseContext::findFunction):
            (TParseContext::executeInitializer):
            (TParseContext::addConstructor):
            (TParseContext::addConstStruct):
            (FreeParseContextIndex):
            (GetGlobalParseContext):
            * src/compiler/PoolAlloc.h:
            (TPoolAllocator::tHeader::tHeader):
            (pool_allocator::allocate):
            (pool_allocator::deallocate):
            * src/compiler/ShaderLang.cpp:
            (ShInitialize):
            (ShFinalize):
            (ShInitBuiltInResource):
            * src/compiler/SymbolTable.cpp:
            (TType::getStructSize):
            * src/compiler/SymbolTable.h:
            (TVariable::setQualifier):
            * src/compiler/Types.h:
            (TType::TType):
            (TType::getBasicType):
            (TType::setBasicType):
            (TType::getPrecision):
            (TType::setPrecision):
            (TType::getQualifier):
            (TType::setQualifier):
            (TType::getNominalSize):
            (TType::setNominalSize):
            (TType::isMatrix):
            (TType::setMatrix):
            (TType::isArray):
            (TType::getArraySize):
            (TType::setArraySize):
            (TType::getMaxArraySize):
            (TType::setMaxArraySize):
            (TType::clearArrayness):
            (TType::setArrayInformationType):
            (TType::getArrayInformationType):
            (TType::isVector):
            (TType::isScalar):
            (TType::setStruct):
            (TType::getTypeName):
            (TType::setTypeName):
            (TType::isField):
            (TType::getFieldName):
            (TType::setFieldName):
            (TType::getBasicString):
            (TType::getPrecisionString):
            (TType::getQualifierString):
            * src/compiler/glslang.l:
            * src/compiler/glslang.y:
            * src/compiler/intermediate.h:
            (TIntermNode::getLine):
            (TIntermNode::setLine):
            (TIntermTyped::getAsTyped):
            (TIntermTyped::setType):
            (TIntermTyped::getType):
            (TIntermTyped::getTypePointer):
            (TIntermTyped::getBasicType):
            (TIntermTyped::getQualifier):
            (TIntermTyped::getPrecision):
            (TIntermTyped::getNominalSize):
            (TIntermTyped::isMatrix):
            (TIntermTyped::isArray):
            (TIntermTyped::isVector):
            (TIntermTyped::isScalar):
            (TIntermTyped::getBasicString):
            (TIntermTyped::getQualifierString):
            (TIntermSymbol::getId):
            (TIntermSymbol::getSymbol):
            (TIntermOperator::setOp):
            (TIntermBinary::setLeft):
            (TIntermBinary::setRight):
            (TIntermBinary::getLeft):
            (TIntermBinary::getRight):
            (TIntermUnary::setOperand):
            (TIntermUnary::getOperand):
            (TIntermAggregate::getAsAggregate):
            (TIntermAggregate::getSequence):
            (TIntermAggregate::setName):
            (TIntermAggregate::getName):
            (TIntermAggregate::setUserDefined):
            (TIntermAggregate::isUserDefined):
            (TIntermAggregate::getQualifier):
            (TIntermAggregate::setOptimize):
            (TIntermAggregate::setDebug):
            (TIntermSelection::getCondition):
            (TIntermSelection::getTrueBlock):
            (TIntermSelection::getFalseBlock):
            (TIntermSelection::getAsSelectionNode):
            * src/compiler/parseConst.cpp:
            (TConstTraverser::TConstTraverser):
            * src/compiler/preprocessor/atom.c:
            (InitAtomTable):
            * src/compiler/preprocessor/atom.h:
            * src/compiler/preprocessor/compile.h:
            * src/compiler/preprocessor/cpp.c:
            * src/compiler/preprocessor/cpp.h:
            * src/compiler/preprocessor/cppstruct.c:
            * src/compiler/preprocessor/memory.c:
            * src/compiler/preprocessor/memory.h:
            * src/compiler/preprocessor/parser.h:
            * src/compiler/preprocessor/preprocess.h:
            * src/compiler/preprocessor/scanner.c:
            * src/compiler/preprocessor/scanner.h:
            * src/compiler/preprocessor/slglobals.h:
            * src/compiler/preprocessor/symbols.c:
            (NewSymbol):
            * src/compiler/preprocessor/symbols.h:
            * src/compiler/preprocessor/tokens.c:
            (RecordToken):
            * src/compiler/preprocessor/tokens.h:
            * src/libEGL/Display.cpp:
            (egl::Display::Display):
            (egl::Display::initialize):
            (egl::Display::terminate):
            (egl::Display::createDevice):
            (egl::Display::createWindowSurface):
            (egl::Display::createContext):
            (egl::Display::getMultiSampleSupport):
            (egl::Display::getCompressedTextureSupport):
            * src/libEGL/Display.h:
            * src/libEGL/Surface.cpp:
            (egl::Surface::Surface):
            (egl::Surface::resetSwapChain):
            (egl::Surface::getWindowHandle):
            (egl::Surface::writeRecordableFlipState):
            (egl::Surface::applyFlipState):
            (egl::Surface::releaseRecordedState):
            (egl::Surface::checkForWindowResize):
            (egl::Surface::swap):
            * src/libEGL/Surface.h:
            * src/libEGL/libEGL.cpp:
            * src/libEGL/libEGL.vcproj:
            * src/libGLESv2/Blit.cpp:
            (gl::Blit::setVertexShader):
            (gl::Blit::setPixelShader):
            (gl::Blit::setFormatConvertShaders):
            * src/libGLESv2/Buffer.cpp:
            (gl::Buffer::Buffer):
            * src/libGLESv2/Buffer.h:
            * src/libGLESv2/Context.cpp:
            (gl::Context::Context):
            (gl::Context::~Context):
            (gl::Context::makeCurrent):
            (gl::Context::markAllStateDirty):
            (gl::Context::getReadFramebufferHandle):
            (gl::Context::getDrawFramebufferHandle):
            (gl::Context::getRenderbufferHandle):
            (gl::Context::getArrayBufferHandle):
            (gl::Context::setVertexAttribState):
            (gl::Context::createBuffer):
            (gl::Context::createProgram):
            (gl::Context::createShader):
            (gl::Context::createTexture):
            (gl::Context::createRenderbuffer):
            (gl::Context::deleteBuffer):
            (gl::Context::deleteShader):
            (gl::Context::deleteProgram):
            (gl::Context::deleteTexture):
            (gl::Context::deleteRenderbuffer):
            (gl::Context::getBuffer):
            (gl::Context::getShader):
            (gl::Context::getProgram):
            (gl::Context::getTexture):
            (gl::Context::getRenderbuffer):
            (gl::Context::getReadFramebuffer):
            (gl::Context::getDrawFramebuffer):
            (gl::Context::bindArrayBuffer):
            (gl::Context::bindElementArrayBuffer):
            (gl::Context::bindTexture2D):
            (gl::Context::bindTextureCubeMap):
            (gl::Context::bindReadFramebuffer):
            (gl::Context::bindDrawFramebuffer):
            (gl::Context::bindRenderbuffer):
            (gl::Context::useProgram):
            (gl::Context::setFramebufferZero):
            (gl::Context::setRenderbufferStorage):
            (gl::Context::getFramebuffer):
            (gl::Context::getArrayBuffer):
            (gl::Context::getElementArrayBuffer):
            (gl::Context::getCurrentProgram):
            (gl::Context::getTexture2D):
            (gl::Context::getTextureCubeMap):
            (gl::Context::getSamplerTexture):
            (gl::Context::getFloatv):
            (gl::Context::getIntegerv):
            (gl::Context::getQueryParameterInfo):
            (gl::Context::applyRenderTarget):
            (gl::Context::applyState):
            (gl::Context::applyIndexBuffer):
            (gl::Context::readPixels):
            (gl::Context::clear):
            (gl::Context::finish):
            (gl::Context::flush):
            (gl::Context::supportsShaderModel3):
            (gl::Context::getMaxSupportedSamples):
            (gl::Context::getNearestSupportedSamples):
            (gl::Context::supportsCompressedTextures):
            (gl::Context::detachBuffer):
            (gl::Context::detachTexture):
            (gl::Context::detachFramebuffer):
            (gl::Context::detachRenderbuffer):
            (gl::Context::getIncompleteTexture):
            (gl::Context::initExtensionString):
            (gl::Context::blitFramebuffer):
            * src/libGLESv2/Context.h:
            (gl::AttributeState::AttributeState):
            * src/libGLESv2/Framebuffer.cpp:
            (gl::Framebuffer::Framebuffer):
            (gl::Framebuffer::~Framebuffer):
            (gl::Framebuffer::lookupRenderbuffer):
            (gl::Framebuffer::setColorbuffer):
            (gl::Framebuffer::setDepthbuffer):
            (gl::Framebuffer::setStencilbuffer):
            (gl::Framebuffer::detachTexture):
            (gl::Framebuffer::detachRenderbuffer):
            (gl::Framebuffer::getRenderTargetSerial):
            (gl::Framebuffer::getRenderTarget):
            (gl::Framebuffer::getDepthStencil):
            (gl::Framebuffer::getDepthbufferSerial):
            (gl::Framebuffer::getStencilbufferSerial):
            (gl::Framebuffer::getColorbuffer):
            (gl::Framebuffer::getDepthbuffer):
            (gl::Framebuffer::getStencilbuffer):
            (gl::Framebuffer::getColorbufferHandle):
            (gl::Framebuffer::getDepthbufferHandle):
            (gl::Framebuffer::getStencilbufferHandle):
            (gl::Framebuffer::hasStencil):
            (gl::Framebuffer::isMultisample):
            (gl::Framebuffer::completeness):
            (gl::DefaultFramebuffer::DefaultFramebuffer):
            (gl::Framebuffer::getSamples):
            (gl::DefaultFramebuffer::completeness):
            * src/libGLESv2/Framebuffer.h:
            * src/libGLESv2/Program.cpp:
            (gl::Program::Program):
            (gl::Program::~Program):
            (gl::Program::attachShader):
            (gl::Program::detachShader):
            (gl::Program::linkVaryings):
            (gl::Program::link):
            (gl::Program::unlink):
            (gl::Program::release):
            (gl::Program::addRef):
            (gl::Program::getRefCount):
            (gl::Program::getDxViewportLocation):
            * src/libGLESv2/Program.h:
            * src/libGLESv2/RefCountObject.cpp: Added.
            (gl::RefCountObject::RefCountObject):
            (gl::RefCountObject::~RefCountObject):
            (gl::RefCountObject::addRef):
            (gl::RefCountObject::release):
            (gl::RefCountObjectBindingPointer::set):
            * src/libGLESv2/RefCountObject.h: Added.
            (gl::RefCountObject::id):
            (gl::RefCountObjectBindingPointer::RefCountObjectBindingPointer):
            (gl::RefCountObjectBindingPointer::~RefCountObjectBindingPointer):
            (gl::RefCountObjectBindingPointer::get):
            (gl::RefCountObjectBindingPointer::id):
            (gl::RefCountObjectBindingPointer::operator ! ):
            (gl::BindingPointer::set):
            (gl::BindingPointer::get):
            (gl::BindingPointer::operator -> ):
            * src/libGLESv2/Renderbuffer.cpp:
            (gl::Renderbuffer::Renderbuffer):
            (gl::Renderbuffer::~Renderbuffer):
            (gl::Renderbuffer::isColorbuffer):
            (gl::Renderbuffer::isDepthbuffer):
            (gl::Renderbuffer::isStencilbuffer):
            (gl::Renderbuffer::getRenderTarget):
            (gl::Renderbuffer::getDepthStencil):
            (gl::Renderbuffer::getWidth):
            (gl::Renderbuffer::getHeight):
            (gl::Renderbuffer::getFormat):
            (gl::Renderbuffer::getD3DFormat):
            (gl::Renderbuffer::getSerial):
            (gl::Renderbuffer::setStorage):
            (gl::RenderbufferStorage::RenderbufferStorage):
            (gl::RenderbufferStorage::~RenderbufferStorage):
            (gl::RenderbufferStorage::isColorbuffer):
            (gl::RenderbufferStorage::isDepthbuffer):
            (gl::RenderbufferStorage::isStencilbuffer):
            (gl::RenderbufferStorage::getRenderTarget):
            (gl::RenderbufferStorage::getDepthStencil):
            (gl::RenderbufferStorage::getWidth):
            (gl::RenderbufferStorage::getHeight):
            (gl::RenderbufferStorage::setSize):
            (gl::RenderbufferStorage::getFormat):
            (gl::RenderbufferStorage::getD3DFormat):
            (gl::RenderbufferStorage::getSamples):
            (gl::RenderbufferStorage::getSerial):
            (gl::RenderbufferStorage::issueSerial):
            (gl::Colorbuffer::Colorbuffer):
            (gl::Colorbuffer::isColorbuffer):
            (gl::Colorbuffer::getRedSize):
            (gl::Colorbuffer::getGreenSize):
            (gl::Colorbuffer::getBlueSize):
            (gl::Colorbuffer::getAlphaSize):
            (gl::DepthStencilbuffer::DepthStencilbuffer):
            (gl::DepthStencilbuffer::~DepthStencilbuffer):
            (gl::DepthStencilbuffer::isDepthbuffer):
            (gl::DepthStencilbuffer::isStencilbuffer):
            (gl::DepthStencilbuffer::getDepthSize):
            (gl::DepthStencilbuffer::getStencilSize):
            (gl::DepthStencilbuffer::getDepthStencil):
            (gl::Depthbuffer::Depthbuffer):
            (gl::Depthbuffer::~Depthbuffer):
            (gl::Depthbuffer::isDepthbuffer):
            (gl::Depthbuffer::isStencilbuffer):
            (gl::Stencilbuffer::Stencilbuffer):
            (gl::Stencilbuffer::~Stencilbuffer):
            (gl::Stencilbuffer::isDepthbuffer):
            (gl::Stencilbuffer::isStencilbuffer):
            * src/libGLESv2/Renderbuffer.h:
            (gl::Renderbuffer::getStorage):
            * src/libGLESv2/ResourceManager.cpp: Added.
            (gl::ResourceManager::ResourceManager):
            (gl::ResourceManager::~ResourceManager):
            (gl::ResourceManager::addRef):
            (gl::ResourceManager::release):
            (gl::ResourceManager::createBuffer):
            (gl::ResourceManager::createShader):
            (gl::ResourceManager::createProgram):
            (gl::ResourceManager::createTexture):
            (gl::ResourceManager::createRenderbuffer):
            (gl::ResourceManager::deleteBuffer):
            (gl::ResourceManager::deleteShader):
            (gl::ResourceManager::deleteProgram):
            (gl::ResourceManager::deleteTexture):
            (gl::ResourceManager::deleteRenderbuffer):
            (gl::ResourceManager::getBuffer):
            (gl::ResourceManager::getShader):
            (gl::ResourceManager::getTexture):
            (gl::ResourceManager::getProgram):
            (gl::ResourceManager::getRenderbuffer):
            (gl::ResourceManager::setRenderbuffer):
            (gl::ResourceManager::checkBufferAllocation):
            (gl::ResourceManager::checkTextureAllocation):
            (gl::ResourceManager::checkRenderbufferAllocation):
            * src/libGLESv2/ResourceManager.h: Added.
            * src/libGLESv2/Shader.cpp:
            (gl::Shader::Shader):
            (gl::Shader::addRef):
            (gl::Shader::release):
            (gl::Shader::getRefCount):
            (gl::Shader::parseVaryings):
            (gl::VertexShader::VertexShader):
            (gl::FragmentShader::FragmentShader):
            * src/libGLESv2/Shader.h:
            * src/libGLESv2/Texture.cpp:
            (gl::Texture::Image::Image):
            (gl::Texture::Texture):
            (gl::Texture::getBlitter):
            (gl::Texture::selectFormat):
            (gl::Texture::loadImageData):
            (gl::Texture::loadAlphaImageData):
            (gl::Texture::loadLuminanceImageData):
            (gl::Texture::loadLuminanceAlphaImageData):
            (gl::Texture::loadRGBUByteImageData):
            (gl::Texture::loadRGB565ImageData):
            (gl::Texture::loadRGBAUByteImageData):
            (gl::Texture::loadRGBA4444ImageData):
            (gl::Texture::loadRGBA5551ImageData):
            (gl::Texture::loadBGRAImageData):
            (gl::Texture::createSurface):
            (gl::Texture::setImage):
            (gl::Texture::setCompressedImage):
            (gl::Texture::subImage):
            (gl::Texture::subImageCompressed):
            (gl::Texture2D::Texture2D):
            (gl::Texture2D::getFormat):
            (gl::Texture2D::setCompressedImage):
            (gl::Texture2D::subImage):
            (gl::Texture2D::subImageCompressed):
            (gl::Texture2D::copyImage):
            (gl::Texture2D::copySubImage):
            (gl::Texture2D::isCompressed):
            (gl::Texture2D::getColorbuffer):
            (gl::TextureCubeMap::TextureCubeMap):
            (gl::TextureCubeMap::getFormat):
            (gl::TextureCubeMap::setCompressedImage):
            (gl::TextureCubeMap::subImage):
            (gl::TextureCubeMap::subImageCompressed):
            (gl::TextureCubeMap::isCompressed):
            (gl::TextureCubeMap::copyImage):
            (gl::TextureCubeMap::copySubImage):
            (gl::TextureCubeMap::getColorbuffer):
            (gl::Texture::TextureColorbufferProxy::addRef):
            (gl::Texture::TextureColorbufferProxy::release):
            (gl::Texture::TextureColorbufferProxy::getWidth):
            (gl::Texture::TextureColorbufferProxy::getHeight):
            (gl::Texture::TextureColorbufferProxy::getFormat):
            * src/libGLESv2/Texture.h:
            * src/libGLESv2/libGLESv2.cpp:
            * src/libGLESv2/libGLESv2.def:
            * src/libGLESv2/libGLESv2.vcproj:
            * src/libGLESv2/main.h:
            * src/libGLESv2/utilities.cpp:
            (gl::ComputeCompressedPitch):
            (gl::ComputeCompressedSize):
            (gl::IsCompressed):
            (gl::ComputePixelSize):
            (gl::CheckTextureFormatType):
            (es2dx::ConvertRenderbufferFormat):
            (es2dx::GetSamplesFromMultisampleType):
            (es2dx::GetMultisampleTypeFromSamples):
            * src/libGLESv2/utilities.h:
    
    
    git-svn-id: http://svn.webkit.org/repository/webkit/trunk@66675 268f45cc-cd09-0410-ab3c-d52691b4dbfc

diff --git a/ANGLE/ANGLE.xcodeproj/project.pbxproj b/ANGLE/ANGLE.xcodeproj/project.pbxproj
index 67b6c3f..95f41c3 100644
--- a/ANGLE/ANGLE.xcodeproj/project.pbxproj
+++ b/ANGLE/ANGLE.xcodeproj/project.pbxproj
@@ -35,7 +35,6 @@
 		FB39D2B11200F35A00088E69 /* UnfoldSelect.cpp in Sources */ = {isa = PBXBuildFile; fileRef = FB39D26D1200F35A00088E69 /* UnfoldSelect.cpp */; };
 		FB39D7231201032000088E69 /* glslang.cpp in Sources */ = {isa = PBXBuildFile; fileRef = FB39D7201201032000088E69 /* glslang.cpp */; };
 		FB39D7241201032000088E69 /* glslang_tab.cpp in Sources */ = {isa = PBXBuildFile; fileRef = FB39D7221201032000088E69 /* glslang_tab.cpp */; };
-		FB39D76D120110FC00088E69 /* ResourceLimits.h in Headers */ = {isa = PBXBuildFile; fileRef = FB39D2BE1200F3E600088E69 /* ResourceLimits.h */; settings = {ATTRIBUTES = (Public, ); }; };
 		FB39D76E120110FC00088E69 /* ShaderLang.h in Headers */ = {isa = PBXBuildFile; fileRef = FB39D2BF1200F3E600088E69 /* ShaderLang.h */; settings = {ATTRIBUTES = (Public, ); }; };
 /* End PBXBuildFile section */
 
@@ -177,7 +176,6 @@
 		FB39D26D1200F35A00088E69 /* UnfoldSelect.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = UnfoldSelect.cpp; sourceTree = "<group>"; };
 		FB39D26E1200F35A00088E69 /* UnfoldSelect.h */ = {isa = PBXFileReference; explicitFileType = sourcecode.cpp.h; fileEncoding = 4; path = UnfoldSelect.h; sourceTree = "<group>"; };
 		FB39D26F1200F35A00088E69 /* unistd.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = unistd.h; sourceTree = "<group>"; };
-		FB39D2BE1200F3E600088E69 /* ResourceLimits.h */ = {isa = PBXFileReference; explicitFileType = sourcecode.cpp.h; fileEncoding = 4; path = ResourceLimits.h; sourceTree = "<group>"; };
 		FB39D2BF1200F3E600088E69 /* ShaderLang.h */ = {isa = PBXFileReference; explicitFileType = sourcecode.cpp.h; fileEncoding = 4; path = ShaderLang.h; sourceTree = "<group>"; };
 		FB39D7201201032000088E69 /* glslang.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = glslang.cpp; path = DerivedSources/ANGLE/glslang.cpp; sourceTree = BUILT_PRODUCTS_DIR; };
 		FB39D7211201032000088E69 /* glslang_tab.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = glslang_tab.h; path = DerivedSources/ANGLE/glslang_tab.h; sourceTree = BUILT_PRODUCTS_DIR; };
@@ -413,7 +411,6 @@
 		FB39D2BD1200F3E600088E69 /* GLSLANG */ = {
 			isa = PBXGroup;
 			children = (
-				FB39D2BE1200F3E600088E69 /* ResourceLimits.h */,
 				FB39D2BF1200F3E600088E69 /* ShaderLang.h */,
 			);
 			name = GLSLANG;
@@ -427,7 +424,6 @@
 			isa = PBXHeadersBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
-				FB39D76D120110FC00088E69 /* ResourceLimits.h in Headers */,
 				FB39D76E120110FC00088E69 /* ShaderLang.h in Headers */,
 			);
 			runOnlyForDeploymentPostprocessing = 0;
@@ -461,7 +457,6 @@
 			isa = PBXProject;
 			buildConfigurationList = FB39D0731200ED9200088E69 /* Build configuration list for PBXProject "ANGLE" */;
 			compatibilityVersion = "Xcode 2.4";
-			developmentRegion = English;
 			hasScannedForEncodings = 0;
 			knownRegions = (
 				English,
diff --git a/ANGLE/ChangeLog b/ANGLE/ChangeLog
index 44234a8..e886a42 100644
--- a/ANGLE/ChangeLog
+++ b/ANGLE/ChangeLog
@@ -1,3 +1,461 @@
+2010-09-01  Zhenyao Mo  <zmo at google.com>
+
+        Reviewed by Kenneth Russell.
+
+        Roll ANGLE under webkit to r402
+        https://bugs.webkit.org/show_bug.cgi?id=45004
+
+        * ANGLE.xcodeproj/project.pbxproj:
+        * include/GLES2/gl2ext.h:
+        * include/GLSLANG/ResourceLimits.h: Removed.
+        * include/GLSLANG/ShaderLang.h:
+        * src/compiler/BaseTypes.h:
+        (getPrecisionString):
+        (getBasicString):
+        (IsSampler):
+        (getQualifierString):
+        * src/compiler/Initialize.cpp:
+        (BuiltInConstants):
+        (IdentifyBuiltIns):
+        * src/compiler/Initialize.h:
+        * src/compiler/InitializeDll.cpp:
+        (InitProcess):
+        (DetachProcess):
+        (InitThread):
+        (DetachThread):
+        * src/compiler/InitializeDll.h:
+        * src/compiler/InitializeParseContext.h:
+        * src/compiler/Intermediate.cpp:
+        (GetHigherPrecision):
+        (TIntermediate::addBinaryMath):
+        (TIntermediate::setAggregateOperator):
+        (TIntermediate::addComma):
+        (TIntermediate::postProcess):
+        (TIntermBinary::promote):
+        (CompareStruct):
+        * src/compiler/OutputGLSL.cpp:
+        (TOutputGLSL::writeFunctionParameters):
+        (TOutputGLSL::visitUnary):
+        (TOutputGLSL::visitBranch):
+        * src/compiler/OutputHLSL.cpp:
+        (sh::OutputHLSL::header):
+        (sh::OutputHLSL::visitBinary):
+        (sh::OutputHLSL::visitAggregate):
+        (sh::OutputHLSL::handleExcessiveLoop):
+        (sh::OutputHLSL::addConstructor):
+        * src/compiler/ParseHelper.cpp:
+        (TParseContext::constructorErrorCheck):
+        (TParseContext::samplerErrorCheck):
+        (TParseContext::paramErrorCheck):
+        (TParseContext::findFunction):
+        (TParseContext::executeInitializer):
+        (TParseContext::addConstructor):
+        (TParseContext::addConstStruct):
+        (FreeParseContextIndex):
+        (GetGlobalParseContext):
+        * src/compiler/PoolAlloc.h:
+        (TPoolAllocator::tHeader::tHeader):
+        (pool_allocator::allocate):
+        (pool_allocator::deallocate):
+        * src/compiler/ShaderLang.cpp:
+        (ShInitialize):
+        (ShFinalize):
+        (ShInitBuiltInResource):
+        * src/compiler/SymbolTable.cpp:
+        (TType::getStructSize):
+        * src/compiler/SymbolTable.h:
+        (TVariable::setQualifier):
+        * src/compiler/Types.h:
+        (TType::TType):
+        (TType::getBasicType):
+        (TType::setBasicType):
+        (TType::getPrecision):
+        (TType::setPrecision):
+        (TType::getQualifier):
+        (TType::setQualifier):
+        (TType::getNominalSize):
+        (TType::setNominalSize):
+        (TType::isMatrix):
+        (TType::setMatrix):
+        (TType::isArray):
+        (TType::getArraySize):
+        (TType::setArraySize):
+        (TType::getMaxArraySize):
+        (TType::setMaxArraySize):
+        (TType::clearArrayness):
+        (TType::setArrayInformationType):
+        (TType::getArrayInformationType):
+        (TType::isVector):
+        (TType::isScalar):
+        (TType::setStruct):
+        (TType::getTypeName):
+        (TType::setTypeName):
+        (TType::isField):
+        (TType::getFieldName):
+        (TType::setFieldName):
+        (TType::getBasicString):
+        (TType::getPrecisionString):
+        (TType::getQualifierString):
+        * src/compiler/glslang.l:
+        * src/compiler/glslang.y:
+        * src/compiler/intermediate.h:
+        (TIntermNode::getLine):
+        (TIntermNode::setLine):
+        (TIntermTyped::getAsTyped):
+        (TIntermTyped::setType):
+        (TIntermTyped::getType):
+        (TIntermTyped::getTypePointer):
+        (TIntermTyped::getBasicType):
+        (TIntermTyped::getQualifier):
+        (TIntermTyped::getPrecision):
+        (TIntermTyped::getNominalSize):
+        (TIntermTyped::isMatrix):
+        (TIntermTyped::isArray):
+        (TIntermTyped::isVector):
+        (TIntermTyped::isScalar):
+        (TIntermTyped::getBasicString):
+        (TIntermTyped::getQualifierString):
+        (TIntermSymbol::getId):
+        (TIntermSymbol::getSymbol):
+        (TIntermOperator::setOp):
+        (TIntermBinary::setLeft):
+        (TIntermBinary::setRight):
+        (TIntermBinary::getLeft):
+        (TIntermBinary::getRight):
+        (TIntermUnary::setOperand):
+        (TIntermUnary::getOperand):
+        (TIntermAggregate::getAsAggregate):
+        (TIntermAggregate::getSequence):
+        (TIntermAggregate::setName):
+        (TIntermAggregate::getName):
+        (TIntermAggregate::setUserDefined):
+        (TIntermAggregate::isUserDefined):
+        (TIntermAggregate::getQualifier):
+        (TIntermAggregate::setOptimize):
+        (TIntermAggregate::setDebug):
+        (TIntermSelection::getCondition):
+        (TIntermSelection::getTrueBlock):
+        (TIntermSelection::getFalseBlock):
+        (TIntermSelection::getAsSelectionNode):
+        * src/compiler/parseConst.cpp:
+        (TConstTraverser::TConstTraverser):
+        * src/compiler/preprocessor/atom.c:
+        (InitAtomTable):
+        * src/compiler/preprocessor/atom.h:
+        * src/compiler/preprocessor/compile.h:
+        * src/compiler/preprocessor/cpp.c:
+        * src/compiler/preprocessor/cpp.h:
+        * src/compiler/preprocessor/cppstruct.c:
+        * src/compiler/preprocessor/memory.c:
+        * src/compiler/preprocessor/memory.h:
+        * src/compiler/preprocessor/parser.h:
+        * src/compiler/preprocessor/preprocess.h:
+        * src/compiler/preprocessor/scanner.c:
+        * src/compiler/preprocessor/scanner.h:
+        * src/compiler/preprocessor/slglobals.h:
+        * src/compiler/preprocessor/symbols.c:
+        (NewSymbol):
+        * src/compiler/preprocessor/symbols.h:
+        * src/compiler/preprocessor/tokens.c:
+        (RecordToken):
+        * src/compiler/preprocessor/tokens.h:
+        * src/libEGL/Display.cpp:
+        (egl::Display::Display):
+        (egl::Display::initialize):
+        (egl::Display::terminate):
+        (egl::Display::createDevice):
+        (egl::Display::createWindowSurface):
+        (egl::Display::createContext):
+        (egl::Display::getMultiSampleSupport):
+        (egl::Display::getCompressedTextureSupport):
+        * src/libEGL/Display.h:
+        * src/libEGL/Surface.cpp:
+        (egl::Surface::Surface):
+        (egl::Surface::resetSwapChain):
+        (egl::Surface::getWindowHandle):
+        (egl::Surface::writeRecordableFlipState):
+        (egl::Surface::applyFlipState):
+        (egl::Surface::releaseRecordedState):
+        (egl::Surface::checkForWindowResize):
+        (egl::Surface::swap):
+        * src/libEGL/Surface.h:
+        * src/libEGL/libEGL.cpp:
+        * src/libEGL/libEGL.vcproj:
+        * src/libGLESv2/Blit.cpp:
+        (gl::Blit::setVertexShader):
+        (gl::Blit::setPixelShader):
+        (gl::Blit::setFormatConvertShaders):
+        * src/libGLESv2/Buffer.cpp:
+        (gl::Buffer::Buffer):
+        * src/libGLESv2/Buffer.h:
+        * src/libGLESv2/Context.cpp:
+        (gl::Context::Context):
+        (gl::Context::~Context):
+        (gl::Context::makeCurrent):
+        (gl::Context::markAllStateDirty):
+        (gl::Context::getReadFramebufferHandle):
+        (gl::Context::getDrawFramebufferHandle):
+        (gl::Context::getRenderbufferHandle):
+        (gl::Context::getArrayBufferHandle):
+        (gl::Context::setVertexAttribState):
+        (gl::Context::createBuffer):
+        (gl::Context::createProgram):
+        (gl::Context::createShader):
+        (gl::Context::createTexture):
+        (gl::Context::createRenderbuffer):
+        (gl::Context::deleteBuffer):
+        (gl::Context::deleteShader):
+        (gl::Context::deleteProgram):
+        (gl::Context::deleteTexture):
+        (gl::Context::deleteRenderbuffer):
+        (gl::Context::getBuffer):
+        (gl::Context::getShader):
+        (gl::Context::getProgram):
+        (gl::Context::getTexture):
+        (gl::Context::getRenderbuffer):
+        (gl::Context::getReadFramebuffer):
+        (gl::Context::getDrawFramebuffer):
+        (gl::Context::bindArrayBuffer):
+        (gl::Context::bindElementArrayBuffer):
+        (gl::Context::bindTexture2D):
+        (gl::Context::bindTextureCubeMap):
+        (gl::Context::bindReadFramebuffer):
+        (gl::Context::bindDrawFramebuffer):
+        (gl::Context::bindRenderbuffer):
+        (gl::Context::useProgram):
+        (gl::Context::setFramebufferZero):
+        (gl::Context::setRenderbufferStorage):
+        (gl::Context::getFramebuffer):
+        (gl::Context::getArrayBuffer):
+        (gl::Context::getElementArrayBuffer):
+        (gl::Context::getCurrentProgram):
+        (gl::Context::getTexture2D):
+        (gl::Context::getTextureCubeMap):
+        (gl::Context::getSamplerTexture):
+        (gl::Context::getFloatv):
+        (gl::Context::getIntegerv):
+        (gl::Context::getQueryParameterInfo):
+        (gl::Context::applyRenderTarget):
+        (gl::Context::applyState):
+        (gl::Context::applyIndexBuffer):
+        (gl::Context::readPixels):
+        (gl::Context::clear):
+        (gl::Context::finish):
+        (gl::Context::flush):
+        (gl::Context::supportsShaderModel3):
+        (gl::Context::getMaxSupportedSamples):
+        (gl::Context::getNearestSupportedSamples):
+        (gl::Context::supportsCompressedTextures):
+        (gl::Context::detachBuffer):
+        (gl::Context::detachTexture):
+        (gl::Context::detachFramebuffer):
+        (gl::Context::detachRenderbuffer):
+        (gl::Context::getIncompleteTexture):
+        (gl::Context::initExtensionString):
+        (gl::Context::blitFramebuffer):
+        * src/libGLESv2/Context.h:
+        (gl::AttributeState::AttributeState):
+        * src/libGLESv2/Framebuffer.cpp:
+        (gl::Framebuffer::Framebuffer):
+        (gl::Framebuffer::~Framebuffer):
+        (gl::Framebuffer::lookupRenderbuffer):
+        (gl::Framebuffer::setColorbuffer):
+        (gl::Framebuffer::setDepthbuffer):
+        (gl::Framebuffer::setStencilbuffer):
+        (gl::Framebuffer::detachTexture):
+        (gl::Framebuffer::detachRenderbuffer):
+        (gl::Framebuffer::getRenderTargetSerial):
+        (gl::Framebuffer::getRenderTarget):
+        (gl::Framebuffer::getDepthStencil):
+        (gl::Framebuffer::getDepthbufferSerial):
+        (gl::Framebuffer::getStencilbufferSerial):
+        (gl::Framebuffer::getColorbuffer):
+        (gl::Framebuffer::getDepthbuffer):
+        (gl::Framebuffer::getStencilbuffer):
+        (gl::Framebuffer::getColorbufferHandle):
+        (gl::Framebuffer::getDepthbufferHandle):
+        (gl::Framebuffer::getStencilbufferHandle):
+        (gl::Framebuffer::hasStencil):
+        (gl::Framebuffer::isMultisample):
+        (gl::Framebuffer::completeness):
+        (gl::DefaultFramebuffer::DefaultFramebuffer):
+        (gl::Framebuffer::getSamples):
+        (gl::DefaultFramebuffer::completeness):
+        * src/libGLESv2/Framebuffer.h:
+        * src/libGLESv2/Program.cpp:
+        (gl::Program::Program):
+        (gl::Program::~Program):
+        (gl::Program::attachShader):
+        (gl::Program::detachShader):
+        (gl::Program::linkVaryings):
+        (gl::Program::link):
+        (gl::Program::unlink):
+        (gl::Program::release):
+        (gl::Program::addRef):
+        (gl::Program::getRefCount):
+        (gl::Program::getDxViewportLocation):
+        * src/libGLESv2/Program.h:
+        * src/libGLESv2/RefCountObject.cpp: Added.
+        (gl::RefCountObject::RefCountObject):
+        (gl::RefCountObject::~RefCountObject):
+        (gl::RefCountObject::addRef):
+        (gl::RefCountObject::release):
+        (gl::RefCountObjectBindingPointer::set):
+        * src/libGLESv2/RefCountObject.h: Added.
+        (gl::RefCountObject::id):
+        (gl::RefCountObjectBindingPointer::RefCountObjectBindingPointer):
+        (gl::RefCountObjectBindingPointer::~RefCountObjectBindingPointer):
+        (gl::RefCountObjectBindingPointer::get):
+        (gl::RefCountObjectBindingPointer::id):
+        (gl::RefCountObjectBindingPointer::operator ! ):
+        (gl::BindingPointer::set):
+        (gl::BindingPointer::get):
+        (gl::BindingPointer::operator -> ):
+        * src/libGLESv2/Renderbuffer.cpp:
+        (gl::Renderbuffer::Renderbuffer):
+        (gl::Renderbuffer::~Renderbuffer):
+        (gl::Renderbuffer::isColorbuffer):
+        (gl::Renderbuffer::isDepthbuffer):
+        (gl::Renderbuffer::isStencilbuffer):
+        (gl::Renderbuffer::getRenderTarget):
+        (gl::Renderbuffer::getDepthStencil):
+        (gl::Renderbuffer::getWidth):
+        (gl::Renderbuffer::getHeight):
+        (gl::Renderbuffer::getFormat):
+        (gl::Renderbuffer::getD3DFormat):
+        (gl::Renderbuffer::getSerial):
+        (gl::Renderbuffer::setStorage):
+        (gl::RenderbufferStorage::RenderbufferStorage):
+        (gl::RenderbufferStorage::~RenderbufferStorage):
+        (gl::RenderbufferStorage::isColorbuffer):
+        (gl::RenderbufferStorage::isDepthbuffer):
+        (gl::RenderbufferStorage::isStencilbuffer):
+        (gl::RenderbufferStorage::getRenderTarget):
+        (gl::RenderbufferStorage::getDepthStencil):
+        (gl::RenderbufferStorage::getWidth):
+        (gl::RenderbufferStorage::getHeight):
+        (gl::RenderbufferStorage::setSize):
+        (gl::RenderbufferStorage::getFormat):
+        (gl::RenderbufferStorage::getD3DFormat):
+        (gl::RenderbufferStorage::getSamples):
+        (gl::RenderbufferStorage::getSerial):
+        (gl::RenderbufferStorage::issueSerial):
+        (gl::Colorbuffer::Colorbuffer):
+        (gl::Colorbuffer::isColorbuffer):
+        (gl::Colorbuffer::getRedSize):
+        (gl::Colorbuffer::getGreenSize):
+        (gl::Colorbuffer::getBlueSize):
+        (gl::Colorbuffer::getAlphaSize):
+        (gl::DepthStencilbuffer::DepthStencilbuffer):
+        (gl::DepthStencilbuffer::~DepthStencilbuffer):
+        (gl::DepthStencilbuffer::isDepthbuffer):
+        (gl::DepthStencilbuffer::isStencilbuffer):
+        (gl::DepthStencilbuffer::getDepthSize):
+        (gl::DepthStencilbuffer::getStencilSize):
+        (gl::DepthStencilbuffer::getDepthStencil):
+        (gl::Depthbuffer::Depthbuffer):
+        (gl::Depthbuffer::~Depthbuffer):
+        (gl::Depthbuffer::isDepthbuffer):
+        (gl::Depthbuffer::isStencilbuffer):
+        (gl::Stencilbuffer::Stencilbuffer):
+        (gl::Stencilbuffer::~Stencilbuffer):
+        (gl::Stencilbuffer::isDepthbuffer):
+        (gl::Stencilbuffer::isStencilbuffer):
+        * src/libGLESv2/Renderbuffer.h:
+        (gl::Renderbuffer::getStorage):
+        * src/libGLESv2/ResourceManager.cpp: Added.
+        (gl::ResourceManager::ResourceManager):
+        (gl::ResourceManager::~ResourceManager):
+        (gl::ResourceManager::addRef):
+        (gl::ResourceManager::release):
+        (gl::ResourceManager::createBuffer):
+        (gl::ResourceManager::createShader):
+        (gl::ResourceManager::createProgram):
+        (gl::ResourceManager::createTexture):
+        (gl::ResourceManager::createRenderbuffer):
+        (gl::ResourceManager::deleteBuffer):
+        (gl::ResourceManager::deleteShader):
+        (gl::ResourceManager::deleteProgram):
+        (gl::ResourceManager::deleteTexture):
+        (gl::ResourceManager::deleteRenderbuffer):
+        (gl::ResourceManager::getBuffer):
+        (gl::ResourceManager::getShader):
+        (gl::ResourceManager::getTexture):
+        (gl::ResourceManager::getProgram):
+        (gl::ResourceManager::getRenderbuffer):
+        (gl::ResourceManager::setRenderbuffer):
+        (gl::ResourceManager::checkBufferAllocation):
+        (gl::ResourceManager::checkTextureAllocation):
+        (gl::ResourceManager::checkRenderbufferAllocation):
+        * src/libGLESv2/ResourceManager.h: Added.
+        * src/libGLESv2/Shader.cpp:
+        (gl::Shader::Shader):
+        (gl::Shader::addRef):
+        (gl::Shader::release):
+        (gl::Shader::getRefCount):
+        (gl::Shader::parseVaryings):
+        (gl::VertexShader::VertexShader):
+        (gl::FragmentShader::FragmentShader):
+        * src/libGLESv2/Shader.h:
+        * src/libGLESv2/Texture.cpp:
+        (gl::Texture::Image::Image):
+        (gl::Texture::Texture):
+        (gl::Texture::getBlitter):
+        (gl::Texture::selectFormat):
+        (gl::Texture::loadImageData):
+        (gl::Texture::loadAlphaImageData):
+        (gl::Texture::loadLuminanceImageData):
+        (gl::Texture::loadLuminanceAlphaImageData):
+        (gl::Texture::loadRGBUByteImageData):
+        (gl::Texture::loadRGB565ImageData):
+        (gl::Texture::loadRGBAUByteImageData):
+        (gl::Texture::loadRGBA4444ImageData):
+        (gl::Texture::loadRGBA5551ImageData):
+        (gl::Texture::loadBGRAImageData):
+        (gl::Texture::createSurface):
+        (gl::Texture::setImage):
+        (gl::Texture::setCompressedImage):
+        (gl::Texture::subImage):
+        (gl::Texture::subImageCompressed):
+        (gl::Texture2D::Texture2D):
+        (gl::Texture2D::getFormat):
+        (gl::Texture2D::setCompressedImage):
+        (gl::Texture2D::subImage):
+        (gl::Texture2D::subImageCompressed):
+        (gl::Texture2D::copyImage):
+        (gl::Texture2D::copySubImage):
+        (gl::Texture2D::isCompressed):
+        (gl::Texture2D::getColorbuffer):
+        (gl::TextureCubeMap::TextureCubeMap):
+        (gl::TextureCubeMap::getFormat):
+        (gl::TextureCubeMap::setCompressedImage):
+        (gl::TextureCubeMap::subImage):
+        (gl::TextureCubeMap::subImageCompressed):
+        (gl::TextureCubeMap::isCompressed):
+        (gl::TextureCubeMap::copyImage):
+        (gl::TextureCubeMap::copySubImage):
+        (gl::TextureCubeMap::getColorbuffer):
+        (gl::Texture::TextureColorbufferProxy::addRef):
+        (gl::Texture::TextureColorbufferProxy::release):
+        (gl::Texture::TextureColorbufferProxy::getWidth):
+        (gl::Texture::TextureColorbufferProxy::getHeight):
+        (gl::Texture::TextureColorbufferProxy::getFormat):
+        * src/libGLESv2/Texture.h:
+        * src/libGLESv2/libGLESv2.cpp:
+        * src/libGLESv2/libGLESv2.def:
+        * src/libGLESv2/libGLESv2.vcproj:
+        * src/libGLESv2/main.h:
+        * src/libGLESv2/utilities.cpp:
+        (gl::ComputeCompressedPitch):
+        (gl::ComputeCompressedSize):
+        (gl::IsCompressed):
+        (gl::ComputePixelSize):
+        (gl::CheckTextureFormatType):
+        (es2dx::ConvertRenderbufferFormat):
+        (es2dx::GetSamplesFromMultisampleType):
+        (es2dx::GetMultisampleTypeFromSamples):
+        * src/libGLESv2/utilities.h:
+
 2010-08-17  Chris Marrin  <cmarrin at apple.com>
 
         Unreviewed.
diff --git a/ANGLE/include/GLES2/gl2ext.h b/ANGLE/include/GLES2/gl2ext.h
index 80a6820..01844de 100644
--- a/ANGLE/include/GLES2/gl2ext.h
+++ b/ANGLE/include/GLES2/gl2ext.h
@@ -222,6 +222,12 @@ typedef void* GLeglImageOES;
 #define GL_UNSIGNED_INT_2_10_10_10_REV_EXT                      0x8368
 #endif
 
+/* GL_EXT_texture_compression_dxt1 */
+#ifndef GL_EXT_texture_compression_dxt1
+#define GL_COMPRESSED_RGB_S3TC_DXT1_EXT                         0x83F0
+#define GL_COMPRESSED_RGBA_S3TC_DXT1_EXT                        0x83F1
+#endif
+
 /*------------------------------------------------------------------------*
  * IMG extension tokens
  *------------------------------------------------------------------------*/
@@ -351,6 +357,25 @@ typedef void* GLeglImageOES;
 #endif
 
 /*------------------------------------------------------------------------*
+ * ANGLE extension tokens
+ *------------------------------------------------------------------------*/
+
+/* GL_ANGLE_framebuffer_blit */
+#ifndef GL_ANGLE_framebuffer_blit
+#define GL_READ_FRAMEBUFFER_ANGLE         0x8CA8
+#define GL_DRAW_FRAMEBUFFER_ANGLE         0x8CA9
+#define GL_DRAW_FRAMEBUFFER_BINDING_ANGLE 0x8CA6 // alias GL_FRAMEBUFFER_BINDING
+#define GL_READ_FRAMEBUFFER_BINDING_ANGLE 0x8CAA
+#endif
+
+/* GL_ANGLE_framebuffer_multisample */
+#ifndef GL_ANGLE_framebuffer_multisample
+#define GL_RENDERBUFFER_SAMPLES_ANGLE                   0x8CAB
+#define GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE_ANGLE     0x8D56
+#define GL_MAX_SAMPLES_ANGLE                            0x8D57
+#endif
+
+/*------------------------------------------------------------------------*
  * End of extension tokens, start of corresponding extension functions
  *------------------------------------------------------------------------*/
 
@@ -623,6 +648,11 @@ typedef void (GL_APIENTRYP PFNGLMULTIDRAWELEMENTSEXTPROC) (GLenum mode, const GL
 #define GL_EXT_texture_type_2_10_10_10_REV 1
 #endif
 
+/* GL_EXT_texture_compression_dxt1 */
+#ifndef GL_EXT_texture_compression_dxt1
+#define GL_EXT_texture_compression_dxt1 1
+#endif
+
 /*------------------------------------------------------------------------*
  * IMG extension functions
  *------------------------------------------------------------------------*/
@@ -766,6 +796,34 @@ typedef void (GL_APIENTRYP PFNGLSTARTTILINGQCOMPROC) (GLuint x, GLuint y, GLuint
 typedef void (GL_APIENTRYP PFNGLENDTILINGQCOMPROC) (GLbitfield preserveMask);
 #endif
 
+/*------------------------------------------------------------------------*
+ * ANGLE extension functions
+ *------------------------------------------------------------------------*/
+
+/* GL_ANGLE_framebuffer_blit */
+#ifndef GL_ANGLE_framebuffer_blit
+#define GL_ANGLE_framebuffer_blit 1
+#ifdef GL_GLEXT_PROTOTYPES
+GL_APICALL void GL_APIENTRY glBlitFramebufferANGLE (GLint srcX0, GLint srcY0, GLint srcX1, GLint srcY1,
+                                                    GLint dstX0, GLint dstY0, GLint dstX1, GLint dstY1,
+                                                    GLbitfield mask, GLenum filter);
+#endif
+typedef void (GL_APIENTRYP PFNGLBLITFRAMEBUFFERANGLEPROC) (GLint srcX0, GLint srcY0, GLint srcX1, GLint srcY1,
+                                                           GLint dstX0, GLint dstY0, GLint dstX1, GLint dstY1,
+                                                           GLbitfield mask, GLenum filter);
+#endif
+
+/* GL_ANGLE_framebuffer_multisample */
+#ifndef GL_ANGLE_framebuffer_multisample
+#define GL_ANGLE_framebuffer_multisample 1
+#ifdef GL_GLEXT_PROTOTYPES
+GL_APICALL void GL_APIENTRY glRenderbufferStorageMultisampleANGLE (GLenum target, GLsizei samples, GLenum internalformat, 
+                                                                   GLsizei width, GLsizei height);
+#endif
+typedef void (GL_APIENTRYP PFNGLRENDERBUFFERSTORAGEMULTISAMPLEANGLEPROC) (GLenum target, GLsizei samples, GLenum internalformat,
+                                                                          GLsizei width, GLsizei height);
+#endif
+
 #ifdef __cplusplus
 }
 #endif
diff --git a/ANGLE/include/GLSLANG/ResourceLimits.h b/ANGLE/include/GLSLANG/ResourceLimits.h
deleted file mode 100644
index 7b7a4b7..0000000
--- a/ANGLE/include/GLSLANG/ResourceLimits.h
+++ /dev/null
@@ -1,21 +0,0 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project 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 _RESOURCE_LIMITS_INCLUDED_
-#define _RESOURCE_LIMITS_INCLUDED_
-
-struct TBuiltInResource
-{
-	int maxVertexAttribs;
-	int maxVertexUniformVectors;
-	int maxVaryingVectors;
-	int maxVertexTextureImageUnits;
-	int maxCombinedTextureImageUnits;
-	int maxTextureImageUnits;
-	int maxFragmentUniformVectors;
-	int maxDrawBuffers;
-};
-#endif // _RESOURCE_LIMITS_INCLUDED_
diff --git a/ANGLE/include/GLSLANG/ShaderLang.h b/ANGLE/include/GLSLANG/ShaderLang.h
index 19e6df0..e0a5cc8 100644
--- a/ANGLE/include/GLSLANG/ShaderLang.h
+++ b/ANGLE/include/GLSLANG/ShaderLang.h
@@ -6,8 +6,6 @@
 #ifndef _COMPILER_INTERFACE_INCLUDED_
 #define _COMPILER_INTERFACE_INCLUDED_
 
-#include "ResourceLimits.h"
-
 //
 // This is the platform independent interface between an OGL driver
 // and the shading language compiler.
@@ -19,10 +17,12 @@ extern "C" {
 //
 // Driver must call this first, once, before doing any other
 // compiler operations.
+// If the function succeeds, the return value is nonzero, else zero.
 //
 int ShInitialize();
 //
 // Driver should call this at shutdown.
+// If the function succeeds, the return value is nonzero, else zero.
 //
 int ShFinalize();
 //
@@ -44,6 +44,32 @@ typedef enum {
 } EShSpec;
 
 //
+// Implementation dependent built-in resources (constants and extensions).
+// The names for these resources has been obtained by stripping gl_/GL_.
+//
+typedef struct
+{
+    // Constants.
+    int MaxVertexAttribs;
+    int MaxVertexUniformVectors;
+    int MaxVaryingVectors;
+    int MaxVertexTextureImageUnits;
+    int MaxCombinedTextureImageUnits;
+    int MaxTextureImageUnits;
+    int MaxFragmentUniformVectors;
+    int MaxDrawBuffers;
+
+    // Extensions.
+    // Set to 1 to enable the extension, else 0.
+    int OES_standard_derivatives;
+} TBuiltInResource;
+
+//
+// Initialize built-in resources with minimum expected values.
+//
+void ShInitBuiltInResource(TBuiltInResource* resources);
+
+//
 // Optimization level for the compiler.
 //
 typedef enum {
diff --git a/ANGLE/src/compiler/BaseTypes.h b/ANGLE/src/compiler/BaseTypes.h
index cb646fc..9f4a860 100644
--- a/ANGLE/src/compiler/BaseTypes.h
+++ b/ANGLE/src/compiler/BaseTypes.h
@@ -19,7 +19,7 @@ enum TPrecision
     EbpHigh,
 };
 
-__inline const char* getPrecisionString(TPrecision p)
+inline const char* getPrecisionString(TPrecision p)
 {
     switch(p)
     {
@@ -47,7 +47,22 @@ enum TBasicType
     EbtAddress,            // should be deprecated??
 };
 
-__inline bool IsSampler(TBasicType type)
+inline const char* getBasicString(TBasicType t)
+{
+    switch (t)
+    {
+    case EbtVoid:              return "void";              break;
+    case EbtFloat:             return "float";             break;
+    case EbtInt:               return "int";               break;
+    case EbtBool:              return "bool";              break;
+    case EbtSampler2D:         return "sampler2D";         break;
+    case EbtSamplerCube:       return "samplerCube";       break;
+    case EbtStruct:            return "structure";         break;
+    default:                   return "unknown type";
+    }
+}
+
+inline bool IsSampler(TBasicType type)
 {
     return type > EbtGuardSamplerBegin && type < EbtGuardSamplerEnd;
 }
@@ -100,7 +115,7 @@ enum TQualifier
 //
 // This is just for debug print out, carried along with the definitions above.
 //
-__inline const char* getQualifierString(TQualifier q)
+inline const char* getQualifierString(TQualifier q)
 {
     switch(q)
     {
diff --git a/ANGLE/src/compiler/Initialize.cpp b/ANGLE/src/compiler/Initialize.cpp
index 58c6162..6bfcf4f 100644
--- a/ANGLE/src/compiler/Initialize.cpp
+++ b/ANGLE/src/compiler/Initialize.cpp
@@ -472,15 +472,15 @@ static TString BuiltInConstants(const TBuiltInResource &resources)
 {
     TStringStream s;
 
-    s << "const int gl_MaxVertexAttribs = " << resources.maxVertexAttribs << ";";
-    s << "const int gl_MaxVertexUniformVectors = " << resources.maxVertexUniformVectors << ";";
+    s << "const int gl_MaxVertexAttribs = " << resources.MaxVertexAttribs << ";";
+    s << "const int gl_MaxVertexUniformVectors = " << resources.MaxVertexUniformVectors << ";";
 
-    s << "const int gl_MaxVaryingVectors = " << resources.maxVaryingVectors << ";";
-    s << "const int gl_MaxVertexTextureImageUnits = " << resources.maxVertexTextureImageUnits << ";";
-    s << "const int gl_MaxCombinedTextureImageUnits = " << resources.maxCombinedTextureImageUnits << ";";
-    s << "const int gl_MaxTextureImageUnits = " << resources.maxTextureImageUnits << ";";
-    s << "const int gl_MaxFragmentUniformVectors = " << resources.maxFragmentUniformVectors << ";";
-    s << "const int gl_MaxDrawBuffers = " << resources.maxDrawBuffers << ";";
+    s << "const int gl_MaxVaryingVectors = " << resources.MaxVaryingVectors << ";";
+    s << "const int gl_MaxVertexTextureImageUnits = " << resources.MaxVertexTextureImageUnits << ";";
+    s << "const int gl_MaxCombinedTextureImageUnits = " << resources.MaxCombinedTextureImageUnits << ";";
+    s << "const int gl_MaxTextureImageUnits = " << resources.MaxTextureImageUnits << ";";
+    s << "const int gl_MaxFragmentUniformVectors = " << resources.MaxFragmentUniformVectors << ";";
+    s << "const int gl_MaxDrawBuffers = " << resources.MaxDrawBuffers << ";";
 
     return s.str();
 }
@@ -591,23 +591,23 @@ void IdentifyBuiltIns(EShLanguage language, EShSpec spec, const TBuiltInResource
     symbolTable.relateToOperator("all",          EOpAll);
 
     // Map language-specific operators.
-    switch(language) {
-    case EShLangVertex:
-        break;
-    case EShLangFragment:
-        //symbolTable.relateToOperator("dFdx",   EOpDPdx);    // OES_standard_derivatives extension
-        //symbolTable.relateToOperator("dFdy",   EOpDPdy);    // OES_standard_derivatives extension
-        //symbolTable.relateToOperator("fwidth", EOpFwidth);  // OES_standard_derivatives extension
-        break;
-    default: break;
-    }
+    switch(language) {
+    case EShLangVertex:
+        break;
+    case EShLangFragment:
+        //symbolTable.relateToOperator("dFdx",   EOpDPdx);    // OES_standard_derivatives extension
+        //symbolTable.relateToOperator("dFdy",   EOpDPdy);    // OES_standard_derivatives extension
+        //symbolTable.relateToOperator("fwidth", EOpFwidth);  // OES_standard_derivatives extension
+        break;
+    default: break;
+    }
 
     // Finally add resource-specific variables.
     switch(language) {
     case EShLangFragment: {
             // Set up gl_FragData.  The array size.
             TType fragData(EbtFloat, EbpMedium, EvqFragColor,   4, false, true);
-            fragData.setArraySize(resources.maxDrawBuffers);
+            fragData.setArraySize(resources.MaxDrawBuffers);
             symbolTable.insert(*new TVariable(NewPoolTString("gl_FragData"),    fragData));
         }
         break;
diff --git a/ANGLE/src/compiler/Initialize.h b/ANGLE/src/compiler/Initialize.h
index 03c9937..c078659 100644
--- a/ANGLE/src/compiler/Initialize.h
+++ b/ANGLE/src/compiler/Initialize.h
@@ -7,8 +7,6 @@
 #ifndef _INITIALIZE_INCLUDED_
 #define _INITIALIZE_INCLUDED_
 
-#include "GLSLANG/ResourceLimits.h"
-
 #include "compiler/Common.h"
 #include "compiler/ShHandle.h"
 #include "compiler/SymbolTable.h"
diff --git a/ANGLE/src/compiler/InitializeDll.cpp b/ANGLE/src/compiler/InitializeDll.cpp
index 06f8384..8763cfe 100644
--- a/ANGLE/src/compiler/InitializeDll.cpp
+++ b/ANGLE/src/compiler/InitializeDll.cpp
@@ -6,72 +6,88 @@
 
 #include "compiler/InitializeDll.h"
 
-#include "GLSLANG/ShaderLang.h"
-
 #include "compiler/InitializeGlobals.h"
 #include "compiler/InitializeParseContext.h"
+#include "compiler/osinclude.h"
 
 OS_TLSIndex ThreadInitializeIndex = OS_INVALID_TLS_INDEX;
 
 bool InitProcess()
 {
     if (ThreadInitializeIndex != OS_INVALID_TLS_INDEX) {
-		//
-		// Function is re-entrant.
-		//
+        //
+        // Function is re-entrant.
+        //
         return true;
-	}
+    }
 
     ThreadInitializeIndex = OS_AllocTLSIndex();
 
     if (ThreadInitializeIndex == OS_INVALID_TLS_INDEX) {
         assert(0 && "InitProcess(): Failed to allocate TLS area for init flag");
         return false;
-	}
+    }
 
 
     if (!InitializePoolIndex()) {
         assert(0 && "InitProcess(): Failed to initalize global pool");
         return false;
-	}
+    }
 
     if (!InitializeParseContextIndex()) {
         assert(0 && "InitProcess(): Failed to initalize parse context");
         return false;
-	}
+    }
 
-	InitThread();
-    return true;
+    return InitThread();
 }
 
+bool DetachProcess()
+{
+    bool success = true;
+
+    if (ThreadInitializeIndex == OS_INVALID_TLS_INDEX)
+        return true;
+
+    success = DetachThread();
+
+    if (!FreeParseContextIndex())
+        success = false;
+
+    FreePoolIndex();
+
+    OS_FreeTLSIndex(ThreadInitializeIndex);
+    ThreadInitializeIndex = OS_INVALID_TLS_INDEX;
+
+    return success;
+}
 
 bool InitThread()
 {
-	//
+    //
     // This function is re-entrant
-	//
+    //
     if (ThreadInitializeIndex == OS_INVALID_TLS_INDEX) {
-		assert(0 && "InitThread(): Process hasn't been initalised.");
+        assert(0 && "InitThread(): Process hasn't been initalised.");
         return false;
-	}
+    }
 
     if (OS_GetTLSValue(ThreadInitializeIndex) != 0)
         return true;
 
-	InitializeGlobalPools();
+    InitializeGlobalPools();
 
-	if (!InitializeGlobalParseContext())
+    if (!InitializeGlobalParseContext())
         return false;
 
     if (!OS_SetTLSValue(ThreadInitializeIndex, (void *)1)) {
-		assert(0 && "InitThread(): Unable to set init flag.");
+        assert(0 && "InitThread(): Unable to set init flag.");
         return false;
-	}
+    }
 
     return true;
 }
 
-
 bool DetachThread()
 {
     bool success = true;
@@ -79,42 +95,21 @@ bool DetachThread()
     if (ThreadInitializeIndex == OS_INVALID_TLS_INDEX)
         return true;
 
-	//
-	// Function is re-entrant and this thread may not have been initalised.
-	//
+    //
+    // Function is re-entrant and this thread may not have been initalised.
+    //
     if (OS_GetTLSValue(ThreadInitializeIndex) != 0) {
         if (!OS_SetTLSValue(ThreadInitializeIndex, (void *)0)) {
-			assert(0 && "DetachThread(): Unable to clear init flag.");
+            assert(0 && "DetachThread(): Unable to clear init flag.");
             success = false;
-		}
+        }
 
-		FreeGlobalPools();
-
-		if (!FreeParseContext())
+        if (!FreeParseContext())
             success = false;
-	}
-
-    return success;
-}
-
-bool DetachProcess()
-{
-    bool success = true;
-
-    if (ThreadInitializeIndex == OS_INVALID_TLS_INDEX)
-        return true;
-
-    ShFinalize();
-
-    success = DetachThread();
-
-	FreePoolIndex();
 
-	if (!FreeParseContextIndex())
-        success = false;
-
-    OS_FreeTLSIndex(ThreadInitializeIndex);
-    ThreadInitializeIndex = OS_INVALID_TLS_INDEX;
+        FreeGlobalPools();
+    }
 
     return success;
 }
+
diff --git a/ANGLE/src/compiler/InitializeDll.h b/ANGLE/src/compiler/InitializeDll.h
index bb17540..857238e 100644
--- a/ANGLE/src/compiler/InitializeDll.h
+++ b/ANGLE/src/compiler/InitializeDll.h
@@ -6,14 +6,11 @@
 #ifndef __INITIALIZEDLL_H
 #define __INITIALIZEDLL_H
 
-
-#include "compiler/osinclude.h"
-
-
 bool InitProcess();
+bool DetachProcess();
+
 bool InitThread();
 bool DetachThread();
-bool DetachProcess();
 
 #endif // __INITIALIZEDLL_H
 
diff --git a/ANGLE/src/compiler/InitializeParseContext.h b/ANGLE/src/compiler/InitializeParseContext.h
index 68295d0..760fd09 100644
--- a/ANGLE/src/compiler/InitializeParseContext.h
+++ b/ANGLE/src/compiler/InitializeParseContext.h
@@ -6,12 +6,11 @@
 
 #ifndef __INITIALIZE_PARSE_CONTEXT_INCLUDED_
 #define __INITIALIZE_PARSE_CONTEXT_INCLUDED_
-#include "compiler/osinclude.h"
 
 bool InitializeParseContextIndex();
-bool InitializeGlobalParseContext();
-bool FreeParseContext();
 bool FreeParseContextIndex();
 
+bool InitializeGlobalParseContext();
+bool FreeParseContext();
 
 #endif // __INITIALIZE_PARSE_CONTEXT_INCLUDED_
diff --git a/ANGLE/src/compiler/Intermediate.cpp b/ANGLE/src/compiler/Intermediate.cpp
index f65bc80..5ebd919 100644
--- a/ANGLE/src/compiler/Intermediate.cpp
+++ b/ANGLE/src/compiler/Intermediate.cpp
@@ -10,6 +10,7 @@
 
 #include <float.h>
 #include <limits.h>
+#include <algorithm>
 
 #include "compiler/localintermediate.h"
 #include "compiler/QualifierAlive.h"
@@ -17,9 +18,10 @@
 
 bool CompareStructure(const TType& leftNodeType, ConstantUnion* rightUnionArray, ConstantUnion* leftUnionArray);
 
-TPrecision GetHighestPrecision( TPrecision left, TPrecision right ){
+static TPrecision GetHigherPrecision( TPrecision left, TPrecision right ){
     return left > right ? left : right;
 }
+
 ////////////////////////////////////////////////////////////////////////////
 //
 // First set of functions are to help build the intermediate representation.
@@ -111,12 +113,6 @@ TIntermTyped* TIntermediate::addBinaryMath(TOperator op, TIntermTyped* left, TIn
     TIntermConstantUnion *leftTempConstant = left->getAsConstantUnion();
     TIntermConstantUnion *rightTempConstant = right->getAsConstantUnion();
 
-    if (leftTempConstant)
-        leftTempConstant = left->getAsConstantUnion();
-
-    if (rightTempConstant)
-        rightTempConstant = right->getAsConstantUnion();
-
     //
     // See if we can fold constants.
     //
@@ -307,7 +303,7 @@ TIntermAggregate* TIntermediate::setAggregateOperator(TIntermNode* node, TOperat
     //
     // Set the operator.
     //
-    aggNode->setOperator(op);
+    aggNode->setOp(op);
     if (line != 0)
         aggNode->setLine(line);
 
@@ -519,9 +515,9 @@ TIntermTyped* TIntermediate::addComma(TIntermTyped* left, TIntermTyped* right, T
         return right;
     } else {
         TIntermTyped *commaAggregate = growAggregate(left, right, line);
-        commaAggregate->getAsAggregate()->setOperator(EOpComma);
+        commaAggregate->getAsAggregate()->setOp(EOpComma);
         commaAggregate->setType(right->getType());
-        commaAggregate->getTypePointer()->changeQualifier(EvqTemporary);
+        commaAggregate->getTypePointer()->setQualifier(EvqTemporary);
         return commaAggregate;
     }
 }
@@ -644,7 +640,7 @@ bool TIntermediate::postProcess(TIntermNode* root, EShLanguage language)
     //
     TIntermAggregate* aggRoot = root->getAsAggregate();
     if (aggRoot && aggRoot->getOp() == EOpNull)
-        aggRoot->setOperator(EOpSequence);
+        aggRoot->setOp(EOpSequence);
 
     return true;
 }
@@ -764,16 +760,9 @@ bool TIntermUnary::promote(TInfoSink&)
 //
 bool TIntermBinary::promote(TInfoSink& infoSink)
 {
-    int size = left->getNominalSize();
-    if (right->getNominalSize() > size)
-        size = right->getNominalSize();
-
-    TBasicType type = left->getBasicType();
-
-    //
-    // Arrays have to be exact matches.
-    //
-    if ((left->isArray() || right->isArray()) && (left->getType() != right->getType()))
+    // GLSL ES 2.0 does not support implicit type casting.
+    // So the basic type should always match.
+    if (left->getBasicType() != right->getBasicType())
         return false;
 
     //
@@ -782,16 +771,27 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
     //
     setType(left->getType());
 
-    TPrecision highestPrecision = GetHighestPrecision(left->getPrecision(), right->getPrecision());
-    getTypePointer()->changePrecision(highestPrecision);
+    // The result gets promoted to the highest precision.
+    TPrecision higherPrecision = GetHigherPrecision(left->getPrecision(), right->getPrecision());
+    getTypePointer()->setPrecision(higherPrecision);
+
+    // Binary operations results in temporary variables unless both
+    // operands are const.
+    if (left->getQualifier() != EvqConst || right->getQualifier() != EvqConst) {
+        getTypePointer()->setQualifier(EvqTemporary);
+    }
 
     //
     // Array operations.
     //
-    if (left->isArray()) {
+    if (left->isArray() || right->isArray()) {
+        //
+        // Arrays types have to be exact matches.
+        //
+        if (left->getType() != right->getType())
+            return false;
 
         switch (op) {
-
             //
             // Promote to conditional
             //
@@ -812,17 +812,16 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
             default:
                 return false;
         }
-
         return true;
     }
 
+    int size = std::max(left->getNominalSize(), right->getNominalSize());
+
     //
-    // All scalars.  Code after this test assumes this case is removed!
+    // All scalars. Code after this test assumes this case is removed!
     //
     if (size == 1) {
-
         switch (op) {
-
             //
             // Promote to conditional
             //
@@ -840,33 +839,36 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
             //
             case EOpLogicalAnd:
             case EOpLogicalOr:
+                // Both operands must be of type bool.
                 if (left->getBasicType() != EbtBool || right->getBasicType() != EbtBool)
                     return false;
                 setType(TType(EbtBool, EbpUndefined));
                 break;
 
-            //
-            // Everything else should have matching types
-            //
             default:
-                if (left->getBasicType() != right->getBasicType() ||
-                    left->isMatrix()     != right->isMatrix())
-                    return false;
+                break;
         }
-
         return true;
     }
 
-    //
+    // If we reach here, at least one of the operands is vector or matrix.
+    // The other operand could be a scalar, vector, or matrix.
     // Are the sizes compatible?
     //
-    if ( left->getNominalSize() != size &&  left->getNominalSize() != 1 ||
-        right->getNominalSize() != size && right->getNominalSize() != 1)
-        return false;
+    if (left->getNominalSize() != right->getNominalSize()) {
+        // If the nominal size of operands do not match:
+        // One of them must be scalar.
+        if (left->getNominalSize() != 1 && right->getNominalSize() != 1)
+            return false;
+        // Operator cannot be of type pure assignment.
+        if (op == EOpAssign || op == EOpInitialize)
+            return false;
+    }
 
     //
     // Can these two operands be combined?
     //
+    TBasicType basicType = left->getBasicType();
     switch (op) {
         case EOpMul:
             if (!left->isMatrix() && right->isMatrix()) {
@@ -874,12 +876,12 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
                     op = EOpVectorTimesMatrix;
                 else {
                     op = EOpMatrixTimesScalar;
-                    setType(TType(type, highestPrecision, EvqTemporary, size, true));
+                    setType(TType(basicType, higherPrecision, EvqTemporary, size, true));
                 }
             } else if (left->isMatrix() && !right->isMatrix()) {
                 if (right->isVector()) {
                     op = EOpMatrixTimesVector;
-                    setType(TType(type, highestPrecision, EvqTemporary, size, false));
+                    setType(TType(basicType, higherPrecision, EvqTemporary, size, false));
                 } else {
                     op = EOpMatrixTimesScalar;
                 }
@@ -890,7 +892,7 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
                     // leave as component product
                 } else if (left->isVector() || right->isVector()) {
                     op = EOpVectorTimesScalar;
-                    setType(TType(type, highestPrecision, EvqTemporary, size, false));
+                    setType(TType(basicType, higherPrecision, EvqTemporary, size, false));
                 }
             } else {
                 infoSink.info.message(EPrefixInternalError, "Missing elses", getLine());
@@ -919,18 +921,16 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
                     if (! left->isVector())
                         return false;
                     op = EOpVectorTimesScalarAssign;
-                    setType(TType(type, highestPrecision, EvqTemporary, size, false));
+                    setType(TType(basicType, higherPrecision, EvqTemporary, size, false));
                 }
             } else {
                 infoSink.info.message(EPrefixInternalError, "Missing elses", getLine());
                 return false;
             }
             break;
+
         case EOpAssign:
         case EOpInitialize:
-            if (left->getNominalSize() != right->getNominalSize())
-                return false;
-            // fall through
         case EOpAdd:
         case EOpSub:
         case EOpDiv:
@@ -938,10 +938,9 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
         case EOpSubAssign:
         case EOpDivAssign:
             if (left->isMatrix() && right->isVector() ||
-                left->isVector() && right->isMatrix() ||
-                left->getBasicType() != right->getBasicType())
+                left->isVector() && right->isMatrix())
                 return false;
-            setType(TType(type, highestPrecision, EvqTemporary, size, left->isMatrix() || right->isMatrix()));
+            setType(TType(basicType, higherPrecision, EvqTemporary, size, left->isMatrix() || right->isMatrix()));
             break;
 
         case EOpEqual:
@@ -951,8 +950,7 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
         case EOpLessThanEqual:
         case EOpGreaterThanEqual:
             if (left->isMatrix() && right->isVector() ||
-                left->isVector() && right->isMatrix() ||
-                left->getBasicType() != right->getBasicType())
+                left->isVector() && right->isMatrix())
                 return false;
             setType(TType(EbtBool, EbpUndefined));
             break;
@@ -960,30 +958,13 @@ bool TIntermBinary::promote(TInfoSink& infoSink)
         default:
             return false;
     }
-
-    //
-    // One more check for assignment.  The Resulting type has to match the left operand.
-    //
-    switch (op) {
-        case EOpAssign:
-        case EOpInitialize:
-        case EOpAddAssign:
-        case EOpSubAssign:
-        case EOpMulAssign:
-        case EOpDivAssign:
-            if (getType() != left->getType())
-                return false;
-            break;
-        default:
-            break;
-    }
-
+    
     return true;
 }
 
 bool CompareStruct(const TType& leftNodeType, ConstantUnion* rightUnionArray, ConstantUnion* leftUnionArray)
 {
-    TTypeList* fields = leftNodeType.getStruct();
+    const TTypeList* fields = leftNodeType.getStruct();
 
     size_t structSize = fields->size();
     int index = 0;
diff --git a/ANGLE/src/compiler/OutputGLSL.cpp b/ANGLE/src/compiler/OutputGLSL.cpp
index 486a27a..fd263b6 100644
--- a/ANGLE/src/compiler/OutputGLSL.cpp
+++ b/ANGLE/src/compiler/OutputGLSL.cpp
@@ -147,7 +147,7 @@ void TOutputGLSL::writeFunctionParameters(const TIntermSequence& args)
             out << arrayBrackets(type);
 
         // Put a comma if this is not the last argument.
-        if (iter != --args.end())
+        if (iter != args.end() - 1)
             out << ", ";
     }
 }
@@ -304,8 +304,6 @@ bool TOutputGLSL::visitBinary(Visit visit, TIntermBinary* node)
 
 bool TOutputGLSL::visitUnary(Visit visit, TIntermUnary* node)
 {
-    TInfoSinkBase& out = objSink();
-
     switch (node->getOp())
     {
         case EOpNegative: writeTriplet(visit, "(-", NULL, ")"); break;
@@ -650,8 +648,6 @@ bool TOutputGLSL::visitLoop(Visit visit, TIntermLoop* node)
 
 bool TOutputGLSL::visitBranch(Visit visit, TIntermBranch* node)
 {
-    TInfoSinkBase &out = objSink();
-
     switch (node->getFlowOp())
     {
         case EOpKill: writeTriplet(visit, "discard", NULL, NULL); break;
diff --git a/ANGLE/src/compiler/OutputHLSL.cpp b/ANGLE/src/compiler/OutputHLSL.cpp
index 36f527c..8b8a4e6 100644
--- a/ANGLE/src/compiler/OutputHLSL.cpp
+++ b/ANGLE/src/compiler/OutputHLSL.cpp
@@ -181,7 +181,7 @@ void OutputHLSL::header()
 
         if (mUsesFragCoord)
         {
-            out << "uniform float4 dx_Window;\n"
+            out << "uniform float4 dx_Viewport;\n"
                    "uniform float2 dx_Depth;\n";
         }
 
@@ -791,11 +791,11 @@ bool OutputHLSL::visitBinary(Visit visit, TIntermBinary *node)
         {
             if (node->getLeft()->isMatrix())
             {
-                switch (node->getLeft()->getSize())
+                switch (node->getLeft()->getNominalSize())
                 {
-                  case 2 * 2: mUsesEqualMat2 = true; break;
-                  case 3 * 3: mUsesEqualMat3 = true; break;
-                  case 4 * 4: mUsesEqualMat4 = true; break;
+                  case 2: mUsesEqualMat2 = true; break;
+                  case 3: mUsesEqualMat3 = true; break;
+                  case 4: mUsesEqualMat4 = true; break;
                   default: UNREACHABLE();
                 }
             }
@@ -804,7 +804,7 @@ bool OutputHLSL::visitBinary(Visit visit, TIntermBinary *node)
                 switch (node->getLeft()->getBasicType())
                 {
                   case EbtFloat:
-                    switch (node->getLeft()->getSize())
+                    switch (node->getLeft()->getNominalSize())
                     {
                       case 2: mUsesEqualVec2 = true; break;
                       case 3: mUsesEqualVec3 = true; break;
@@ -813,7 +813,7 @@ bool OutputHLSL::visitBinary(Visit visit, TIntermBinary *node)
                     }
                     break;
                   case EbtInt:
-                    switch (node->getLeft()->getSize())
+                    switch (node->getLeft()->getNominalSize())
                     {
                       case 2: mUsesEqualIVec2 = true; break;
                       case 3: mUsesEqualIVec3 = true; break;
@@ -822,7 +822,7 @@ bool OutputHLSL::visitBinary(Visit visit, TIntermBinary *node)
                     }
                     break;
                   case EbtBool:
-                    switch (node->getLeft()->getSize())
+                    switch (node->getLeft()->getNominalSize())
                     {
                       case 2: mUsesEqualBVec2 = true; break;
                       case 3: mUsesEqualBVec3 = true; break;
@@ -1288,7 +1288,7 @@ bool OutputHLSL::visitAggregate(Visit visit, TIntermAggregate *node)
       case EOpVectorNotEqual:   outputTriplet(visit, "(", " != ", ")");                break;
       case EOpMod:
         {
-            switch (node->getSequence()[0]->getAsTyped()->getSize())   // Number of components in the first argument
+            switch (node->getSequence()[0]->getAsTyped()->getNominalSize())   // Number of components in the first argument
             {
               case 1: mUsesMod1 = true; break;
               case 2: mUsesMod2 = true; break;
@@ -1317,7 +1317,7 @@ bool OutputHLSL::visitAggregate(Visit visit, TIntermAggregate *node)
       case EOpCross:         outputTriplet(visit, "cross(", ", ", ")");         break;
       case EOpFaceForward:
         {
-            switch (node->getSequence()[0]->getAsTyped()->getSize())   // Number of components in the first argument
+            switch (node->getSequence()[0]->getAsTyped()->getNominalSize())   // Number of components in the first argument
             {
             case 1: mUsesFaceforward1 = true; break;
             case 2: mUsesFaceforward2 = true; break;
@@ -1553,7 +1553,7 @@ bool OutputHLSL::handleExcessiveLoop(TIntermLoop *node)
 
                     if (symbol && constant)
                     {
-                        if (constant->getBasicType() == EbtInt && constant->getSize() == 1)
+                        if (constant->getBasicType() == EbtInt && constant->getNominalSize() == 1)
                         {
                             index = symbol;
                             initial = constant->getUnionArrayPointer()[0].getIConst();
@@ -1575,7 +1575,7 @@ bool OutputHLSL::handleExcessiveLoop(TIntermLoop *node)
 
             if (constant)
             {
-                if (constant->getBasicType() == EbtInt && constant->getSize() == 1)
+                if (constant->getBasicType() == EbtInt && constant->getNominalSize() == 1)
                 {
                     comparator = test->getOp();
                     limit = constant->getUnionArrayPointer()[0].getIConst();
@@ -1597,7 +1597,7 @@ bool OutputHLSL::handleExcessiveLoop(TIntermLoop *node)
 
             if (constant)
             {
-                if (constant->getBasicType() == EbtInt && constant->getSize() == 1)
+                if (constant->getBasicType() == EbtInt && constant->getNominalSize() == 1)
                 {
                     int value = constant->getUnionArrayPointer()[0].getIConst();
 
@@ -1848,8 +1848,8 @@ void OutputHLSL::addConstructor(const TType &type, const TString &name, const TI
 
     TType ctorType = type;
     ctorType.clearArrayness();
-    ctorType.changePrecision(EbpHigh);
-    ctorType.changeQualifier(EvqTemporary);
+    ctorType.setPrecision(EbpHigh);
+    ctorType.setQualifier(EvqTemporary);
 
     TString ctorName = type.getStruct() ? decorate(name) : name;
 
diff --git a/ANGLE/src/compiler/ParseHelper.cpp b/ANGLE/src/compiler/ParseHelper.cpp
index f1ab572..407226b 100644
--- a/ANGLE/src/compiler/ParseHelper.cpp
+++ b/ANGLE/src/compiler/ParseHelper.cpp
@@ -486,7 +486,7 @@ bool TParseContext::constructorErrorCheck(int line, TIntermNode* node, TFunction
     }
     
     if (constType)
-        type->changeQualifier(EvqConst);
+        type->setQualifier(EvqConst);
 
     if (type->isArray() && type->getArraySize() != function.getParamCount()) {
         error(line, "array constructor needs one argument per array element", "constructor", "");
@@ -586,14 +586,14 @@ bool TParseContext::samplerErrorCheck(int line, const TPublicType& pType, const
 {
     if (pType.type == EbtStruct) {
         if (containsSampler(*pType.userDef)) {
-            error(line, reason, TType::getBasicString(pType.type), "(structure contains a sampler)");
+            error(line, reason, getBasicString(pType.type), "(structure contains a sampler)");
         
             return true;
         }
         
         return false;
     } else if (IsSampler(pType.type)) {
-        error(line, reason, TType::getBasicString(pType.type), "");
+        error(line, reason, getBasicString(pType.type), "");
 
         return true;
     }
@@ -879,9 +879,9 @@ bool TParseContext::paramErrorCheck(int line, TQualifier qualifier, TQualifier p
     }
 
     if (qualifier == EvqConst)
-        type->changeQualifier(EvqConstReadOnly);
+        type->setQualifier(EvqConstReadOnly);
     else
-        type->changeQualifier(paramQualifier);
+        type->setQualifier(paramQualifier);
 
     return false;
 }
@@ -913,21 +913,24 @@ bool TParseContext::extensionErrorCheck(int line, const char* extension)
 //
 const TFunction* TParseContext::findFunction(int line, TFunction* call, bool *builtIn)
 {
-    const TSymbol* symbol = symbolTable.find(call->getMangledName(), builtIn);
+    // First find by unmangled name to check whether the function name has been
+    // hidden by a variable name or struct typename.
+    const TSymbol* symbol = symbolTable.find(call->getName(), builtIn);
+    if (symbol == 0) {
+        symbol = symbolTable.find(call->getMangledName(), builtIn);
+    }
 
-    if (symbol == 0) {        
+    if (symbol == 0) {
         error(line, "no matching overloaded function found", call->getName().c_str(), "");
         return 0;
     }
 
-    if (! symbol->isFunction()) {
+    if (!symbol->isFunction()) {
         error(line, "function name expected", call->getName().c_str(), "");
         return 0;
     }
-    
-    const TFunction* function = static_cast<const TFunction*>(symbol);
-    
-    return function;
+
+    return static_cast<const TFunction*>(symbol);
 }
 
 //
@@ -973,13 +976,13 @@ bool TParseContext::executeInitializer(TSourceLoc line, TString& identifier, TPu
     if (qualifier == EvqConst) {
         if (qualifier != initializer->getType().getQualifier()) {
             error(line, " assigning non-constant to", "=", "'%s'", variable->getType().getCompleteString().c_str());
-            variable->getType().changeQualifier(EvqTemporary);
+            variable->getType().setQualifier(EvqTemporary);
             return true;
         }
         if (type != initializer->getType()) {
             error(line, " non-matching types for const initializer ", 
                 variable->getType().getQualifierString(), "");
-            variable->getType().changeQualifier(EvqTemporary);
+            variable->getType().setQualifier(EvqTemporary);
             return true;
         }
         if (initializer->getAsConstantUnion()) { 
@@ -998,7 +1001,7 @@ bool TParseContext::executeInitializer(TSourceLoc line, TString& identifier, TPu
             variable->shareConstPointer(constArray);
         } else {
             error(line, " cannot assign to", "=", "'%s'", variable->getType().getCompleteString().c_str());
-            variable->getType().changeQualifier(EvqTemporary);
+            variable->getType().setQualifier(EvqTemporary);
             return true;
         }
     }
@@ -1049,7 +1052,7 @@ TIntermTyped* TParseContext::addConstructor(TIntermNode* node, const TType* type
 
     TIntermAggregate* aggrNode = node->getAsAggregate();
     
-    TTypeList::iterator memberTypes;
+    TTypeList::const_iterator memberTypes;
     if (op == EOpConstructStruct)
         memberTypes = type->getStruct()->begin();
     
@@ -1347,7 +1350,7 @@ TIntermTyped* TParseContext::addConstArrayNode(int index, TIntermTyped* node, TS
 //
 TIntermTyped* TParseContext::addConstStruct(TString& identifier, TIntermTyped* node, TSourceLoc line)
 {
-    TTypeList* fields = node->getType().getStruct();
+    const TTypeList* fields = node->getType().getStruct();
     TIntermTyped *typedNode;
     int instanceSize = 0;
     unsigned int index = 0;
@@ -1410,6 +1413,20 @@ bool InitializeParseContextIndex()
     return true;
 }
 
+bool FreeParseContextIndex()
+{
+    OS_TLSIndex tlsiIndex = GlobalParseContextIndex;
+
+    if (GlobalParseContextIndex == OS_INVALID_TLS_INDEX) {
+        assert(0 && "FreeParseContextIndex(): Parse Context index not initalised");
+        return false;
+    }
+
+    GlobalParseContextIndex = OS_INVALID_TLS_INDEX;
+
+    return OS_FreeTLSIndex(tlsiIndex);
+}
+
 bool InitializeGlobalParseContext()
 {
     if (GlobalParseContextIndex == OS_INVALID_TLS_INDEX) {
@@ -1435,17 +1452,6 @@ bool InitializeGlobalParseContext()
     return true;
 }
 
-TParseContextPointer& GetGlobalParseContext()
-{
-    //
-    // Minimal error checking for speed
-    //
-
-    TThreadParseContext *lpParseContext = static_cast<TThreadParseContext *>(OS_GetTLSValue(GlobalParseContextIndex));
-
-    return lpParseContext->lpGlobalParseContext;
-}
-
 bool FreeParseContext()
 {
     if (GlobalParseContextIndex == OS_INVALID_TLS_INDEX) {
@@ -1460,16 +1466,14 @@ bool FreeParseContext()
     return true;
 }
 
-bool FreeParseContextIndex()
+TParseContextPointer& GetGlobalParseContext()
 {
-    OS_TLSIndex tlsiIndex = GlobalParseContextIndex;
-
-    if (GlobalParseContextIndex == OS_INVALID_TLS_INDEX) {
-        assert(0 && "FreeParseContextIndex(): Parse Context index not initalised");
-        return false;
-    }
+    //
+    // Minimal error checking for speed
+    //
 
-    GlobalParseContextIndex = OS_INVALID_TLS_INDEX;
+    TThreadParseContext *lpParseContext = static_cast<TThreadParseContext *>(OS_GetTLSValue(GlobalParseContextIndex));
 
-    return OS_FreeTLSIndex(tlsiIndex);
+    return lpParseContext->lpGlobalParseContext;
 }
+
diff --git a/ANGLE/src/compiler/PoolAlloc.h b/ANGLE/src/compiler/PoolAlloc.h
index 0fa3194..645db78 100644
--- a/ANGLE/src/compiler/PoolAlloc.h
+++ b/ANGLE/src/compiler/PoolAlloc.h
@@ -157,11 +157,12 @@ protected:
     
     struct tHeader {
         tHeader(tHeader* nextPage, size_t pageCount) :
+            nextPage(nextPage),
+            pageCount(pageCount)
 #ifdef GUARD_BLOCKS
-            lastAllocation(0),
+          , lastAllocation(0)
 #endif
-            nextPage(nextPage),
-            pageCount(pageCount) { }
+            { }
 
         ~tHeader() {
 #ifdef GUARD_BLOCKS
@@ -263,19 +264,26 @@ public:
     template<class Other>
     pool_allocator(const pool_allocator<Other>& p) : allocator(p.getAllocator()) { }
 
+#if defined(__SUNPRO_CC) && !defined(_RWSTD_ALLOCATOR)
+    // libCStd on some platforms have a different allocate/deallocate interface.
+    // Caller pre-bakes sizeof(T) into 'n' which is the number of bytes to be
+    // allocated, not the number of elements.
+    void* allocate(size_type n) { 
+        return getAllocator().allocate(n);
+    }
+    void* allocate(size_type n, const void*) {
+        return getAllocator().allocate(n);
+    }
+    void deallocate(void*, size_type) {}
+#else
     pointer allocate(size_type n) { 
         return reinterpret_cast<pointer>(getAllocator().allocate(n * sizeof(T)));
     }
     pointer allocate(size_type n, const void*) { 
         return reinterpret_cast<pointer>(getAllocator().allocate(n * sizeof(T)));
     }
-
-    void deallocate(void*, size_type) { }
-    void deallocate(pointer, size_type) { }
-
-    pointer _Charalloc(size_t n) {
-        return reinterpret_cast<pointer>(getAllocator().allocate(n));
-    }
+    void deallocate(pointer, size_type) {}
+#endif  // _RWSTD_ALLOCATOR
 
     void construct(pointer p, const T& val) { new ((void *)p) T(val); }
     void destroy(pointer p) { p->T::~T(); }
diff --git a/ANGLE/src/compiler/ShaderLang.cpp b/ANGLE/src/compiler/ShaderLang.cpp
index 3c36ef8..e0c646a 100644
--- a/ANGLE/src/compiler/ShaderLang.cpp
+++ b/ANGLE/src/compiler/ShaderLang.cpp
@@ -90,15 +90,45 @@ static bool GenerateBuiltInSymbolTable(
 //
 int ShInitialize()
 {
-    bool ret = InitProcess();
+    if (!InitProcess())
+        return 0;
 
-    return ret ? 1 : 0;
+    return 1;
 }
 
 //
-// Driver calls these to create and destroy compiler objects.
+// Cleanup symbol tables
+//
+int ShFinalize()
+{
+    if (!DetachProcess())
+        return 0;
+
+    return 1;
+}
+
+//
+// Initialize built-in resources with minimum expected values.
 //
+void ShInitBuiltInResource(TBuiltInResource* resources)
+{
+    // Constants.
+    resources->MaxVertexAttribs = 8;
+    resources->MaxVertexUniformVectors = 128;
+    resources->MaxVaryingVectors = 8;
+    resources->MaxVertexTextureImageUnits = 0;
+    resources->MaxCombinedTextureImageUnits = 8;
+    resources->MaxTextureImageUnits = 8;
+    resources->MaxFragmentUniformVectors = 16;
+    resources->MaxDrawBuffers = 1;
+
+    // Extensions.
+    resources->OES_standard_derivatives = 0;
+}
 
+//
+// Driver calls these to create and destroy compiler objects.
+//
 ShHandle ShConstructCompiler(EShLanguage language, EShSpec spec, const TBuiltInResource* resources)
 {
     if (!InitThread())
@@ -130,14 +160,6 @@ void ShDestruct(ShHandle handle)
 }
 
 //
-// Cleanup symbol tables
-//
-int ShFinalize()
-{
-    return 1;
-}
-
-//
 // Do an actual compile on the given strings.  The result is left 
 // in the given compile object.
 //
diff --git a/ANGLE/src/compiler/SymbolTable.cpp b/ANGLE/src/compiler/SymbolTable.cpp
index d97f0ec..1b08667 100644
--- a/ANGLE/src/compiler/SymbolTable.cpp
+++ b/ANGLE/src/compiler/SymbolTable.cpp
@@ -65,7 +65,7 @@ int TType::getStructSize() const
     }
 
     if (structureSize == 0)
-        for (TTypeList::iterator tl = getStruct()->begin(); tl != getStruct()->end(); tl++)
+        for (TTypeList::const_iterator tl = getStruct()->begin(); tl != getStruct()->end(); tl++)
             structureSize += ((*tl).type)->getObjectSize();
 
     return structureSize;
diff --git a/ANGLE/src/compiler/SymbolTable.h b/ANGLE/src/compiler/SymbolTable.h
index 07c81d1..b1a80b5 100644
--- a/ANGLE/src/compiler/SymbolTable.h
+++ b/ANGLE/src/compiler/SymbolTable.h
@@ -76,7 +76,7 @@ public:
     TType& getType() { return type; }    
     const TType& getType() const { return type; }
     bool isUserType() const { return userType; }
-    void changeQualifier(TQualifier qualifier) { type.changeQualifier(qualifier); }
+    void setQualifier(TQualifier qualifier) { type.setQualifier(qualifier); }
     void updateArrayInformationType(TType *t) { arrayInformationType = t; }
     TType* getArrayInformationType() { return arrayInformationType; }
 
diff --git a/ANGLE/src/compiler/Types.h b/ANGLE/src/compiler/Types.h
index 44511b4..897b28f 100644
--- a/ANGLE/src/compiler/Types.h
+++ b/ANGLE/src/compiler/Types.h
@@ -82,28 +82,27 @@ typedef TMap<TTypeList*, TTypeList*>::iterator TStructureMapIterator;
 class TType {
 public:
     POOL_ALLOCATOR_NEW_DELETE(GlobalPoolAllocator)
-    explicit TType(TBasicType t, TPrecision p, TQualifier q = EvqTemporary, int s = 1, bool m = false, bool a = false) :
-                            type(t), precision(p), qualifier(q), size(s), matrix(m), array(a), arraySize(0),
-                            structure(0), structureSize(0), maxArraySize(0), arrayInformationType(0), fieldName(0), mangled(0), typeName(0)
-                            { }
+    TType() {}
+    TType(TBasicType t, TPrecision p, TQualifier q = EvqTemporary, int s = 1, bool m = false, bool a = false) :
+            type(t), precision(p), qualifier(q), size(s), matrix(m), array(a), arraySize(0),
+            structure(0), structureSize(0), maxArraySize(0), arrayInformationType(0), fieldName(0), mangled(0), typeName(0)
+    {
+    }
     explicit TType(const TPublicType &p) :
-                            type(p.type), precision(p.precision), qualifier(p.qualifier), size(p.size), matrix(p.matrix), array(p.array), arraySize(p.arraySize),
-                            structure(0), structureSize(0), maxArraySize(0), arrayInformationType(0), fieldName(0), mangled(0), typeName(0)
-                            {
-                              if (p.userDef) {
-                                  structure = p.userDef->getStruct();
-                                  typeName = NewPoolTString(p.userDef->getTypeName().c_str());
-                              }
-                            }
-    explicit TType(TTypeList* userDef, const TString& n, TPrecision p = EbpUndefined) :
-                            type(EbtStruct), precision(p), qualifier(EvqTemporary), size(1), matrix(false), array(false), arraySize(0),
-                            structure(userDef), structureSize(0), maxArraySize(0), arrayInformationType(0), fieldName(0), mangled(0) {
-                                typeName = NewPoolTString(n.c_str());
-                            }
-    explicit TType() {}
-    virtual ~TType() {}
-
-    TType(const TType& type) { *this = type; }
+            type(p.type), precision(p.precision), qualifier(p.qualifier), size(p.size), matrix(p.matrix), array(p.array), arraySize(p.arraySize),
+            structure(0), structureSize(0), maxArraySize(0), arrayInformationType(0), fieldName(0), mangled(0), typeName(0)
+    {
+        if (p.userDef) {
+            structure = p.userDef->getStruct();
+            typeName = NewPoolTString(p.userDef->getTypeName().c_str());
+        }
+    }
+    TType(TTypeList* userDef, const TString& n, TPrecision p = EbpUndefined) :
+            type(EbtStruct), precision(p), qualifier(EvqTemporary), size(1), matrix(false), array(false), arraySize(0),
+            structure(userDef), structureSize(0), maxArraySize(0), arrayInformationType(0), fieldName(0), mangled(0)
+    {
+        typeName = NewPoolTString(n.c_str());
+    }
 
     void copyType(const TType& copyOf, TStructureMap& remapper)
     {
@@ -157,77 +156,19 @@ public:
         return newType;
     }
 
-    virtual void setType(TBasicType t, int s, bool m, bool a, int aS = 0)
-                            { type = t; size = s; matrix = m; array = a; arraySize = aS; }
-    virtual void setType(TBasicType t, int s, bool m, TType* userDef = 0)
-                            { type = t;
-                              size = s;
-                              matrix = m;
-                              if (userDef)
-                                  structure = userDef->getStruct();
-                              // leave array information intact.
-                            }
-    virtual void setTypeName(const TString& n) { typeName = NewPoolTString(n.c_str()); }
-    virtual void setFieldName(const TString& n) { fieldName = NewPoolTString(n.c_str()); }
-    virtual const TString& getTypeName() const
-    {
-        assert(typeName);
-        return *typeName;
-    }
+    TBasicType getBasicType() const { return type; }
+    void setBasicType(TBasicType t) { type = t; }
 
-    virtual const TString& getFieldName() const
-    {
-        assert(fieldName);
-        return *fieldName;
-    }
+    TPrecision getPrecision() const { return precision; }
+    void setPrecision(TPrecision p) { precision = p; }
 
-    virtual TBasicType getBasicType() const { return type; }
-    virtual TPrecision getPrecision() const { return precision; }
-    virtual TQualifier getQualifier() const { return qualifier; }
-    virtual void changePrecision(TPrecision p) { precision = p; }
-    virtual void changeQualifier(TQualifier q) { qualifier = q; }
+    TQualifier getQualifier() const { return qualifier; }
+    void setQualifier(TQualifier q) { qualifier = q; }
 
     // One-dimensional size of single instance type
-    virtual int getNominalSize() const { return size; }
-
-    // Full-dimensional size of single instance of type
-    virtual int getInstanceSize() const
-    {
-        if (matrix)
-            return size * size;
-        else
-            return size;
-    }
-
-    virtual bool isMatrix() const { return matrix ? true : false; }
-    virtual bool isArray() const  { return array ? true : false; }
-    bool isField() const { return fieldName != 0; }
-    int getArraySize() const { return arraySize; }
-    void setArraySize(int s) { array = true; arraySize = s; }
-    void setMaxArraySize (int s) { maxArraySize = s; }
-    int getMaxArraySize () const { return maxArraySize; }
-    void clearArrayness() { array = false; arraySize = 0; maxArraySize = 0; }
-    void setArrayInformationType(TType* t) { arrayInformationType = t; }
-    TType* getArrayInformationType() const { return arrayInformationType; }
-    virtual bool isVector() const { return size > 1 && !matrix; }
-    virtual bool isScalar() const { return size == 1 && !matrix && !structure; }
-    static const char* getBasicString(TBasicType t) {
-        switch (t) {
-        case EbtVoid:              return "void";              break;
-        case EbtFloat:             return "float";             break;
-        case EbtInt:               return "int";               break;
-        case EbtBool:              return "bool";              break;
-        case EbtSampler2D:         return "sampler2D";         break;
-        case EbtSamplerCube:       return "samplerCube";       break;
-        case EbtStruct:            return "structure";         break;
-        default:                   return "unknown type";
-        }
-    }
-    const char* getBasicString() const { return TType::getBasicString(type); }
-    const char* getPrecisionString() const { return ::getPrecisionString(precision); }
-    const char* getQualifierString() const { return ::getQualifierString(qualifier); }
-    TTypeList* getStruct() { return structure; }
-
+    int getNominalSize() const { return size; }
+    void setNominalSize(int s) { size = s; }
+    // Full size of single instance of type
     int getObjectSize() const
     {
         int totalSize;
@@ -245,7 +186,45 @@ public:
         return totalSize;
     }
 
+    bool isMatrix() const { return matrix ? true : false; }
+    void setMatrix(bool m) { matrix = m; }
+
+    bool isArray() const  { return array ? true : false; }
+    int getArraySize() const { return arraySize; }
+    void setArraySize(int s) { array = true; arraySize = s; }
+    int getMaxArraySize () const { return maxArraySize; }
+    void setMaxArraySize (int s) { maxArraySize = s; }
+    void clearArrayness() { array = false; arraySize = 0; maxArraySize = 0; }
+    void setArrayInformationType(TType* t) { arrayInformationType = t; }
+    TType* getArrayInformationType() const { return arrayInformationType; }
+
+    bool isVector() const { return size > 1 && !matrix; }
+    bool isScalar() const { return size == 1 && !matrix && !structure; }
+
     TTypeList* getStruct() const { return structure; }
+    void setStruct(TTypeList* s) { structure = s; }
+
+    const TString& getTypeName() const
+    {
+        assert(typeName);
+        return *typeName;
+    }
+    void setTypeName(const TString& n)
+    {
+        typeName = NewPoolTString(n.c_str());
+    }
+
+    bool isField() const { return fieldName != 0; }
+    const TString& getFieldName() const
+    {
+        assert(fieldName);
+        return *fieldName;
+    }
+    void setFieldName(const TString& n)
+    {
+        fieldName = NewPoolTString(n.c_str());
+    }
+
     TString& getMangledName() {
         if (!mangled) {
             mangled = NewPoolTString("");
@@ -255,6 +234,7 @@ public:
 
         return *mangled;
     }
+
     bool sameElementType(const TType& right) const {
         return      type == right.type   &&
                     size == right.size   &&
@@ -282,6 +262,10 @@ public:
 
         return false;
     }
+
+    const char* getBasicString() const { return ::getBasicString(type); }
+    const char* getPrecisionString() const { return ::getPrecisionString(precision); }
+    const char* getQualifierString() const { return ::getQualifierString(qualifier); }
     TString getCompleteString() const;
 
 protected:
@@ -295,11 +279,12 @@ protected:
     unsigned int matrix  : 1;
     unsigned int array   : 1;
     int arraySize;
+    int maxArraySize;
+    TType* arrayInformationType;
 
     TTypeList* structure;      // 0 unless this is a struct
     mutable int structureSize;
-    int maxArraySize;
-    TType* arrayInformationType;
+
     TString *fieldName;         // for structure field names
     TString *mangled;
     TString *typeName;          // for structure field type name
diff --git a/ANGLE/src/compiler/glslang.l b/ANGLE/src/compiler/glslang.l
index 395c0bf..02c226f 100644
--- a/ANGLE/src/compiler/glslang.l
+++ b/ANGLE/src/compiler/glslang.l
@@ -309,7 +309,7 @@ int PaParseStrings(char* argv[], int strLen[], int argc, TParseContext& parseCon
    
     if (*cpp->PaStrLen >= 0) {    
         int ret = yyparse((void*)(&parseContextLocal));
-        if (cpp->CompileError == 1 || parseContextLocal.recoveredFromError || parseContextLocal.numErrors > 0)
+        if (ret || cpp->CompileError == 1 || parseContextLocal.recoveredFromError || parseContextLocal.numErrors > 0)
              return 1;
         else
              return 0;
@@ -318,7 +318,7 @@ int PaParseStrings(char* argv[], int strLen[], int argc, TParseContext& parseCon
         return 0;
 }
 
-void yyerror(char *s) 
+void yyerror(const char *s) 
 {
     if (((TParseContext *)cpp->pC)->AfterEOF) {
         if (cpp->tokensBeforeEOF == 1) {
diff --git a/ANGLE/src/compiler/glslang.y b/ANGLE/src/compiler/glslang.y
index a297ad2..d0d29df 100644
--- a/ANGLE/src/compiler/glslang.y
+++ b/ANGLE/src/compiler/glslang.y
@@ -38,7 +38,7 @@ compiler/tools. Remove it when we can exclusively use the newer version.
 #define parseContext ((TParseContext*)(parseContextLocal))
 #define YYLEX_PARAM parseContextLocal
 #define YY_DECL int yylex(YYSTYPE* pyylval, void* parseContextLocal)
-extern void yyerror(char*);
+extern void yyerror(const char*);
 
 #define FRAG_VERT_ONLY(S, L) {                                                  \
     if (parseContext->language != EShLangFragment &&                             \
@@ -311,7 +311,7 @@ postfix_expression
                 $$->setType(TType($1->getBasicType(), $1->getPrecision(), EvqTemporary, $1->getNominalSize(), $1->isMatrix()));
 
             if ($1->getType().getQualifier() == EvqConst)
-                $$->getTypePointer()->changeQualifier(EvqConst);
+                $$->getTypePointer()->setQualifier(EvqConst);
         } else if ($1->isMatrix() && $1->getType().getQualifier() == EvqConst)
             $$->setType(TType($1->getBasicType(), $1->getPrecision(), EvqConst, $1->getNominalSize()));
         else if ($1->isMatrix())
@@ -389,7 +389,7 @@ postfix_expression
             }
         } else if ($1->getBasicType() == EbtStruct) {
             bool fieldFound = false;
-            TTypeList* fields = $1->getType().getStruct();
+            const TTypeList* fields = $1->getType().getStruct();
             if (fields == 0) {
                 parseContext->error($2.line, "structure has no fields", "Internal Error", "");
                 parseContext->recover();
@@ -413,7 +413,7 @@ postfix_expression
                             $$->setType(*(*fields)[i].type);
                             // change the qualifier of the return type, not of the structure field
                             // as the structure definition is shared between various structures.
-                            $$->getTypePointer()->changeQualifier(EvqConst);
+                            $$->getTypePointer()->setQualifier(EvqConst);
                         }
                     } else {
                         ConstantUnion *unionArray = new ConstantUnion[1];
@@ -673,7 +673,7 @@ function_identifier
                 break;
             }
             if (op == EOpNull) {
-                parseContext->error($1.line, "cannot construct this type", TType::getBasicString($1.type), "");
+                parseContext->error($1.line, "cannot construct this type", getBasicString($1.type), "");
                 parseContext->recover();
                 $1.type = EbtFloat;
                 op = EOpConstructFloat;
@@ -1007,12 +1007,12 @@ declaration
             }
         }
         
-        prototype->setOperator(EOpPrototype);
+        prototype->setOp(EOpPrototype);
         $$ = prototype;
     }
     | init_declarator_list SEMICOLON {
         if ($1.intermAggregate)
-            $1.intermAggregate->setOperator(EOpDeclaration);
+            $1.intermAggregate->setOp(EOpDeclaration);
         $$ = $1.intermAggregate;
     }
     | PRECISION precision_qualifier type_specifier_no_prec SEMICOLON {
@@ -1795,19 +1795,24 @@ struct_declaration
         }
         for (unsigned int i = 0; i < $$->size(); ++i) {
             //
-            // Careful not to replace already know aspects of type, like array-ness
+            // Careful not to replace already known aspects of type, like array-ness
             //
-            (*$$)[i].type->setType($1.type, $1.size, $1.matrix, $1.userDef);
+            TType* type = (*$$)[i].type;
+            type->setBasicType($1.type);
+            type->setNominalSize($1.size);
+            type->setMatrix($1.matrix);
 
             // don't allow arrays of arrays
-            if ((*$$)[i].type->isArray()) {
+            if (type->isArray()) {
                 if (parseContext->arrayTypeErrorCheck($1.line, $1))
                     parseContext->recover();
             }
             if ($1.array)
-                (*$$)[i].type->setArraySize($1.arraySize);
-            if ($1.userDef)
-                (*$$)[i].type->setTypeName($1.userDef->getTypeName());
+                type->setArraySize($1.arraySize);
+            if ($1.userDef) {
+                type->setStruct($1.userDef->getStruct());
+                type->setTypeName($1.userDef->getTypeName());
+            }
         }
     }
     ;
@@ -1873,7 +1878,7 @@ compound_statement
     : LEFT_BRACE RIGHT_BRACE { $$ = 0; }
     | LEFT_BRACE { parseContext->symbolTable.push(); } statement_list { parseContext->symbolTable.pop(); } RIGHT_BRACE {
         if ($3 != 0)
-            $3->setOperator(EOpSequence);
+            $3->setOp(EOpSequence);
         $$ = $3;
     }
     ;
@@ -1890,7 +1895,7 @@ compound_statement_no_new_scope
     }
     | LEFT_BRACE statement_list RIGHT_BRACE {
         if ($2)
-            $2->setOperator(EOpSequence);
+            $2->setOp(EOpSequence);
         $$ = $2;
     }
     ;
diff --git a/ANGLE/src/compiler/intermediate.h b/ANGLE/src/compiler/intermediate.h
index c83fc48..d262905 100644
--- a/ANGLE/src/compiler/intermediate.h
+++ b/ANGLE/src/compiler/intermediate.h
@@ -203,8 +203,10 @@ public:
     POOL_ALLOCATOR_NEW_DELETE(GlobalPoolAllocator)
 
     TIntermNode() : line(0) {}
-    virtual TSourceLoc getLine() const { return line; }
-    virtual void setLine(TSourceLoc l) { line = l; }
+
+    TSourceLoc getLine() const { return line; }
+    void setLine(TSourceLoc l) { line = l; }
+
     virtual void traverse(TIntermTraverser*) = 0;
     virtual TIntermTyped* getAsTyped() { return 0; }
     virtual TIntermConstantUnion* getAsConstantUnion() { return 0; }
@@ -215,6 +217,7 @@ public:
     virtual TIntermSymbol* getAsSymbolNode() { return 0; }
     virtual TIntermLoop* getAsLoopNode() { return 0; }
     virtual ~TIntermNode() { }
+
 protected:
     TSourceLoc line;
 };
@@ -233,22 +236,23 @@ struct TIntermNodePair {
 class TIntermTyped : public TIntermNode {
 public:
     TIntermTyped(const TType& t) : type(t)  { }
-    virtual TIntermTyped* getAsTyped()         { return this; }
-    virtual void setType(const TType& t) { type = t; }
-    virtual const TType& getType() const { return type; }
-    virtual TType* getTypePointer() { return &type; }
-
-    virtual TBasicType getBasicType() const { return type.getBasicType(); }
-    virtual TQualifier getQualifier() const { return type.getQualifier(); }
-    virtual TPrecision getPrecision() const { return type.getPrecision(); }
-    virtual int getNominalSize() const { return type.getNominalSize(); }
-    virtual int getSize() const { return type.getInstanceSize(); }
-    virtual bool isMatrix() const { return type.isMatrix(); }
-    virtual bool isArray()  const { return type.isArray(); }
-    virtual bool isVector() const { return type.isVector(); }
-    virtual bool isScalar() const { return type.isScalar(); }
-    const char* getBasicString()      const { return type.getBasicString(); }
-    const char* getQualifierString()  const { return type.getQualifierString(); }
+    virtual TIntermTyped* getAsTyped() { return this; }
+
+    void setType(const TType& t) { type = t; }
+    const TType& getType() const { return type; }
+    TType* getTypePointer() { return &type; }
+
+    TBasicType getBasicType() const { return type.getBasicType(); }
+    TQualifier getQualifier() const { return type.getQualifier(); }
+    TPrecision getPrecision() const { return type.getPrecision(); }
+    int getNominalSize() const { return type.getNominalSize(); }
+    
+    bool isMatrix() const { return type.isMatrix(); }
+    bool isArray()  const { return type.isArray(); }
+    bool isVector() const { return type.isVector(); }
+    bool isScalar() const { return type.isScalar(); }
+    const char* getBasicString() const { return type.getBasicString(); }
+    const char* getQualifierString() const { return type.getQualifierString(); }
     TString getCompleteString() const { return type.getCompleteString(); }
 
 protected:
@@ -266,13 +270,16 @@ public:
             test(aTest),
             terminal(aTerminal),
             first(testFirst) { }
+
     virtual TIntermLoop* getAsLoopNode() { return this; }
     virtual void traverse(TIntermTraverser*);
+
     TIntermNode *getInit() { return init; }
     TIntermNode *getBody() { return body; }
     TIntermTyped *getTest() { return test; }
     TIntermTyped *getTerminal() { return terminal; }
     bool testFirst() { return first; }
+
 protected:
     TIntermNode *init;
     TIntermNode *body;       // code to loop over
@@ -289,9 +296,12 @@ public:
     TIntermBranch(TOperator op, TIntermTyped* e) :
             flowOp(op),
             expression(e) { }
+
     virtual void traverse(TIntermTraverser*);
+
     TOperator getFlowOp() { return flowOp; }
     TIntermTyped* getExpression() { return expression; }
+
 protected:
     TOperator flowOp;
     TIntermTyped* expression;  // non-zero except for "return exp;" statements
@@ -307,10 +317,13 @@ public:
     // it is essential to use "symbol = sym" to assign to symbol
     TIntermSymbol(int i, const TString& sym, const TType& t) : 
             TIntermTyped(t), id(i)  { symbol = sym;} 
-    virtual int getId() const { return id; }
-    virtual const TString& getSymbol() const { return symbol;  }
+
+    int getId() const { return id; }
+    const TString& getSymbol() const { return symbol; }
+
     virtual void traverse(TIntermTraverser*);
     virtual TIntermSymbol* getAsSymbolNode() { return this; }
+
 protected:
     int id;
     TString symbol;
@@ -319,11 +332,15 @@ protected:
 class TIntermConstantUnion : public TIntermTyped {
 public:
     TIntermConstantUnion(ConstantUnion *unionPointer, const TType& t) : TIntermTyped(t), unionArrayPointer(unionPointer) { }
+
     ConstantUnion* getUnionArrayPointer() const { return unionArrayPointer; }
     void setUnionArrayPointer(ConstantUnion *c) { unionArrayPointer = c; }
+
     virtual TIntermConstantUnion* getAsConstantUnion()  { return this; }
-    virtual void traverse(TIntermTraverser* );
-    virtual TIntermTyped* fold(TOperator, TIntermTyped*, TInfoSink&);
+    virtual void traverse(TIntermTraverser*);
+
+    TIntermTyped* fold(TOperator, TIntermTyped*, TInfoSink&);
+
 protected:
     ConstantUnion *unionArrayPointer;
 };
@@ -334,9 +351,11 @@ protected:
 class TIntermOperator : public TIntermTyped {
 public:
     TOperator getOp() const { return op; }
+    void setOp(TOperator o) { op = o; }
+
     bool modifiesState() const;
     bool isConstructor() const;
-    virtual bool promote(TInfoSink&) { return true; }
+
 protected:
     TIntermOperator(TOperator o) : TIntermTyped(TType(EbtFloat, EbpUndefined)), op(o) {}
     TIntermOperator(TOperator o, TType& t) : TIntermTyped(t), op(o) {}   
@@ -349,13 +368,16 @@ protected:
 class TIntermBinary : public TIntermOperator {
 public:
     TIntermBinary(TOperator o) : TIntermOperator(o) {}
-    virtual void traverse(TIntermTraverser*);
-    virtual void setLeft(TIntermTyped* n) { left = n; }
-    virtual void setRight(TIntermTyped* n) { right = n; }
-    virtual TIntermTyped* getLeft() const { return left; }
-    virtual TIntermTyped* getRight() const { return right; }
+
     virtual TIntermBinary* getAsBinaryNode() { return this; }
-    virtual bool promote(TInfoSink&);
+    virtual void traverse(TIntermTraverser*);
+
+    void setLeft(TIntermTyped* n) { left = n; }
+    void setRight(TIntermTyped* n) { right = n; }
+    TIntermTyped* getLeft() const { return left; }
+    TIntermTyped* getRight() const { return right; }
+    bool promote(TInfoSink&);
+
 protected:
     TIntermTyped* left;
     TIntermTyped* right;
@@ -368,11 +390,14 @@ class TIntermUnary : public TIntermOperator {
 public:
     TIntermUnary(TOperator o, TType& t) : TIntermOperator(o, t), operand(0) {}
     TIntermUnary(TOperator o) : TIntermOperator(o), operand(0) {}
+
     virtual void traverse(TIntermTraverser*);
-    virtual void setOperand(TIntermTyped* o) { operand = o; }
-    virtual TIntermTyped* getOperand() { return operand; }
     virtual TIntermUnary* getAsUnaryNode() { return this; }
-    virtual bool promote(TInfoSink&);
+
+    void setOperand(TIntermTyped* o) { operand = o; }
+    TIntermTyped* getOperand() { return operand; }    
+    bool promote(TInfoSink&);
+
 protected:
     TIntermTyped* operand;
 };
@@ -387,21 +412,24 @@ public:
     TIntermAggregate() : TIntermOperator(EOpNull), userDefined(false), pragmaTable(0) { }
     TIntermAggregate(TOperator o) : TIntermOperator(o), pragmaTable(0) { }
     ~TIntermAggregate() { delete pragmaTable; }
+
     virtual TIntermAggregate* getAsAggregate() { return this; }
-    virtual void setOperator(TOperator o) { op = o; }
-    virtual TIntermSequence& getSequence() { return sequence; }
-    virtual void setName(const TString& n) { name = n; }
-    virtual const TString& getName() const { return name; }
     virtual void traverse(TIntermTraverser*);
-    virtual void setUserDefined() { userDefined = true; }
-    virtual bool isUserDefined() { return userDefined; }
-    virtual TQualifierList& getQualifier() { return qualifier; }
+
+    TIntermSequence& getSequence() { return sequence; }
+    void setName(const TString& n) { name = n; }
+    const TString& getName() const { return name; }
+
+    void setUserDefined() { userDefined = true; }
+    bool isUserDefined() { return userDefined; }
+    TQualifierList& getQualifier() { return qualifier; }
     void setOptimize(bool o) { optimize = o; }
-    void setDebug(bool d) { debug = d; }
     bool getOptimize() { return optimize; }
+    void setDebug(bool d) { debug = d; }
     bool getDebug() { return debug; }
     void addToPragmaTable(const TPragmaTable& pTable);
     const TPragmaTable& getPragmaTable() const { return *pragmaTable; }
+
 protected:
     TIntermAggregate(const TIntermAggregate&); // disallow copy constructor
     TIntermAggregate& operator=(const TIntermAggregate&); // disallow assignment operator
@@ -423,12 +451,15 @@ public:
             TIntermTyped(TType(EbtVoid, EbpUndefined)), condition(cond), trueBlock(trueB), falseBlock(falseB) {}
     TIntermSelection(TIntermTyped* cond, TIntermNode* trueB, TIntermNode* falseB, const TType& type) :
             TIntermTyped(type), condition(cond), trueBlock(trueB), falseBlock(falseB) {}
+
     virtual void traverse(TIntermTraverser*);
+
     bool usesTernaryOperator() const { return getBasicType() != EbtVoid; }
-    virtual TIntermNode* getCondition() const { return condition; }
-    virtual TIntermNode* getTrueBlock() const { return trueBlock; }
-    virtual TIntermNode* getFalseBlock() const { return falseBlock; }
-    virtual TIntermSelection* getAsSelectionNode() { return this; }
+    TIntermNode* getCondition() const { return condition; }
+    TIntermNode* getTrueBlock() const { return trueBlock; }
+    TIntermNode* getFalseBlock() const { return falseBlock; }
+    TIntermSelection* getAsSelectionNode() { return this; }
+
 protected:
     TIntermTyped* condition;
     TIntermNode* trueBlock;
diff --git a/ANGLE/src/compiler/parseConst.cpp b/ANGLE/src/compiler/parseConst.cpp
index 833d429..9a8a50c 100644
--- a/ANGLE/src/compiler/parseConst.cpp
+++ b/ANGLE/src/compiler/parseConst.cpp
@@ -12,23 +12,31 @@
 //
 class TConstTraverser : public TIntermTraverser {
 public:
-    TConstTraverser(ConstantUnion* cUnion, bool singleConstParam, TOperator constructType, TInfoSink& sink, TSymbolTable& symTable, TType& t) : unionArray(cUnion), type(t),
-        constructorType(constructType), singleConstantParam(singleConstParam), infoSink(sink), symbolTable(symTable), error(false), isMatrix(false), matrixSize(0)
-	{
-		index = 0;
-	}
+    TConstTraverser(ConstantUnion* cUnion, bool singleConstParam, TOperator constructType, TInfoSink& sink, TSymbolTable& symTable, TType& t)
+        : error(false),
+          index(0),
+          unionArray(cUnion),
+          type(t),
+          constructorType(constructType),
+          singleConstantParam(singleConstParam),
+          infoSink(sink),
+          symbolTable(symTable),
+          size(0),
+          isMatrix(false),
+          matrixSize(0) {
+    }
 
-	bool error;
+    bool error;
 
 protected:
-	void visitSymbol(TIntermSymbol*);
-	void visitConstantUnion(TIntermConstantUnion*);
-	bool visitBinary(Visit visit, TIntermBinary*);
-	bool visitUnary(Visit visit, TIntermUnary*);
-	bool visitSelection(Visit visit, TIntermSelection*);
-	bool visitAggregate(Visit visit, TIntermAggregate*);
-	bool visitLoop(Visit visit, TIntermLoop*);
-	bool visitBranch(Visit visit, TIntermBranch*);
+    void visitSymbol(TIntermSymbol*);
+    void visitConstantUnion(TIntermConstantUnion*);
+    bool visitBinary(Visit visit, TIntermBinary*);
+    bool visitUnary(Visit visit, TIntermUnary*);
+    bool visitSelection(Visit visit, TIntermSelection*);
+    bool visitAggregate(Visit visit, TIntermAggregate*);
+    bool visitLoop(Visit visit, TIntermLoop*);
+    bool visitBranch(Visit visit, TIntermBranch*);
 
     int index;
     ConstantUnion *unionArray;
diff --git a/ANGLE/src/compiler/preprocessor/atom.c b/ANGLE/src/compiler/preprocessor/atom.c
index 32b9c74..c5636b7 100644
--- a/ANGLE/src/compiler/preprocessor/atom.c
+++ b/ANGLE/src/compiler/preprocessor/atom.c
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
@@ -624,7 +619,7 @@ static int AddAtomFixed(AtomTable *atable, const char *s, int atom)
 
 int InitAtomTable(AtomTable *atable, int htsize)
 {
-    int ii;
+    unsigned int ii;
 
     htsize = htsize <= 0 ? INIT_HASH_TABLE_SIZE : htsize;
     if (!InitStringTable(&atable->stable))
diff --git a/ANGLE/src/compiler/preprocessor/atom.h b/ANGLE/src/compiler/preprocessor/atom.h
index 9d42037..1d84c32 100644
--- a/ANGLE/src/compiler/preprocessor/atom.h
+++ b/ANGLE/src/compiler/preprocessor/atom.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/compile.h b/ANGLE/src/compiler/preprocessor/compile.h
index a40b99e..5bfa902 100644
--- a/ANGLE/src/compiler/preprocessor/compile.h
+++ b/ANGLE/src/compiler/preprocessor/compile.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/cpp.c b/ANGLE/src/compiler/preprocessor/cpp.c
index 6bf8e65..f15c56d 100644
--- a/ANGLE/src/compiler/preprocessor/cpp.c
+++ b/ANGLE/src/compiler/preprocessor/cpp.c
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/cpp.h b/ANGLE/src/compiler/preprocessor/cpp.h
index 658475e..db4c184 100644
--- a/ANGLE/src/compiler/preprocessor/cpp.h
+++ b/ANGLE/src/compiler/preprocessor/cpp.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/cppstruct.c b/ANGLE/src/compiler/preprocessor/cppstruct.c
index afbc477..8e142bc 100644
--- a/ANGLE/src/compiler/preprocessor/cppstruct.c
+++ b/ANGLE/src/compiler/preprocessor/cppstruct.c
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/memory.c b/ANGLE/src/compiler/preprocessor/memory.c
index 393a0d0..e6fea7a 100644
--- a/ANGLE/src/compiler/preprocessor/memory.c
+++ b/ANGLE/src/compiler/preprocessor/memory.c
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/memory.h b/ANGLE/src/compiler/preprocessor/memory.h
index e7f5b75..b3ae2f9 100644
--- a/ANGLE/src/compiler/preprocessor/memory.h
+++ b/ANGLE/src/compiler/preprocessor/memory.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/parser.h b/ANGLE/src/compiler/preprocessor/parser.h
index 91a6200..f67342b 100644
--- a/ANGLE/src/compiler/preprocessor/parser.h
+++ b/ANGLE/src/compiler/preprocessor/parser.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/preprocess.h b/ANGLE/src/compiler/preprocessor/preprocess.h
index 3dd605b..0602c91 100644
--- a/ANGLE/src/compiler/preprocessor/preprocess.h
+++ b/ANGLE/src/compiler/preprocessor/preprocess.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/scanner.c b/ANGLE/src/compiler/preprocessor/scanner.c
index 0944da5..c77d271 100644
--- a/ANGLE/src/compiler/preprocessor/scanner.c
+++ b/ANGLE/src/compiler/preprocessor/scanner.c
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/scanner.h b/ANGLE/src/compiler/preprocessor/scanner.h
index c422b3a..571fe57 100644
--- a/ANGLE/src/compiler/preprocessor/scanner.h
+++ b/ANGLE/src/compiler/preprocessor/scanner.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/slglobals.h b/ANGLE/src/compiler/preprocessor/slglobals.h
index a535180..4634626 100644
--- a/ANGLE/src/compiler/preprocessor/slglobals.h
+++ b/ANGLE/src/compiler/preprocessor/slglobals.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/symbols.c b/ANGLE/src/compiler/preprocessor/symbols.c
index 1193abb..5baedf5 100644
--- a/ANGLE/src/compiler/preprocessor/symbols.c
+++ b/ANGLE/src/compiler/preprocessor/symbols.c
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
@@ -157,7 +152,7 @@ Symbol *NewSymbol(SourceLoc *loc, Scope *fScope, int name, symbolkind kind)
 {
     Symbol *lSymb;
     char *pch;
-    int ii;
+    unsigned int ii;
 
     lSymb = (Symbol *) mem_Alloc(fScope->pool, sizeof(Symbol));
     lSymb->left = NULL;
diff --git a/ANGLE/src/compiler/preprocessor/symbols.h b/ANGLE/src/compiler/preprocessor/symbols.h
index 41e0778..c19f79c 100644
--- a/ANGLE/src/compiler/preprocessor/symbols.h
+++ b/ANGLE/src/compiler/preprocessor/symbols.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/compiler/preprocessor/tokens.c b/ANGLE/src/compiler/preprocessor/tokens.c
index 7cfc73d..057cce8 100644
--- a/ANGLE/src/compiler/preprocessor/tokens.c
+++ b/ANGLE/src/compiler/preprocessor/tokens.c
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
@@ -210,7 +205,7 @@ void DeleteTokenStream(TokenStream *pTok)
 void RecordToken(TokenStream *pTok, int token, yystypepp * yylvalpp)
 {
     const char *s;
-    unsigned char *str=NULL;
+    char *str=NULL;
 
     if (token > 256)
         lAddByte(pTok, (unsigned char)((token & 0x7f) + 0x80));
diff --git a/ANGLE/src/compiler/preprocessor/tokens.h b/ANGLE/src/compiler/preprocessor/tokens.h
index 8d7e712..8766df9 100644
--- a/ANGLE/src/compiler/preprocessor/tokens.h
+++ b/ANGLE/src/compiler/preprocessor/tokens.h
@@ -1,8 +1,3 @@
-//
-// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-//
 /****************************************************************************\
 Copyright (c) 2002, NVIDIA Corporation.
 
diff --git a/ANGLE/src/libEGL/Display.cpp b/ANGLE/src/libEGL/Display.cpp
index 287d8da..e2802da 100644
--- a/ANGLE/src/libEGL/Display.cpp
+++ b/ANGLE/src/libEGL/Display.cpp
@@ -23,8 +23,12 @@ namespace egl
 {
 Display::Display(HDC deviceContext) : mDc(deviceContext)
 {
+    mD3d9Module = NULL;
+    
     mD3d9 = NULL;
+    mD3d9ex = NULL;
     mDevice = NULL;
+    mDeviceWindow = NULL;
 
     mAdapter = D3DADAPTER_DEFAULT;
 
@@ -51,7 +55,38 @@ bool Display::initialize()
         return true;
     }
 
-    mD3d9 = Direct3DCreate9(D3D_SDK_VERSION);
+    mD3d9Module = LoadLibrary(TEXT("d3d9.dll"));
+    if (mD3d9Module == NULL)
+    {
+        terminate();
+        return false;
+    }
+
+    typedef IDirect3D9* (WINAPI *Direct3DCreate9Func)(UINT);
+    Direct3DCreate9Func Direct3DCreate9Ptr = reinterpret_cast<Direct3DCreate9Func>(GetProcAddress(mD3d9Module, "Direct3DCreate9"));
+
+    if (Direct3DCreate9Ptr == NULL)
+    {
+        terminate();
+        return false;
+    }
+
+    typedef HRESULT (WINAPI *Direct3DCreate9ExFunc)(UINT, IDirect3D9Ex**);
+    Direct3DCreate9ExFunc Direct3DCreate9ExPtr = reinterpret_cast<Direct3DCreate9ExFunc>(GetProcAddress(mD3d9Module, "Direct3DCreate9Ex"));
+
+    // Use Direct3D9Ex if available. Among other things, this version is less
+    // inclined to report a lost context, for example when the user switches
+    // desktop. Direct3D9Ex is available in Windows Vista and later if suitable drivers are available.
+    if (Direct3DCreate9ExPtr && SUCCEEDED(Direct3DCreate9ExPtr(D3D_SDK_VERSION, &mD3d9ex)))
+    {
+        ASSERT(mD3d9ex);
+        mD3d9ex->QueryInterface(IID_IDirect3D9, reinterpret_cast<void**>(&mD3d9));
+        ASSERT(mD3d9);
+    }
+    else
+    {
+        mD3d9 = Direct3DCreate9Ptr(D3D_SDK_VERSION);
+    }
 
     if (mD3d9)
     {
@@ -69,86 +104,91 @@ bool Display::initialize()
 
         if (mDeviceCaps.PixelShaderVersion < D3DPS_VERSION(2, 0))
         {
-            mD3d9->Release();
-            mD3d9 = NULL;
+            terminate();
+            return error(EGL_NOT_INITIALIZED, false);
         }
-        else
-        {
-            mMinSwapInterval = 4;
-            mMaxSwapInterval = 0;
 
-            if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_IMMEDIATE) {mMinSwapInterval = std::min(mMinSwapInterval, 0); mMaxSwapInterval = std::max(mMaxSwapInterval, 0);}
-            if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_ONE)       {mMinSwapInterval = std::min(mMinSwapInterval, 1); mMaxSwapInterval = std::max(mMaxSwapInterval, 1);}
-            if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_TWO)       {mMinSwapInterval = std::min(mMinSwapInterval, 2); mMaxSwapInterval = std::max(mMaxSwapInterval, 2);}
-            if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_THREE)     {mMinSwapInterval = std::min(mMinSwapInterval, 3); mMaxSwapInterval = std::max(mMaxSwapInterval, 3);}
-            if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_FOUR)      {mMinSwapInterval = std::min(mMinSwapInterval, 4); mMaxSwapInterval = std::max(mMaxSwapInterval, 4);}
+        mMinSwapInterval = 4;
+        mMaxSwapInterval = 0;
 
-            const D3DFORMAT renderTargetFormats[] =
-            {
-                D3DFMT_A1R5G5B5,
-            //  D3DFMT_A2R10G10B10,   // The color_ramp conformance test uses ReadPixels with UNSIGNED_BYTE causing it to think that rendering skipped a colour value.
-                D3DFMT_A8R8G8B8,
-                D3DFMT_R5G6B5,
-                D3DFMT_X1R5G5B5,
-                D3DFMT_X8R8G8B8
-            };
-
-            const D3DFORMAT depthStencilFormats[] =
-            {
-            //  D3DFMT_D16_LOCKABLE,
-                D3DFMT_D32,
-            //  D3DFMT_D15S1,
-                D3DFMT_D24S8,
-                D3DFMT_D24X8,
-            //  D3DFMT_D24X4S4,
-                D3DFMT_D16,
-            //  D3DFMT_D32F_LOCKABLE,
-            //  D3DFMT_D24FS8
-            };
-
-            D3DDISPLAYMODE currentDisplayMode;
-            mD3d9->GetAdapterDisplayMode(mAdapter, &currentDisplayMode);
-
-            ConfigSet configSet;
-
-            for (int formatIndex = 0; formatIndex < sizeof(renderTargetFormats) / sizeof(D3DFORMAT); formatIndex++)
-            {
-                D3DFORMAT renderTargetFormat = renderTargetFormats[formatIndex];
+        if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_IMMEDIATE) {mMinSwapInterval = std::min(mMinSwapInterval, 0); mMaxSwapInterval = std::max(mMaxSwapInterval, 0);}
+        if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_ONE)       {mMinSwapInterval = std::min(mMinSwapInterval, 1); mMaxSwapInterval = std::max(mMaxSwapInterval, 1);}
+        if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_TWO)       {mMinSwapInterval = std::min(mMinSwapInterval, 2); mMaxSwapInterval = std::max(mMaxSwapInterval, 2);}
+        if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_THREE)     {mMinSwapInterval = std::min(mMinSwapInterval, 3); mMaxSwapInterval = std::max(mMaxSwapInterval, 3);}
+        if (mDeviceCaps.PresentationIntervals & D3DPRESENT_INTERVAL_FOUR)      {mMinSwapInterval = std::min(mMinSwapInterval, 4); mMaxSwapInterval = std::max(mMaxSwapInterval, 4);}
+
+        const D3DFORMAT renderTargetFormats[] =
+        {
+            D3DFMT_A1R5G5B5,
+        //  D3DFMT_A2R10G10B10,   // The color_ramp conformance test uses ReadPixels with UNSIGNED_BYTE causing it to think that rendering skipped a colour value.
+            D3DFMT_A8R8G8B8,
+            D3DFMT_R5G6B5,
+            D3DFMT_X1R5G5B5,
+            D3DFMT_X8R8G8B8
+        };
+
+        const D3DFORMAT depthStencilFormats[] =
+        {
+        //  D3DFMT_D16_LOCKABLE,
+            D3DFMT_D32,
+        //  D3DFMT_D15S1,
+            D3DFMT_D24S8,
+            D3DFMT_D24X8,
+        //  D3DFMT_D24X4S4,
+            D3DFMT_D16,
+        //  D3DFMT_D32F_LOCKABLE,
+        //  D3DFMT_D24FS8
+        };
+
+        D3DDISPLAYMODE currentDisplayMode;
+        mD3d9->GetAdapterDisplayMode(mAdapter, &currentDisplayMode);
+
+        ConfigSet configSet;
+
+        for (int formatIndex = 0; formatIndex < sizeof(renderTargetFormats) / sizeof(D3DFORMAT); formatIndex++)
+        {
+            D3DFORMAT renderTargetFormat = renderTargetFormats[formatIndex];
 
-                HRESULT result = mD3d9->CheckDeviceFormat(mAdapter, mDeviceType, currentDisplayMode.Format, D3DUSAGE_RENDERTARGET, D3DRTYPE_SURFACE, renderTargetFormat);
+            HRESULT result = mD3d9->CheckDeviceFormat(mAdapter, mDeviceType, currentDisplayMode.Format, D3DUSAGE_RENDERTARGET, D3DRTYPE_SURFACE, renderTargetFormat);
 
-                if (SUCCEEDED(result))
+            if (SUCCEEDED(result))
+            {
+                for (int depthStencilIndex = 0; depthStencilIndex < sizeof(depthStencilFormats) / sizeof(D3DFORMAT); depthStencilIndex++)
                 {
-                    for (int depthStencilIndex = 0; depthStencilIndex < sizeof(depthStencilFormats) / sizeof(D3DFORMAT); depthStencilIndex++)
+                    D3DFORMAT depthStencilFormat = depthStencilFormats[depthStencilIndex];
+                    HRESULT result = mD3d9->CheckDeviceFormat(mAdapter, mDeviceType, currentDisplayMode.Format, D3DUSAGE_DEPTHSTENCIL, D3DRTYPE_SURFACE, depthStencilFormat);
+
+                    if (SUCCEEDED(result))
                     {
-                        D3DFORMAT depthStencilFormat = depthStencilFormats[depthStencilIndex];
-                        HRESULT result = mD3d9->CheckDeviceFormat(mAdapter, mDeviceType, currentDisplayMode.Format, D3DUSAGE_DEPTHSTENCIL, D3DRTYPE_SURFACE, depthStencilFormat);
+                        HRESULT result = mD3d9->CheckDepthStencilMatch(mAdapter, mDeviceType, currentDisplayMode.Format, renderTargetFormat, depthStencilFormat);
 
                         if (SUCCEEDED(result))
                         {
-                            HRESULT result = mD3d9->CheckDepthStencilMatch(mAdapter, mDeviceType, currentDisplayMode.Format, renderTargetFormat, depthStencilFormat);
+                            // FIXME: enumerate multi-sampling
 
-                            if (SUCCEEDED(result))
-                            {
-                                // FIXME: Enumerate multi-sampling
-
-                                configSet.add(currentDisplayMode, mMinSwapInterval, mMaxSwapInterval, renderTargetFormat, depthStencilFormat, 0);
-                            }
+                            configSet.add(currentDisplayMode, mMinSwapInterval, mMaxSwapInterval, renderTargetFormat, depthStencilFormat, 0);
                         }
                     }
                 }
             }
+        }
 
-            // Give the sorted configs a unique ID and store them internally
-            EGLint index = 1;
-            for (ConfigSet::Iterator config = configSet.mSet.begin(); config != configSet.mSet.end(); config++)
-            {
-                Config configuration = *config;
-                configuration.mConfigID = index;
-                index++;
+        // Give the sorted configs a unique ID and store them internally
+        EGLint index = 1;
+        for (ConfigSet::Iterator config = configSet.mSet.begin(); config != configSet.mSet.end(); config++)
+        {
+            Config configuration = *config;
+            configuration.mConfigID = index;
+            index++;
 
-                mConfigSet.mSet.insert(configuration);
-            }
+            mConfigSet.mSet.insert(configuration);
+        }
+
+        if (!createDevice())
+        {
+            terminate();
+
+            return false;
         }
     }
 
@@ -185,6 +225,24 @@ void Display::terminate()
         mD3d9->Release();
         mD3d9 = NULL;
     }
+
+    if (mDeviceWindow)
+    {
+        DestroyWindow(mDeviceWindow);
+        mDeviceWindow = NULL;
+    }
+    
+    if (mD3d9ex)
+    {
+        mD3d9ex->Release();
+        mD3d9ex = NULL;
+    }
+
+    if (mD3d9Module)
+    {
+        FreeLibrary(mD3d9Module);
+        mD3d9Module = NULL;
+    }
 }
 
 void Display::startScene()
@@ -254,132 +312,74 @@ bool Display::getConfigAttrib(EGLConfig config, EGLint attribute, EGLint *value)
     return true;
 }
 
-Surface *Display::createWindowSurface(HWND window, EGLConfig config)
+bool Display::createDevice()
 {
-    const Config *configuration = mConfigSet.get(config);
+    static const TCHAR windowName[] = TEXT("AngleHiddenWindow");
+    static const TCHAR className[] = TEXT("STATIC");
+
+    mDeviceWindow = CreateWindowEx(WS_EX_NOACTIVATE, className, windowName, WS_DISABLED | WS_POPUP, 0, 0, 1, 1, HWND_MESSAGE, NULL, GetModuleHandle(NULL), NULL);
 
     D3DPRESENT_PARAMETERS presentParameters = {0};
 
-    presentParameters.AutoDepthStencilFormat = configuration->mDepthStencilFormat;
+    // The default swap chain is never actually used. Surface will create a new swap chain with the proper parameters.
+    presentParameters.AutoDepthStencilFormat = D3DFMT_UNKNOWN;
     presentParameters.BackBufferCount = 1;
-    presentParameters.BackBufferFormat = configuration->mRenderTargetFormat;
-    presentParameters.BackBufferWidth = 0;
-    presentParameters.BackBufferHeight = 0;
-    presentParameters.EnableAutoDepthStencil = configuration->mDepthSize ? TRUE : FALSE;
+    presentParameters.BackBufferFormat = D3DFMT_UNKNOWN;
+    presentParameters.BackBufferWidth = 1;
+    presentParameters.BackBufferHeight = 1;
+    presentParameters.EnableAutoDepthStencil = FALSE;
     presentParameters.Flags = 0;
-    presentParameters.hDeviceWindow = window;
-    presentParameters.MultiSampleQuality = 0;                  // FIXME: Unimplemented
-    presentParameters.MultiSampleType = D3DMULTISAMPLE_NONE;   // FIXME: Unimplemented
+    presentParameters.hDeviceWindow = mDeviceWindow;
+    presentParameters.MultiSampleQuality = 0;
+    presentParameters.MultiSampleType = D3DMULTISAMPLE_NONE;
     presentParameters.PresentationInterval = convertInterval(mMinSwapInterval);
-    presentParameters.SwapEffect = D3DSWAPEFFECT_COPY;
-    presentParameters.Windowed = TRUE;   // FIXME
+    presentParameters.SwapEffect = D3DSWAPEFFECT_DISCARD;
+    presentParameters.Windowed = TRUE;
 
-    IDirect3DSwapChain9 *swapChain = NULL;
-    IDirect3DSurface9 *depthStencilSurface = NULL;
+    DWORD behaviorFlags = D3DCREATE_FPU_PRESERVE | D3DCREATE_NOWINDOWCHANGES;
 
-    if (!mDevice)
+    HRESULT result = mD3d9->CreateDevice(mAdapter, mDeviceType, mDeviceWindow, behaviorFlags | D3DCREATE_HARDWARE_VERTEXPROCESSING | D3DCREATE_PUREDEVICE, &presentParameters, &mDevice);
+
+    if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
     {
-        DWORD behaviorFlags = D3DCREATE_FPU_PRESERVE | D3DCREATE_NOWINDOWCHANGES;
+        return error(EGL_BAD_ALLOC, false);
+    }
 
-        HRESULT result = mD3d9->CreateDevice(mAdapter, mDeviceType, window, behaviorFlags | D3DCREATE_HARDWARE_VERTEXPROCESSING | D3DCREATE_PUREDEVICE, &presentParameters, &mDevice);
+    if (FAILED(result))
+    {
+        result = mD3d9->CreateDevice(mAdapter, mDeviceType, mDeviceWindow, behaviorFlags | D3DCREATE_SOFTWARE_VERTEXPROCESSING, &presentParameters, &mDevice);
 
         if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
         {
-            return error(EGL_BAD_ALLOC, (egl::Surface*)NULL);
-        }
-
-        if (FAILED(result))
-        {
-            result = mD3d9->CreateDevice(mAdapter, mDeviceType, window, behaviorFlags | D3DCREATE_SOFTWARE_VERTEXPROCESSING, &presentParameters, &mDevice);
-
-            if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
-            {
-                return error(EGL_BAD_ALLOC, (egl::Surface*)NULL);
-            }
-        }
-
-        ASSERT(SUCCEEDED(result));
-
-        if (mDevice)
-        {
-            mSceneStarted = false;
-            mDevice->GetSwapChain(0, &swapChain);
-            mDevice->GetDepthStencilSurface(&depthStencilSurface);
+            return error(EGL_BAD_ALLOC, false);
         }
     }
-    else
-    {
-        if (!mSurfaceSet.empty())
-        {
-            // if the device already exists, and there are other surfaces/windows currently in use, we need to create
-            // a separate swap chain for the new draw surface.
-            HRESULT result = mDevice->CreateAdditionalSwapChain(&presentParameters, &swapChain);
-
-            if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
-            {
-                ERR("Could not create additional swap chains. Out of memory.");
-                return error(EGL_BAD_ALLOC, (egl::Surface*)NULL);
-            }
-
-            ASSERT(SUCCEEDED(result));
 
-            // CreateAdditionalSwapChain does not automatically generate a depthstencil surface, unlike 
-            // CreateDevice, so we must do so explicitly.
-            result = mDevice->CreateDepthStencilSurface(presentParameters.BackBufferWidth, presentParameters.BackBufferHeight,
-                                                        presentParameters.AutoDepthStencilFormat, presentParameters.MultiSampleType,
-                                                        presentParameters.MultiSampleQuality, FALSE, &depthStencilSurface, NULL);
+    ASSERT(SUCCEEDED(result));
 
-            if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
-            {
-                swapChain->Release();
-                ERR("Could not create depthstencil surface for new swap chain. Out of memory.");
-                return error(EGL_BAD_ALLOC, (egl::Surface*)NULL);
-            }
+    // Permanent non-default states
+    mDevice->SetRenderState(D3DRS_POINTSPRITEENABLE, TRUE);
 
-            ASSERT(SUCCEEDED(result));
-        }
-        else
-        {
-            // if the device already exists, but there are no surfaces in use, then all the surfaces/windows
-            // have been destroyed, and we should repurpose the originally created depthstencil surface for
-            // use with the new surface we are creating.
-            HRESULT result = mDevice->Reset(&presentParameters);
+    mSceneStarted = false;
 
-            if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
-            {
-                ERR("Could not reset presentation parameters for device. Out of memory.");
-                return error(EGL_BAD_ALLOC, (egl::Surface*)NULL);
-            }
-
-            ASSERT(SUCCEEDED(result));
-
-            if (mDevice)
-            {
-                mSceneStarted = false;
-                mDevice->GetSwapChain(0, &swapChain);
-                mDevice->GetDepthStencilSurface(&depthStencilSurface);
-            }
-        }
-    }
-
-    Surface *surface = NULL;
+    return true;
+}
 
-    if (swapChain)
-    {
-        surface = new Surface(this, swapChain, depthStencilSurface, configuration);
-        mSurfaceSet.insert(surface);
+Surface *Display::createWindowSurface(HWND window, EGLConfig config)
+{
+    const Config *configuration = mConfigSet.get(config);
 
-        swapChain->Release();
-    }
+    Surface *surface = new Surface(this, configuration, window);
+    mSurfaceSet.insert(surface);
 
     return surface;
 }
 
-EGLContext Display::createContext(EGLConfig configHandle)
+EGLContext Display::createContext(EGLConfig configHandle, const gl::Context *shareContext)
 {
     const egl::Config *config = mConfigSet.get(configHandle);
 
-    gl::Context *context = glCreateContext(config);
+    gl::Context *context = glCreateContext(config, shareContext);
     mContextSet.insert(context);
 
     return context;
@@ -468,4 +468,23 @@ D3DCAPS9 Display::getDeviceCaps()
 {
     return mDeviceCaps;
 }
+
+void Display::getMultiSampleSupport(D3DFORMAT format, bool *multiSampleArray)
+{
+    for (int multiSampleIndex = 0; multiSampleIndex <= D3DMULTISAMPLE_16_SAMPLES; multiSampleIndex++)
+    {
+        HRESULT result = mD3d9->CheckDeviceMultiSampleType(mAdapter, mDeviceType, format,
+                                                           TRUE, (D3DMULTISAMPLE_TYPE)multiSampleIndex, NULL);
+
+        multiSampleArray[multiSampleIndex] = SUCCEEDED(result);
+    }
+}
+
+bool Display::getCompressedTextureSupport()
+{
+    D3DDISPLAYMODE currentDisplayMode;
+    mD3d9->GetAdapterDisplayMode(mAdapter, &currentDisplayMode);
+
+    return SUCCEEDED(mD3d9->CheckDeviceFormat(mAdapter, mDeviceType, currentDisplayMode.Format, 0, D3DRTYPE_TEXTURE, D3DFMT_DXT1));
+}
 }
diff --git a/ANGLE/src/libEGL/Display.h b/ANGLE/src/libEGL/Display.h
index 02c9fde..bd33012 100644
--- a/ANGLE/src/libEGL/Display.h
+++ b/ANGLE/src/libEGL/Display.h
@@ -43,7 +43,7 @@ class Display
     bool getConfigAttrib(EGLConfig config, EGLint attribute, EGLint *value);
 
     egl::Surface *createWindowSurface(HWND window, EGLConfig config);
-    EGLContext createContext(EGLConfig configHandle);
+    EGLContext createContext(EGLConfig configHandle, const gl::Context *shareContext);
 
     void destroySurface(egl::Surface *surface);
     void destroyContext(gl::Context *context);
@@ -60,16 +60,22 @@ class Display
 
     virtual IDirect3DDevice9 *getDevice();
     virtual D3DCAPS9 getDeviceCaps();
+    virtual void getMultiSampleSupport(D3DFORMAT format, bool *multiSampleArray);
+    virtual bool getCompressedTextureSupport();
 
   private:
     DISALLOW_COPY_AND_ASSIGN(Display);
     const HDC mDc;
 
+    HMODULE mD3d9Module;
+    
     UINT mAdapter;
     D3DDEVTYPE mDeviceType;
-    IDirect3D9 *mD3d9;
+    IDirect3D9 *mD3d9;  // Always valid after successful initialization.
+    IDirect3D9Ex *mD3d9ex;  // Might be null if D3D9Ex is not supported.
     IDirect3DDevice9 *mDevice;
     D3DCAPS9 mDeviceCaps;
+    HWND mDeviceWindow;
 
     bool mSceneStarted;
     GLint mSwapInterval;
@@ -84,6 +90,8 @@ class Display
 
     typedef std::set<gl::Context*> ContextSet;
     ContextSet mContextSet;
+
+    bool createDevice();
 };
 }
 
diff --git a/ANGLE/src/libEGL/Surface.cpp b/ANGLE/src/libEGL/Surface.cpp
index ef5c6c7..a5638d4 100644
--- a/ANGLE/src/libEGL/Surface.cpp
+++ b/ANGLE/src/libEGL/Surface.cpp
@@ -17,9 +17,11 @@
 
 namespace egl
 {
-Surface::Surface(Display *display, IDirect3DSwapChain9 *swapChain, IDirect3DSurface9 *depthStencil, const Config *config) 
-    : mDisplay(display), mSwapChain(swapChain), mDepthStencil(depthStencil), mConfig(config)
+Surface::Surface(Display *display, const Config *config, HWND window) 
+    : mDisplay(display), mConfig(config), mWindow(window)
 {
+    mSwapChain = NULL;
+    mDepthStencil = NULL;
     mBackBuffer = NULL;
     mRenderTarget = NULL;
     mFlipTexture = NULL;
@@ -30,42 +32,7 @@ Surface::Surface(Display *display, IDirect3DSwapChain9 *swapChain, IDirect3DSurf
     mRenderBuffer = EGL_BACK_BUFFER;
     mSwapBehavior = EGL_BUFFER_PRESERVED;
 
-    if (mSwapChain)
-    {
-        mSwapChain->AddRef();
-        mSwapChain->GetBackBuffer(0, D3DBACKBUFFER_TYPE_MONO, &mBackBuffer);
-
-        D3DSURFACE_DESC description;
-        mBackBuffer->GetDesc(&description);
-
-        mWidth = description.Width;
-        mHeight = description.Height;
-
-        IDirect3DDevice9 *device = display->getDevice();
-        HRESULT result = device->CreateRenderTarget(mWidth, mHeight, description.Format, description.MultiSampleType, description.MultiSampleQuality, FALSE, &mRenderTarget, NULL);
-
-        if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
-        {
-            error(EGL_BAD_ALLOC);
-
-            return;
-        }
-
-        ASSERT(SUCCEEDED(result));
-
-        result = device->CreateTexture(mWidth, mHeight, 1, D3DUSAGE_RENDERTARGET, description.Format, D3DPOOL_DEFAULT, &mFlipTexture, NULL);
-
-        if (FAILED(result))
-        {
-            ASSERT(result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY);
-
-            error(EGL_BAD_ALLOC);
-
-            mRenderTarget->Release();
-
-            return;
-        }
-    }
+    resetSwapChain();
 }
 
 Surface::~Surface()
@@ -106,20 +73,121 @@ Surface::~Surface()
     }
 }
 
-HWND Surface::getWindowHandle()
+void Surface::resetSwapChain()
 {
-    if (mSwapChain)
+    IDirect3DDevice9 *device = mDisplay->getDevice();
+
+    D3DPRESENT_PARAMETERS presentParameters = {0};
+
+    presentParameters.AutoDepthStencilFormat = mConfig->mDepthStencilFormat;
+    presentParameters.BackBufferCount = 1;
+    presentParameters.BackBufferFormat = mConfig->mRenderTargetFormat;
+    presentParameters.EnableAutoDepthStencil = FALSE;
+    presentParameters.Flags = 0;
+    presentParameters.hDeviceWindow = getWindowHandle();
+    presentParameters.MultiSampleQuality = 0;                  // FIXME: Unimplemented
+    presentParameters.MultiSampleType = D3DMULTISAMPLE_NONE;   // FIXME: Unimplemented
+    presentParameters.PresentationInterval = Display::convertInterval(mConfig->mMinSwapInterval);
+    presentParameters.SwapEffect = D3DSWAPEFFECT_DISCARD;
+    presentParameters.Windowed = TRUE;
+
+    RECT windowRect;
+    if (!GetClientRect(getWindowHandle(), &windowRect))
+    {
+        ASSERT(false);
+        return;
+    }
+
+    presentParameters.BackBufferWidth = windowRect.right - windowRect.left;
+    presentParameters.BackBufferHeight = windowRect.bottom - windowRect.top;
+
+    IDirect3DSwapChain9 *swapChain = NULL;
+    HRESULT result = device->CreateAdditionalSwapChain(&presentParameters, &swapChain);
+
+    if (FAILED(result))
+    {
+        ASSERT(result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY);
+
+        ERR("Could not create additional swap chains: %08lX", result);
+        return error(EGL_BAD_ALLOC);
+    }
+
+    IDirect3DSurface9 *depthStencilSurface = NULL;
+    result = device->CreateDepthStencilSurface(presentParameters.BackBufferWidth, presentParameters.BackBufferHeight,
+                                               presentParameters.AutoDepthStencilFormat, presentParameters.MultiSampleType,
+                                               presentParameters.MultiSampleQuality, FALSE, &depthStencilSurface, NULL);
+
+    if (FAILED(result))
+    {
+        ASSERT(result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY);
+
+        swapChain->Release();
+
+        ERR("Could not create depthstencil surface for new swap chain: %08lX", result);
+        return error(EGL_BAD_ALLOC);
+    }
+
+    IDirect3DSurface9 *renderTarget = NULL;
+    result = device->CreateRenderTarget(presentParameters.BackBufferWidth, presentParameters.BackBufferHeight, presentParameters.BackBufferFormat,
+                                        presentParameters.MultiSampleType, presentParameters.MultiSampleQuality, FALSE, &renderTarget, NULL);
+
+    if (FAILED(result))
+    {
+        ASSERT(result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY);
+
+        swapChain->Release();
+        depthStencilSurface->Release();
+
+        ERR("Could not create render target surface for new swap chain: %08lX", result);
+        return error(EGL_BAD_ALLOC);
+    }
+
+    ASSERT(SUCCEEDED(result));
+
+    IDirect3DTexture9 *flipTexture = NULL;
+    result = device->CreateTexture(presentParameters.BackBufferWidth, presentParameters.BackBufferHeight, 1, D3DUSAGE_RENDERTARGET,
+                                   presentParameters.BackBufferFormat, D3DPOOL_DEFAULT, &flipTexture, NULL);
+
+    if (FAILED(result))
     {
-        D3DPRESENT_PARAMETERS presentParameters;
-        mSwapChain->GetPresentParameters(&presentParameters);
+        ASSERT(result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY);
+
+        swapChain->Release();
+        depthStencilSurface->Release();
+        renderTarget->Release();
 
-        return presentParameters.hDeviceWindow;
+        ERR("Could not create flip texture for new swap chain: %08lX", result);
+        return error(EGL_BAD_ALLOC);
     }
 
-    return NULL;
+    IDirect3DSurface9 *backBuffer = NULL;
+    swapChain->GetBackBuffer(0, D3DBACKBUFFER_TYPE_MONO, &backBuffer);
+
+    if (mSwapChain) mSwapChain->Release();
+    if (mDepthStencil) mDepthStencil->Release();
+    if (mBackBuffer) mBackBuffer->Release();
+    if (mRenderTarget) mRenderTarget->Release();
+    if (mFlipTexture) mFlipTexture->Release();
+
+    mWidth = presentParameters.BackBufferWidth;
+    mHeight = presentParameters.BackBufferHeight;
+
+    mSwapChain = swapChain;
+    mDepthStencil = depthStencilSurface;
+    mBackBuffer = backBuffer;
+    mRenderTarget = renderTarget;
+    mFlipTexture = flipTexture;
+
+    // The flip state block recorded mFlipTexture so it is now invalid.
+    releaseRecordedState(device);
+}
+
+HWND Surface::getWindowHandle()
+{
+    return mWindow;
 }
 
-void Surface::writeRecordableFlipState(IDirect3DDevice9 *device, IDirect3DTexture9 *source)
+void Surface::writeRecordableFlipState(IDirect3DDevice9 *device)
 {
     // Disable all pipeline operations
     device->SetRenderState(D3DRS_ZENABLE, D3DZB_FALSE);
@@ -138,16 +206,18 @@ void Surface::writeRecordableFlipState(IDirect3DDevice9 *device, IDirect3DTextur
     device->SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
     device->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
     device->SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_DISABLE);
-    device->SetTexture(0, source);
+    device->SetTexture(0, NULL); // The actual texture will change after resizing. But the pre-flip state block must save/restore the texture.
     device->SetSamplerState(0, D3DSAMP_MAGFILTER, D3DTEXF_POINT);
     device->SetSamplerState(0, D3DSAMP_MINFILTER, D3DTEXF_POINT);
     device->SetSamplerState(0, D3DSAMP_SRGBTEXTURE, FALSE);
+    device->SetSamplerState(0, D3DSAMP_ADDRESSU, D3DTADDRESS_CLAMP);
+    device->SetSamplerState(0, D3DSAMP_ADDRESSV, D3DTADDRESS_CLAMP);
     device->SetFVF(D3DFVF_XYZRHW | D3DFVF_TEX1);
 
     device->SetStreamSourceFreq(0, 1); // DrawPrimitiveUP only cares about stream 0, not the rest.
 }
 
-void Surface::applyFlipState(IDirect3DDevice9 *device, IDirect3DTexture9 *source)
+void Surface::applyFlipState(IDirect3DDevice9 *device)
 {
     HRESULT hr;
 
@@ -158,7 +228,7 @@ void Surface::applyFlipState(IDirect3DDevice9 *device, IDirect3DTexture9 *source
         // mPreFlipState will record the original state each entry.
         hr = device->BeginStateBlock();
         ASSERT(SUCCEEDED(hr));
-        writeRecordableFlipState(device, source);
+        writeRecordableFlipState(device);
         hr = device->EndStateBlock(&mPreFlipState);
         ASSERT(SUCCEEDED(hr) || hr == D3DERR_OUTOFVIDEOMEMORY || hr == E_OUTOFMEMORY);
 
@@ -171,7 +241,7 @@ void Surface::applyFlipState(IDirect3DDevice9 *device, IDirect3DTexture9 *source
         hr = device->BeginStateBlock();
         ASSERT(SUCCEEDED(hr));
 
-        writeRecordableFlipState(device, source);
+        writeRecordableFlipState(device);
 
         hr = device->EndStateBlock(&mFlipState);
         ASSERT(SUCCEEDED(hr) || hr == D3DERR_OUTOFVIDEOMEMORY || hr == E_OUTOFMEMORY);
@@ -223,29 +293,88 @@ void Surface::restoreState(IDirect3DDevice9 *device)
     }
 }
 
+// On the next flip, this will cause the state to be recorded from scratch.
+// In particular we need to do this if the flip texture changes.
+void Surface::releaseRecordedState(IDirect3DDevice9 *device)
+{
+    if (mFlipState)
+    {
+        mFlipState->Release();
+        mFlipState = NULL;
+    }
+
+    if (mPreFlipState)
+    {
+        mPreFlipState->Release();
+        mPreFlipState = NULL;
+    }
+}
+
+bool Surface::checkForWindowResize()
+{
+    RECT client;
+    if (!GetClientRect(getWindowHandle(), &client))
+    {
+        ASSERT(false);
+        return false;
+    }
+
+    if (getWidth() != client.right - client.left || getHeight() != client.bottom - client.top)
+    {
+        resetSwapChain();
+
+        if (static_cast<egl::Surface*>(getCurrentDrawSurface()) == this)
+        {
+            glMakeCurrent(glGetCurrentContext(), static_cast<egl::Display*>(getCurrentDisplay()), this);
+        }
+
+        return true;
+    }
+
+    return false;
+}
+
 bool Surface::swap()
 {
     if (mSwapChain)
     {
+        IDirect3DTexture9 *flipTexture = mFlipTexture;
+        flipTexture->AddRef();
+
+        IDirect3DSurface9 *renderTarget = mRenderTarget;
+        renderTarget->AddRef();
+
+        EGLint oldWidth = mWidth;
+        EGLint oldHeight = mHeight;
+
+        checkForWindowResize();
+
         IDirect3DDevice9 *device = mDisplay->getDevice();
 
         IDirect3DSurface9 *textureSurface;
-        mFlipTexture->GetSurfaceLevel(0, &textureSurface);
+        flipTexture->GetSurfaceLevel(0, &textureSurface);
 
         mDisplay->endScene();
-        device->StretchRect(mRenderTarget, NULL, textureSurface, NULL, D3DTEXF_NONE);
+        device->StretchRect(renderTarget, NULL, textureSurface, NULL, D3DTEXF_NONE);
+        renderTarget->Release();
 
-        applyFlipState(device, mFlipTexture);
+        applyFlipState(device);
+        device->SetTexture(0, flipTexture);
+
+        float xscale = (float)mWidth / oldWidth;
+        float yscale = (float)mHeight / oldHeight;
 
         // Render the texture upside down into the back buffer
-        float quad[4][6] = {{     0 - 0.5f,       0 - 0.5f, 0.0f, 1.0f, 0.0f, 1.0f},
-                            {mWidth - 0.5f,       0 - 0.5f, 0.0f, 1.0f, 1.0f, 1.0f},
-                            {mWidth - 0.5f, mHeight - 0.5f, 0.0f, 1.0f, 1.0f, 0.0f},
-                            {     0 - 0.5f, mHeight - 0.5f, 0.0f, 1.0f, 0.0f, 0.0f}};   // x, y, z, rhw, u, v
+        // Texcoords are chosen to pin a potentially resized image into the upper-left corner without scaling.
+        float quad[4][6] = {{     0 - 0.5f,       0 - 0.5f, 0.0f, 1.0f, 0.0f,   1.0f       },
+                            {mWidth - 0.5f,       0 - 0.5f, 0.0f, 1.0f, xscale, 1.0f       },
+                            {mWidth - 0.5f, mHeight - 0.5f, 0.0f, 1.0f, xscale, 1.0f-yscale},
+                            {     0 - 0.5f, mHeight - 0.5f, 0.0f, 1.0f, 0.0f,   1.0f-yscale}};   // x, y, z, rhw, u, v
 
         mDisplay->startScene();
         device->DrawPrimitiveUP(D3DPT_TRIANGLEFAN, 2, quad, 6 * sizeof(float));
 
+        flipTexture->Release();
         textureSurface->Release();
 
         restoreState(device);
@@ -264,6 +393,7 @@ bool Surface::swap()
         }
 
         ASSERT(SUCCEEDED(result));
+
     }
 
     return true;
diff --git a/ANGLE/src/libEGL/Surface.h b/ANGLE/src/libEGL/Surface.h
index 8c684a0..5bc912c 100644
--- a/ANGLE/src/libEGL/Surface.h
+++ b/ANGLE/src/libEGL/Surface.h
@@ -25,7 +25,7 @@ class Config;
 class Surface
 {
   public:
-    Surface(Display *display, IDirect3DSwapChain9 *swapChain, IDirect3DSurface9* depthStencil, const egl::Config *config);
+    Surface(Display *display, const egl::Config *config, HWND window);
 
     ~Surface();
 
@@ -42,20 +42,25 @@ class Surface
     DISALLOW_COPY_AND_ASSIGN(Surface);
 
     Display *const mDisplay;
-    IDirect3DSwapChain9 *const mSwapChain;
+    IDirect3DSwapChain9 *mSwapChain;
     IDirect3DSurface9 *mBackBuffer;
     IDirect3DSurface9 *mRenderTarget;
     IDirect3DSurface9 *mDepthStencil;
     IDirect3DTexture9 *mFlipTexture;
 
-    void applyFlipState(IDirect3DDevice9 *device, IDirect3DTexture9 *source);
+    void resetSwapChain();
+    bool checkForWindowResize();
+
+    void applyFlipState(IDirect3DDevice9 *device);
     void restoreState(IDirect3DDevice9 *device);
-    void writeRecordableFlipState(IDirect3DDevice9 *device, IDirect3DTexture9 *source);
+    void writeRecordableFlipState(IDirect3DDevice9 *device);
+    void releaseRecordedState(IDirect3DDevice9 *device);
     IDirect3DStateBlock9 *mFlipState;
     IDirect3DStateBlock9 *mPreFlipState;
     IDirect3DSurface9 *mPreFlipBackBuffer;
     IDirect3DSurface9 *mPreFlipDepthStencil;
 
+    const HWND mWindow;            // Window that the surface is created for.
     const egl::Config *mConfig;    // EGL config surface was created with
     EGLint mHeight;                // Height of surface
     EGLint mWidth;                 // Width of surface
diff --git a/ANGLE/src/libEGL/libEGL.cpp b/ANGLE/src/libEGL/libEGL.cpp
index 5c2cc1d..5ceb6ef 100644
--- a/ANGLE/src/libEGL/libEGL.cpp
+++ b/ANGLE/src/libEGL/libEGL.cpp
@@ -772,7 +772,7 @@ EGLContext __stdcall eglCreateContext(EGLDisplay dpy, EGLConfig config, EGLConte
             return EGL_NO_CONTEXT;
         }
 
-        EGLContext context = display->createContext(config);
+        EGLContext context = display->createContext(config, static_cast<gl::Context*>(share_context));
 
         return success(context);
     }
@@ -824,9 +824,8 @@ EGLBoolean __stdcall eglMakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface
         egl::Display *display = static_cast<egl::Display*>(dpy);
         gl::Context *context = static_cast<gl::Context*>(ctx);
         IDirect3DDevice9 *device = display->getDevice();
-        DWORD passes;
 
-        if (!device || device->ValidateDevice(&passes) == D3DERR_DEVICELOST)
+        if (!device || device->TestCooperativeLevel() != D3D_OK)
         {
             return error(EGL_CONTEXT_LOST, EGL_FALSE);
         }
diff --git a/ANGLE/src/libEGL/libEGL.vcproj b/ANGLE/src/libEGL/libEGL.vcproj
index 30e6183..505f4d9 100644
--- a/ANGLE/src/libEGL/libEGL.vcproj
+++ b/ANGLE/src/libEGL/libEGL.vcproj
@@ -62,7 +62,7 @@
 			/>
 			<Tool
 				Name="VCLinkerTool"
-				AdditionalDependencies="d3d9.lib"
+				AdditionalDependencies="dxguid.lib"
 				LinkIncremental="2"
 				ModuleDefinitionFile="libEGL.def"
 				GenerateDebugInformation="true"
@@ -140,7 +140,7 @@
 			/>
 			<Tool
 				Name="VCLinkerTool"
-				AdditionalDependencies="d3d9.lib"
+				AdditionalDependencies="dxguid.lib"
 				LinkIncremental="1"
 				ModuleDefinitionFile="libEGL.def"
 				GenerateDebugInformation="true"
diff --git a/ANGLE/src/libGLESv2/Blit.cpp b/ANGLE/src/libGLESv2/Blit.cpp
index 92bde05..00c878f 100644
--- a/ANGLE/src/libGLESv2/Blit.cpp
+++ b/ANGLE/src/libGLESv2/Blit.cpp
@@ -232,12 +232,12 @@ bool Blit::setShader(ShaderId source, const char *profile,
 
 bool Blit::setVertexShader(ShaderId shader)
 {
-    return setShader<IDirect3DVertexShader9>(shader, mContext->getVertexShaderProfile(), &IDirect3DDevice9::CreateVertexShader, &IDirect3DDevice9::SetVertexShader);
+    return setShader<IDirect3DVertexShader9>(shader, mContext->supportsShaderModel3() ? "vs_3_0" : "vs_2_0", &IDirect3DDevice9::CreateVertexShader, &IDirect3DDevice9::SetVertexShader);
 }
 
 bool Blit::setPixelShader(ShaderId shader)
 {
-    return setShader<IDirect3DPixelShader9>(shader, mContext->getPixelShaderProfile(), &IDirect3DDevice9::CreatePixelShader, &IDirect3DDevice9::SetPixelShader);
+    return setShader<IDirect3DPixelShader9>(shader, mContext->supportsShaderModel3() ? "ps_3_0" : "ps_2_0", &IDirect3DDevice9::CreatePixelShader, &IDirect3DDevice9::SetPixelShader);
 }
 
 RECT Blit::getSurfaceRect(IDirect3DSurface9 *surface) const
@@ -325,6 +325,7 @@ bool Blit::setFormatConvertShaders(GLenum destFormat)
     {
       default: UNREACHABLE();
       case GL_RGBA:
+      case GL_BGRA_EXT:
       case GL_RGB:
       case GL_ALPHA:
         okay = okay && setPixelShader(SHADER_PS_COMPONENTMASK);
@@ -351,6 +352,7 @@ bool Blit::setFormatConvertShaders(GLenum destFormat)
     {
       default: UNREACHABLE();
       case GL_RGBA:
+      case GL_BGRA_EXT:
         psConst0[X] = 1;
         psConst0[Z] = 1;
         break;
diff --git a/ANGLE/src/libGLESv2/Buffer.cpp b/ANGLE/src/libGLESv2/Buffer.cpp
index 87d4185..43993e7 100644
--- a/ANGLE/src/libGLESv2/Buffer.cpp
+++ b/ANGLE/src/libGLESv2/Buffer.cpp
@@ -13,7 +13,7 @@
 namespace gl
 {
 
-Buffer::Buffer()
+Buffer::Buffer(GLuint id) : RefCountObject(id)
 {
     mContents = NULL;
     mSize = 0;
diff --git a/ANGLE/src/libGLESv2/Buffer.h b/ANGLE/src/libGLESv2/Buffer.h
index 5fe0d75..5611cc9 100644
--- a/ANGLE/src/libGLESv2/Buffer.h
+++ b/ANGLE/src/libGLESv2/Buffer.h
@@ -18,14 +18,15 @@
 #include <GLES2/gl2.h>
 
 #include "common/angleutils.h"
+#include "libGLESv2/RefCountObject.h"
 
 namespace gl
 {
 
-class Buffer
+class Buffer : public RefCountObject
 {
   public:
-    Buffer();
+    explicit Buffer(GLuint id);
 
     virtual ~Buffer();
 
diff --git a/ANGLE/src/libGLESv2/Context.cpp b/ANGLE/src/libGLESv2/Context.cpp
index 55a83ff..48ef8fc 100644
--- a/ANGLE/src/libGLESv2/Context.cpp
+++ b/ANGLE/src/libGLESv2/Context.cpp
@@ -17,6 +17,7 @@
 #include "libGLESv2/mathutil.h"
 #include "libGLESv2/utilities.h"
 #include "libGLESv2/Blit.h"
+#include "libGLESv2/ResourceManager.h"
 #include "libGLESv2/Buffer.h"
 #include "libGLESv2/FrameBuffer.h"
 #include "libGLESv2/Program.h"
@@ -33,7 +34,7 @@
 
 namespace gl
 {
-Context::Context(const egl::Config *config)
+Context::Context(const egl::Config *config, const gl::Context *shareContext)
     : mConfig(config)
 {
     setClearColor(0.0f, 0.0f, 0.0f, 0.0f);
@@ -103,37 +104,39 @@ Context::Context(const egl::Config *config)
     mState.colorMaskAlpha = true;
     mState.depthMask = true;
 
+    if (shareContext != NULL)
+    {
+        mResourceManager = shareContext->mResourceManager;
+        mResourceManager->addRef();
+    }
+    else
+    {
+        mResourceManager = new ResourceManager();
+    }
+
     // [OpenGL ES 2.0.24] section 3.7 page 83:
     // In the initial state, TEXTURE_2D and TEXTURE_CUBE_MAP have twodimensional
     // and cube map texture state vectors respectively associated with them.
     // In order that access to these initial textures not be lost, they are treated as texture
     // objects all of whose names are 0.
 
-    mTexture2DZero = new Texture2D(this);
-    mTextureCubeMapZero = new TextureCubeMap(this);
+    mTexture2DZero = new Texture2D(0);
+    mTextureCubeMapZero = new TextureCubeMap(0);
 
     mColorbufferZero = NULL;
-    mDepthbufferZero = NULL;
-    mStencilbufferZero = NULL;
+    mDepthStencilbufferZero = NULL;
 
     mState.activeSampler = 0;
-    mState.arrayBuffer = 0;
-    mState.elementArrayBuffer = 0;
+    bindArrayBuffer(0);
+    bindElementArrayBuffer(0);
     bindTextureCubeMap(0);
     bindTexture2D(0);
-    bindFramebuffer(0);
+    bindReadFramebuffer(0);
+    bindDrawFramebuffer(0);
     bindRenderbuffer(0);
 
     for (int type = 0; type < SAMPLER_TYPE_COUNT; type++)
     {
-        for (int sampler = 0; sampler < MAX_TEXTURE_IMAGE_UNITS; sampler++)
-        {
-            mState.samplerTexture[type][sampler] = 0;
-        }
-    }
-
-    for (int type = 0; type < SAMPLER_TYPE_COUNT; type++)
-    {
         mIncompleteTextures[type] = NULL;
     }
 
@@ -155,65 +158,72 @@ Context::Context(const egl::Config *config)
 
     mHasBeenCurrent = false;
 
+    mMaxSupportedSamples = 0;
     mMaskedClearSavedState = NULL;
     markAllStateDirty();
 }
 
 Context::~Context()
 {
-    mState.currentProgram = 0;
-
-    for (int type = 0; type < SAMPLER_TYPE_COUNT; type++)
+    if (mState.currentProgram != 0)
     {
-        delete mIncompleteTextures[type];
+        Program *programObject = mResourceManager->getProgram(mState.currentProgram);
+        if (programObject)
+        {
+            programObject->release();
+        }
+        mState.currentProgram = 0;
     }
 
-    delete mTexture2DZero;
-    delete mTextureCubeMapZero;
-
-    delete mColorbufferZero;
-    delete mDepthbufferZero;
-    delete mStencilbufferZero;
-
-    delete mBufferBackEnd;
-    delete mVertexDataManager;
-    delete mIndexDataManager;
-    delete mBlit;
-
-    while (!mBufferMap.empty())
+    while (!mFramebufferMap.empty())
     {
-        deleteBuffer(mBufferMap.begin()->first);
+        deleteFramebuffer(mFramebufferMap.begin()->first);
     }
 
-    while (!mProgramMap.empty())
+    while (!mMultiSampleSupport.empty())
     {
-        deleteProgram(mProgramMap.begin()->first);
+        delete [] mMultiSampleSupport.begin()->second;
+        mMultiSampleSupport.erase(mMultiSampleSupport.begin());
     }
 
-    while (!mShaderMap.empty())
+    for (int type = 0; type < SAMPLER_TYPE_COUNT; type++)
     {
-        deleteShader(mShaderMap.begin()->first);
+        for (int sampler = 0; sampler < MAX_TEXTURE_IMAGE_UNITS; sampler++)
+        {
+            mState.samplerTexture[type][sampler].set(NULL);
+        }
     }
 
-    while (!mFramebufferMap.empty())
+    for (int type = 0; type < SAMPLER_TYPE_COUNT; type++)
     {
-        deleteFramebuffer(mFramebufferMap.begin()->first);
+        delete mIncompleteTextures[type];
     }
 
-    while (!mRenderbufferMap.empty())
+    for (int i = 0; i < MAX_VERTEX_ATTRIBS; i++)
     {
-        deleteRenderbuffer(mRenderbufferMap.begin()->first);
+        mState.vertexAttribute[i].mBoundBuffer.set(NULL);
     }
 
-    while (!mTextureMap.empty())
-    {
-        deleteTexture(mTextureMap.begin()->first);
-    }
+    mState.arrayBuffer.set(NULL);
+    mState.elementArrayBuffer.set(NULL);
+    mState.texture2D.set(NULL);
+    mState.textureCubeMap.set(NULL);
+    mState.renderbuffer.set(NULL);
+
+    delete mTexture2DZero;
+    delete mTextureCubeMapZero;
+
+    delete mBufferBackEnd;
+    delete mVertexDataManager;
+    delete mIndexDataManager;
+    delete mBlit;
 
     if (mMaskedClearSavedState)
     {
         mMaskedClearSavedState->Release();
     }
+
+    mResourceManager->release();
 }
 
 void Context::makeCurrent(egl::Display *display, egl::Surface *surface)
@@ -229,6 +239,34 @@ void Context::makeCurrent(egl::Display *display, egl::Surface *surface)
         mIndexDataManager = new IndexDataManager(this, mBufferBackEnd);
         mBlit = new Blit(this);
 
+        const D3DFORMAT renderBufferFormats[] =
+        {
+            D3DFMT_A8R8G8B8,
+            D3DFMT_X8R8G8B8,
+            D3DFMT_R5G6B5,
+            D3DFMT_D24S8
+        };
+
+        int max = 0;
+        for (int i = 0; i < sizeof(renderBufferFormats) / sizeof(D3DFORMAT); ++i)
+        {
+            bool *multisampleArray = new bool[D3DMULTISAMPLE_16_SAMPLES + 1];
+            display->getMultiSampleSupport(renderBufferFormats[i], multisampleArray);
+            mMultiSampleSupport[renderBufferFormats[i]] = multisampleArray;
+
+            for (int j = D3DMULTISAMPLE_16_SAMPLES; j >= 0; --j)
+            {
+                if (multisampleArray[j] && j != D3DMULTISAMPLE_NONMASKABLE && j > max)
+                {
+                    max = j;
+                }
+            }
+        }
+
+        mMaxSupportedSamples = max;
+
+        mSupportsCompressedTextures = display->getCompressedTextureSupport();
+
         initExtensionString();
 
         mState.viewportX = 0;
@@ -248,19 +286,11 @@ void Context::makeCurrent(egl::Display *display, egl::Surface *surface)
     IDirect3DSurface9 *defaultRenderTarget = surface->getRenderTarget();
     IDirect3DSurface9 *depthStencil = surface->getDepthStencil();
 
-    Framebuffer *framebufferZero = new Framebuffer();
     Colorbuffer *colorbufferZero = new Colorbuffer(defaultRenderTarget);
-    Depthbuffer *depthbufferZero = new Depthbuffer(depthStencil);
-    Stencilbuffer *stencilbufferZero = new Stencilbuffer(depthStencil);
+    DepthStencilbuffer *depthStencilbufferZero = new DepthStencilbuffer(depthStencil);
+    Framebuffer *framebufferZero = new DefaultFramebuffer(colorbufferZero, depthStencilbufferZero);
 
     setFramebufferZero(framebufferZero);
-    setColorbufferZero(colorbufferZero);
-    setDepthbufferZero(depthbufferZero);
-    setStencilbufferZero(stencilbufferZero);
-
-    framebufferZero->setColorbuffer(GL_RENDERBUFFER, 0);
-    framebufferZero->setDepthbuffer(GL_RENDERBUFFER, 0);
-    framebufferZero->setStencilbuffer(GL_RENDERBUFFER, 0);
 
     defaultRenderTarget->Release();
 
@@ -269,16 +299,7 @@ void Context::makeCurrent(egl::Display *display, egl::Surface *surface)
         depthStencil->Release();
     }
     
-    if (mDeviceCaps.PixelShaderVersion == D3DPS_VERSION(3, 0))
-    {
-        mPsProfile = "ps_3_0";
-        mVsProfile = "vs_3_0";
-    }
-    else  // egl::Display guarantees support for at least 2.0
-    {
-        mPsProfile = "ps_2_0";
-        mVsProfile = "vs_2_0";
-    }
+    mSupportsShaderModel3 = mDeviceCaps.PixelShaderVersion == D3DPS_VERSION(3, 0);
 
     markAllStateDirty();
 }
@@ -300,6 +321,12 @@ void Context::markAllStateDirty()
     mScissorStateDirty = true;
     mSampleStateDirty = true;
     mDitherStateDirty = true;
+    mFrontFaceDirty = true;
+
+    if (mBufferBackEnd != NULL)
+    {
+        mBufferBackEnd->invalidate();
+    }
 }
 
 void Context::setClearColor(float red, float green, float blue, float alpha)
@@ -671,19 +698,24 @@ void Context::setActiveSampler(int active)
     mState.activeSampler = active;
 }
 
-GLuint Context::getFramebufferHandle() const
+GLuint Context::getReadFramebufferHandle() const
 {
-    return mState.framebuffer;
+    return mState.readFramebuffer;
+}
+
+GLuint Context::getDrawFramebufferHandle() const
+{
+    return mState.drawFramebuffer;
 }
 
 GLuint Context::getRenderbufferHandle() const
 {
-    return mState.renderbuffer;
+    return mState.renderbuffer.id();
 }
 
 GLuint Context::getArrayBufferHandle() const
 {
-    return mState.arrayBuffer;
+    return mState.arrayBuffer.id();
 }
 
 void Context::setVertexAttribEnabled(unsigned int attribNum, bool enabled)
@@ -696,10 +728,10 @@ const AttributeState &Context::getVertexAttribState(unsigned int attribNum)
     return mState.vertexAttribute[attribNum];
 }
 
-void Context::setVertexAttribState(unsigned int attribNum, GLuint boundBuffer, GLint size, GLenum type, bool normalized,
+void Context::setVertexAttribState(unsigned int attribNum, Buffer *boundBuffer, GLint size, GLenum type, bool normalized,
                                    GLsizei stride, const void *pointer)
 {
-    mState.vertexAttribute[attribNum].mBoundBuffer = boundBuffer;
+    mState.vertexAttribute[attribNum].mBoundBuffer.set(boundBuffer);
     mState.vertexAttribute[attribNum].mSize = size;
     mState.vertexAttribute[attribNum].mType = type;
     mState.vertexAttribute[attribNum].mNormalized = normalized;
@@ -738,72 +770,29 @@ GLint Context::getUnpackAlignment() const
     return mState.unpackAlignment;
 }
 
-// Returns an unused buffer name
 GLuint Context::createBuffer()
 {
-    unsigned int handle = 1;
-
-    while (mBufferMap.find(handle) != mBufferMap.end())
-    {
-        handle++;
-    }
-
-    mBufferMap[handle] = NULL;
-
-    return handle;
+    return mResourceManager->createBuffer();
 }
 
-// Returns an unused shader/program name
-GLuint Context::createShader(GLenum type)
+GLuint Context::createProgram()
 {
-    unsigned int handle = 1;
-
-    while (mShaderMap.find(handle) != mShaderMap.end() || mProgramMap.find(handle) != mProgramMap.end())   // Shared name space
-    {
-        handle++;
-    }
-
-    if (type == GL_VERTEX_SHADER)
-    {
-        mShaderMap[handle] = new VertexShader(this, handle);
-    }
-    else if (type == GL_FRAGMENT_SHADER)
-    {
-        mShaderMap[handle] = new FragmentShader(this, handle);
-    }
-    else UNREACHABLE();
-
-    return handle;
+    return mResourceManager->createProgram();
 }
 
-// Returns an unused program/shader name
-GLuint Context::createProgram()
+GLuint Context::createShader(GLenum type)
 {
-    unsigned int handle = 1;
-
-    while (mProgramMap.find(handle) != mProgramMap.end() || mShaderMap.find(handle) != mShaderMap.end())   // Shared name space
-    {
-        handle++;
-    }
-
-    mProgramMap[handle] = new Program();
-
-    return handle;
+    return mResourceManager->createShader(type);
 }
 
-// Returns an unused texture name
 GLuint Context::createTexture()
 {
-    unsigned int handle = 1;
-
-    while (mTextureMap.find(handle) != mTextureMap.end())
-    {
-        handle++;
-    }
-
-    mTextureMap[handle] = NULL;
+    return mResourceManager->createTexture();
+}
 
-    return handle;
+GLuint Context::createRenderbuffer()
+{
+    return mResourceManager->createRenderbuffer();
 }
 
 // Returns an unused framebuffer name
@@ -821,85 +810,44 @@ GLuint Context::createFramebuffer()
     return handle;
 }
 
-// Returns an unused renderbuffer name
-GLuint Context::createRenderbuffer()
-{
-    unsigned int handle = 1;
-
-    while (mRenderbufferMap.find(handle) != mRenderbufferMap.end())
-    {
-        handle++;
-    }
-
-    mRenderbufferMap[handle] = NULL;
-
-    return handle;
-}
-
 void Context::deleteBuffer(GLuint buffer)
 {
-    BufferMap::iterator bufferObject = mBufferMap.find(buffer);
-
-    if (bufferObject != mBufferMap.end())
+    if (mResourceManager->getBuffer(buffer))
     {
         detachBuffer(buffer);
-
-        delete bufferObject->second;
-        mBufferMap.erase(bufferObject);
     }
+    
+    mResourceManager->deleteBuffer(buffer);
 }
 
 void Context::deleteShader(GLuint shader)
 {
-    ShaderMap::iterator shaderObject = mShaderMap.find(shader);
-
-    if (shaderObject != mShaderMap.end())
-    {
-        if (!shaderObject->second->isAttached())
-        {
-            delete shaderObject->second;
-            mShaderMap.erase(shaderObject);
-        }
-        else
-        {
-            shaderObject->second->flagForDeletion();
-        }
-    }
+    mResourceManager->deleteShader(shader);
 }
 
 void Context::deleteProgram(GLuint program)
 {
-    ProgramMap::iterator programObject = mProgramMap.find(program);
-
-    if (programObject != mProgramMap.end())
-    {
-        if (program != mState.currentProgram)
-        {
-            delete programObject->second;
-            mProgramMap.erase(programObject);
-        }
-        else
-        {
-            programObject->second->flagForDeletion();
-        }
-    }
+    mResourceManager->deleteProgram(program);
 }
 
 void Context::deleteTexture(GLuint texture)
 {
-    TextureMap::iterator textureObject = mTextureMap.find(texture);
-
-    if (textureObject != mTextureMap.end())
+    if (mResourceManager->getTexture(texture))
     {
         detachTexture(texture);
+    }
 
-        if (texture != 0)
-        {
-            delete textureObject->second;
-        }
+    mResourceManager->deleteTexture(texture);
+}
 
-        mTextureMap.erase(textureObject);
+void Context::deleteRenderbuffer(GLuint renderbuffer)
+{
+    if (mResourceManager->getRenderbuffer(renderbuffer))
+    {
+        detachRenderbuffer(renderbuffer);
     }
+    
+    mResourceManager->deleteRenderbuffer(renderbuffer);
 }
 
 void Context::deleteFramebuffer(GLuint framebuffer)
@@ -915,307 +863,186 @@ void Context::deleteFramebuffer(GLuint framebuffer)
     }
 }
 
-void Context::deleteRenderbuffer(GLuint renderbuffer)
+Buffer *Context::getBuffer(GLuint handle)
 {
-    RenderbufferMap::iterator renderbufferObject = mRenderbufferMap.find(renderbuffer);
-
-    if (renderbufferObject != mRenderbufferMap.end())
-    {
-        detachRenderbuffer(renderbuffer);
-
-        delete renderbufferObject->second;
-        mRenderbufferMap.erase(renderbufferObject);
-    }
+    return mResourceManager->getBuffer(handle);
 }
 
-void Context::bindArrayBuffer(unsigned int buffer)
+Shader *Context::getShader(GLuint handle)
 {
-    if (buffer != 0 && !getBuffer(buffer))
-    {
-        mBufferMap[buffer] = new Buffer();
-    }
-
-    mState.arrayBuffer = buffer;
+    return mResourceManager->getShader(handle);
 }
 
-void Context::bindElementArrayBuffer(unsigned int buffer)
+Program *Context::getProgram(GLuint handle)
 {
-    if (buffer != 0 && !getBuffer(buffer))
-    {
-        mBufferMap[buffer] = new Buffer();
-    }
-
-    mState.elementArrayBuffer = buffer;
+    return mResourceManager->getProgram(handle);
 }
 
-void Context::bindTexture2D(GLuint texture)
+Texture *Context::getTexture(GLuint handle)
 {
-    if (!getTexture(texture) && texture != 0)
-    {
-        mTextureMap[texture] = new Texture2D(this);
-    }
-
-    mState.texture2D = texture;
-
-    mState.samplerTexture[SAMPLER_2D][mState.activeSampler] = texture;
+    return mResourceManager->getTexture(handle);
 }
 
-void Context::bindTextureCubeMap(GLuint texture)
+Renderbuffer *Context::getRenderbuffer(GLuint handle)
 {
-    if (!getTexture(texture) && texture != 0)
-    {
-        mTextureMap[texture] = new TextureCubeMap(this);
-    }
-
-    mState.textureCubeMap = texture;
-
-    mState.samplerTexture[SAMPLER_CUBE][mState.activeSampler] = texture;
+    return mResourceManager->getRenderbuffer(handle);
 }
 
-void Context::bindFramebuffer(GLuint framebuffer)
+Framebuffer *Context::getReadFramebuffer()
 {
-    if (!getFramebuffer(framebuffer))
-    {
-        mFramebufferMap[framebuffer] = new Framebuffer();
-    }
-
-    mState.framebuffer = framebuffer;
+    return getFramebuffer(mState.readFramebuffer);
 }
 
-void Context::bindRenderbuffer(GLuint renderbuffer)
+Framebuffer *Context::getDrawFramebuffer()
 {
-    if (renderbuffer != 0 && !getRenderbuffer(renderbuffer))
-    {
-        mRenderbufferMap[renderbuffer] = new Renderbuffer();
-    }
-
-    mState.renderbuffer = renderbuffer;
+    return getFramebuffer(mState.drawFramebuffer);
 }
 
-void Context::useProgram(GLuint program)
+void Context::bindArrayBuffer(unsigned int buffer)
 {
-    Program *programObject = getCurrentProgram();
-
-    GLuint priorProgram = mState.currentProgram;
-    mState.currentProgram = program;               // Must switch before trying to delete, otherwise it only gets flagged.
+    mResourceManager->checkBufferAllocation(buffer);
 
-    if (programObject && programObject->isFlaggedForDeletion())
-    {
-        deleteProgram(priorProgram);
-    }
+    mState.arrayBuffer.set(getBuffer(buffer));
 }
 
-void Context::setFramebufferZero(Framebuffer *buffer)
+void Context::bindElementArrayBuffer(unsigned int buffer)
 {
-    delete mFramebufferMap[0];
-    mFramebufferMap[0] = buffer;
-}
+    mResourceManager->checkBufferAllocation(buffer);
 
-void Context::setColorbufferZero(Colorbuffer *buffer)
-{
-    delete mColorbufferZero;
-    mColorbufferZero = buffer;
+    mState.elementArrayBuffer.set(getBuffer(buffer));
 }
 
-void Context::setDepthbufferZero(Depthbuffer *buffer)
+void Context::bindTexture2D(GLuint texture)
 {
-    delete mDepthbufferZero;
-    mDepthbufferZero = buffer;
-}
+    mResourceManager->checkTextureAllocation(texture, SAMPLER_2D);
 
-void Context::setStencilbufferZero(Stencilbuffer *buffer)
-{
-    delete mStencilbufferZero;
-    mStencilbufferZero = buffer;
-}
+    mState.texture2D.set(getTexture(texture));
 
-void Context::setRenderbuffer(Renderbuffer *buffer)
-{
-    delete mRenderbufferMap[mState.renderbuffer];
-    mRenderbufferMap[mState.renderbuffer] = buffer;
+    mState.samplerTexture[SAMPLER_2D][mState.activeSampler].set(mState.texture2D.get());
 }
 
-Buffer *Context::getBuffer(unsigned int handle)
+void Context::bindTextureCubeMap(GLuint texture)
 {
-    BufferMap::iterator buffer = mBufferMap.find(handle);
+    mResourceManager->checkTextureAllocation(texture, SAMPLER_CUBE);
 
-    if (buffer == mBufferMap.end())
-    {
-        return NULL;
-    }
-    else
-    {
-        return buffer->second;
-    }
-}
+    mState.textureCubeMap.set(getTexture(texture));
 
-Shader *Context::getShader(unsigned int handle)
-{
-    ShaderMap::iterator shader = mShaderMap.find(handle);
-
-    if (shader == mShaderMap.end())
-    {
-        return NULL;
-    }
-    else
-    {
-        return shader->second;
-    }
+    mState.samplerTexture[SAMPLER_CUBE][mState.activeSampler].set(mState.textureCubeMap.get());
 }
 
-Program *Context::getProgram(unsigned int handle)
+void Context::bindReadFramebuffer(GLuint framebuffer)
 {
-    ProgramMap::iterator program = mProgramMap.find(handle);
-
-    if (program == mProgramMap.end())
-    {
-        return NULL;
-    }
-    else
+    if (!getFramebuffer(framebuffer))
     {
-        return program->second;
+        mFramebufferMap[framebuffer] = new Framebuffer();
     }
-}
-
-Texture *Context::getTexture(unsigned int handle)
-{
-    if (handle == 0) return NULL;
-
-    TextureMap::iterator texture = mTextureMap.find(handle);
 
-    if (texture == mTextureMap.end())
-    {
-        return NULL;
-    }
-    else
-    {
-        return texture->second;
-    }
+    mState.readFramebuffer = framebuffer;
 }
 
-Framebuffer *Context::getFramebuffer(unsigned int handle)
+void Context::bindDrawFramebuffer(GLuint framebuffer)
 {
-    FramebufferMap::iterator framebuffer = mFramebufferMap.find(handle);
-
-    if (framebuffer == mFramebufferMap.end())
-    {
-        return NULL;
-    }
-    else
+    if (!getFramebuffer(framebuffer))
     {
-        return framebuffer->second;
+        mFramebufferMap[framebuffer] = new Framebuffer();
     }
+
+    mState.drawFramebuffer = framebuffer;
 }
 
-Renderbuffer *Context::getRenderbuffer(unsigned int handle)
+void Context::bindRenderbuffer(GLuint renderbuffer)
 {
-    RenderbufferMap::iterator renderbuffer = mRenderbufferMap.find(handle);
+    mResourceManager->checkRenderbufferAllocation(renderbuffer);
 
-    if (renderbuffer == mRenderbufferMap.end())
-    {
-        return NULL;
-    }
-    else
-    {
-        return renderbuffer->second;
-    }
+    mState.renderbuffer.set(getRenderbuffer(renderbuffer));
 }
 
-Colorbuffer *Context::getColorbuffer(GLuint handle)
+void Context::useProgram(GLuint program)
 {
-    if (handle != 0)
+    GLuint priorProgram = mState.currentProgram;
+    mState.currentProgram = program;               // Must switch before trying to delete, otherwise it only gets flagged.
+
+    if (priorProgram != program)
     {
-        Renderbuffer *renderbuffer = getRenderbuffer(handle);
+        Program *newProgram = mResourceManager->getProgram(program);
+        Program *oldProgram = mResourceManager->getProgram(priorProgram);
 
-        if (renderbuffer && renderbuffer->isColorbuffer())
+        if (newProgram)
         {
-            return static_cast<Colorbuffer*>(renderbuffer);
+            newProgram->addRef();
+        }
+        
+        if (oldProgram)
+        {
+            oldProgram->release();
         }
     }
-    else   // Special case: 0 refers to different initial render targets based on the attachment type
-    {
-        return mColorbufferZero;
-    }
-
-    return NULL;
 }
 
-Depthbuffer *Context::getDepthbuffer(GLuint handle)
+void Context::setFramebufferZero(Framebuffer *buffer)
 {
-    if (handle != 0)
-    {
-        Renderbuffer *renderbuffer = getRenderbuffer(handle);
-
-        if (renderbuffer && renderbuffer->isDepthbuffer())
-        {
-            return static_cast<Depthbuffer*>(renderbuffer);
-        }
-    }
-    else   // Special case: 0 refers to different initial render targets based on the attachment type
-    {
-        return mDepthbufferZero;
-    }
+    delete mFramebufferMap[0];
+    mFramebufferMap[0] = buffer;
+}
 
-    return NULL;
+void Context::setRenderbufferStorage(RenderbufferStorage *renderbuffer)
+{
+    Renderbuffer *renderbufferObject = mState.renderbuffer.get();
+    renderbufferObject->setStorage(renderbuffer);
 }
 
-Stencilbuffer *Context::getStencilbuffer(GLuint handle)
+Framebuffer *Context::getFramebuffer(unsigned int handle)
 {
-    if (handle != 0)
-    {
-        Renderbuffer *renderbuffer = getRenderbuffer(handle);
+    FramebufferMap::iterator framebuffer = mFramebufferMap.find(handle);
 
-        if (renderbuffer && renderbuffer->isStencilbuffer())
-        {
-            return static_cast<Stencilbuffer*>(renderbuffer);
-        }
+    if (framebuffer == mFramebufferMap.end())
+    {
+        return NULL;
     }
     else
     {
-        return mStencilbufferZero;
+        return framebuffer->second;
     }
-
-    return NULL;
 }
 
 Buffer *Context::getArrayBuffer()
 {
-    return getBuffer(mState.arrayBuffer);
+    return mState.arrayBuffer.get();
 }
 
 Buffer *Context::getElementArrayBuffer()
 {
-    return getBuffer(mState.elementArrayBuffer);
+    return mState.elementArrayBuffer.get();
 }
 
 Program *Context::getCurrentProgram()
 {
-    return getProgram(mState.currentProgram);
+    return mResourceManager->getProgram(mState.currentProgram);
 }
 
 Texture2D *Context::getTexture2D()
 {
-    if (mState.texture2D == 0)   // Special case: 0 refers to different initial textures based on the target
+    if (mState.texture2D.id() == 0)   // Special case: 0 refers to different initial textures based on the target
     {
         return mTexture2DZero;
     }
 
-    return (Texture2D*)getTexture(mState.texture2D);
+    return static_cast<Texture2D*>(mState.texture2D.get());
 }
 
 TextureCubeMap *Context::getTextureCubeMap()
 {
-    if (mState.textureCubeMap == 0)   // Special case: 0 refers to different initial textures based on the target
+    if (mState.textureCubeMap.id() == 0)   // Special case: 0 refers to different initial textures based on the target
     {
         return mTextureCubeMapZero;
     }
 
-    return (TextureCubeMap*)getTexture(mState.textureCubeMap);
+    return static_cast<TextureCubeMap*>(mState.textureCubeMap.get());
 }
 
 Texture *Context::getSamplerTexture(unsigned int sampler, SamplerType type)
 {
-    GLuint texid = mState.samplerTexture[type][sampler];
+    GLuint texid = mState.samplerTexture[type][sampler].id();
 
     if (texid == 0)
     {
@@ -1227,12 +1054,7 @@ Texture *Context::getSamplerTexture(unsigned int sampler, SamplerType type)
         }
     }
 
-    return getTexture(texid);
-}
-
-Framebuffer *Context::getFramebuffer()
-{
-    return getFramebuffer(mState.framebuffer);
+    return mState.samplerTexture[type][sampler].get();
 }
 
 bool Context::getBooleanv(GLenum pname, GLboolean *params)
@@ -1283,7 +1105,7 @@ bool Context::getFloatv(GLenum pname, GLfloat *params)
         break;
       case GL_ALIASED_POINT_SIZE_RANGE:
         params[0] = gl::ALIASED_POINT_SIZE_RANGE_MIN;
-        params[1] = gl::ALIASED_POINT_SIZE_RANGE_MAX;
+        params[1] = supportsShaderModel3() ? gl::ALIASED_POINT_SIZE_RANGE_MAX_SM3 : gl::ALIASED_POINT_SIZE_RANGE_MAX_SM2;
         break;
       case GL_DEPTH_RANGE:
         params[0] = mState.zNear;
@@ -1326,13 +1148,13 @@ bool Context::getIntegerv(GLenum pname, GLint *params)
       case GL_MAX_FRAGMENT_UNIFORM_VECTORS:     *params = gl::MAX_FRAGMENT_UNIFORM_VECTORS;     break;
       case GL_MAX_RENDERBUFFER_SIZE:            *params = gl::MAX_RENDERBUFFER_SIZE;            break;
       case GL_NUM_SHADER_BINARY_FORMATS:        *params = 0;                                    break;
-      case GL_NUM_COMPRESSED_TEXTURE_FORMATS:   *params = 0;                                    break;
-      case GL_COMPRESSED_TEXTURE_FORMATS: /* no compressed texture formats are supported */     break;
       case GL_SHADER_BINARY_FORMATS:      /* no shader binary formats are supported */          break;
-      case GL_ARRAY_BUFFER_BINDING:             *params = mState.arrayBuffer;                   break;
-      case GL_ELEMENT_ARRAY_BUFFER_BINDING:     *params = mState.elementArrayBuffer;            break;
-      case GL_FRAMEBUFFER_BINDING:              *params = mState.framebuffer;                   break;
-      case GL_RENDERBUFFER_BINDING:             *params = mState.renderbuffer;                  break;
+      case GL_ARRAY_BUFFER_BINDING:             *params = mState.arrayBuffer.id();              break;
+      case GL_ELEMENT_ARRAY_BUFFER_BINDING:     *params = mState.elementArrayBuffer.id();       break;
+      //case GL_FRAMEBUFFER_BINDING:              // now equivalent to GL_DRAW_FRAMEBUFFER_BINDING_ANGLE
+      case GL_DRAW_FRAMEBUFFER_BINDING_ANGLE:     *params = mState.drawFramebuffer;               break;
+      case GL_READ_FRAMEBUFFER_BINDING_ANGLE:     *params = mState.readFramebuffer;               break;
+      case GL_RENDERBUFFER_BINDING:             *params = mState.renderbuffer.id();             break;
       case GL_CURRENT_PROGRAM:                  *params = mState.currentProgram;                break;
       case GL_PACK_ALIGNMENT:                   *params = mState.packAlignment;                 break;
       case GL_UNPACK_ALIGNMENT:                 *params = mState.unpackAlignment;               break;
@@ -1363,8 +1185,63 @@ bool Context::getIntegerv(GLenum pname, GLint *params)
       case GL_SUBPIXEL_BITS:                    *params = 4;                                    break;
       case GL_MAX_TEXTURE_SIZE:                 *params = gl::MAX_TEXTURE_SIZE;                 break;
       case GL_MAX_CUBE_MAP_TEXTURE_SIZE:        *params = gl::MAX_CUBE_MAP_TEXTURE_SIZE;        break;
-      case GL_SAMPLE_BUFFERS:                   *params = 0;                                    break;
-      case GL_SAMPLES:                          *params = 0;                                    break;
+      case GL_NUM_COMPRESSED_TEXTURE_FORMATS:   
+        {
+            if (supportsCompressedTextures())
+            {
+                // at current, only GL_COMPRESSED_RGB_S3TC_DXT1_EXT and 
+                // GL_COMPRESSED_RGBA_S3TC_DXT1_EXT are supported
+                *params = 2;
+            }
+            else
+            {
+                *params = 0;
+            }
+        }
+        break;
+      case GL_MAX_SAMPLES_ANGLE:
+        {
+            GLsizei maxSamples = getMaxSupportedSamples();
+            if (maxSamples != 0)
+            {
+                *params = maxSamples;
+            }
+            else
+            {
+                return false;
+            }
+
+            break;
+        }
+      case GL_SAMPLE_BUFFERS:                   
+      case GL_SAMPLES:
+        {
+            gl::Framebuffer *framebuffer = getDrawFramebuffer();
+            if (framebuffer->completeness() == GL_FRAMEBUFFER_COMPLETE)
+            {
+                switch (pname)
+                {
+                  case GL_SAMPLE_BUFFERS:
+                    if (framebuffer->getSamples() != 0)
+                    {
+                        *params = 1;
+                    }
+                    else
+                    {
+                        *params = 0;
+                    }
+                    break;
+                  case GL_SAMPLES:
+                    *params = framebuffer->getSamples();
+                    break;
+                }
+            }
+            else 
+            {
+                *params = 0;
+            }
+        }
+        break;
       case GL_IMPLEMENTATION_COLOR_READ_TYPE:   *params = gl::IMPLEMENTATION_COLOR_READ_TYPE;   break;
       case GL_IMPLEMENTATION_COLOR_READ_FORMAT: *params = gl::IMPLEMENTATION_COLOR_READ_FORMAT; break;
       case GL_MAX_VIEWPORT_DIMS:
@@ -1374,6 +1251,15 @@ bool Context::getIntegerv(GLenum pname, GLint *params)
             params[1] = maxDimension;
         }
         break;
+      case GL_COMPRESSED_TEXTURE_FORMATS:
+        {
+            if (supportsCompressedTextures())
+            {
+                params[0] = GL_COMPRESSED_RGB_S3TC_DXT1_EXT;
+                params[1] = GL_COMPRESSED_RGBA_S3TC_DXT1_EXT;
+            }
+        }
+        break;
       case GL_VIEWPORT:
         params[0] = mState.viewportX;
         params[1] = mState.viewportY;
@@ -1393,7 +1279,7 @@ bool Context::getIntegerv(GLenum pname, GLint *params)
       case GL_BLUE_BITS:
       case GL_ALPHA_BITS:
         {
-            gl::Framebuffer *framebuffer = getFramebuffer();
+            gl::Framebuffer *framebuffer = getDrawFramebuffer();
             gl::Colorbuffer *colorbuffer = framebuffer->getColorbuffer();
 
             if (colorbuffer)
@@ -1414,8 +1300,8 @@ bool Context::getIntegerv(GLenum pname, GLint *params)
         break;
       case GL_DEPTH_BITS:
         {
-            gl::Framebuffer *framebuffer = getFramebuffer();
-            gl::Depthbuffer *depthbuffer = framebuffer->getDepthbuffer();
+            gl::Framebuffer *framebuffer = getDrawFramebuffer();
+            gl::DepthStencilbuffer *depthbuffer = framebuffer->getDepthbuffer();
 
             if (depthbuffer)
             {
@@ -1429,8 +1315,8 @@ bool Context::getIntegerv(GLenum pname, GLint *params)
         break;
       case GL_STENCIL_BITS:
         {
-            gl::Framebuffer *framebuffer = getFramebuffer();
-            gl::Stencilbuffer *stencilbuffer = framebuffer->getStencilbuffer();
+            gl::Framebuffer *framebuffer = getDrawFramebuffer();
+            gl::DepthStencilbuffer *stencilbuffer = framebuffer->getStencilbuffer();
 
             if (stencilbuffer)
             {
@@ -1450,7 +1336,7 @@ bool Context::getIntegerv(GLenum pname, GLint *params)
                 return false;
             }
 
-            *params = mState.samplerTexture[SAMPLER_2D][mState.activeSampler];
+            *params = mState.samplerTexture[SAMPLER_2D][mState.activeSampler].id();
         }
         break;
       case GL_TEXTURE_BINDING_CUBE_MAP:
@@ -1461,7 +1347,7 @@ bool Context::getIntegerv(GLenum pname, GLint *params)
                 return false;
             }
 
-            *params = mState.samplerTexture[SAMPLER_CUBE][mState.activeSampler];
+            *params = mState.samplerTexture[SAMPLER_CUBE][mState.activeSampler].id();
         }
         break;
       default:
@@ -1552,6 +1438,19 @@ bool Context::getQueryParameterInfo(GLenum pname, GLenum *type, unsigned int *nu
             *numParams = 1;
         }
         break;
+      case GL_MAX_SAMPLES_ANGLE:
+        {
+            if (getMaxSupportedSamples() != 0)
+            {
+                *type = GL_INT;
+                *numParams = 1;
+            }
+            else
+            {
+                return false;
+            }
+        }
+        break;
       case GL_MAX_VIEWPORT_DIMS:
         {
             *type = GL_INT;
@@ -1626,7 +1525,7 @@ bool Context::applyRenderTarget(bool ignoreViewport)
 {
     IDirect3DDevice9 *device = getDevice();
 
-    Framebuffer *framebufferObject = getFramebuffer();
+    Framebuffer *framebufferObject = getDrawFramebuffer();
 
     if (!framebufferObject || framebufferObject->completeness() != GL_FRAMEBUFFER_COMPLETE)
     {
@@ -1636,20 +1535,35 @@ bool Context::applyRenderTarget(bool ignoreViewport)
     }
 
     IDirect3DSurface9 *renderTarget = framebufferObject->getRenderTarget();
-    IDirect3DSurface9 *depthStencil = framebufferObject->getDepthStencil();
+    IDirect3DSurface9 *depthStencil = NULL;
 
     unsigned int renderTargetSerial = framebufferObject->getRenderTargetSerial();
     if (renderTargetSerial != mAppliedRenderTargetSerial)
     {
         device->SetRenderTarget(0, renderTarget);
         mAppliedRenderTargetSerial = renderTargetSerial;
+        mScissorStateDirty = true; // Scissor area must be clamped to render target's size-- this is different for different render targets.
     }
 
-    unsigned int depthbufferSerial = framebufferObject->getDepthbufferSerial();
-    if (depthbufferSerial != mAppliedDepthbufferSerial)
+    unsigned int depthbufferSerial = 0;
+    unsigned int stencilbufferSerial = 0;
+    if (framebufferObject->getDepthbufferType() != GL_NONE)
+    {
+        depthStencil = framebufferObject->getDepthbuffer()->getDepthStencil();
+        depthbufferSerial = framebufferObject->getDepthbuffer()->getSerial();
+    }
+    else if (framebufferObject->getStencilbufferType() != GL_NONE)
+    {
+        depthStencil = framebufferObject->getStencilbuffer()->getDepthStencil();
+        stencilbufferSerial = framebufferObject->getStencilbuffer()->getSerial();
+    }
+
+    if (depthbufferSerial != mAppliedDepthbufferSerial ||
+        stencilbufferSerial != mAppliedStencilbufferSerial)
     {
         device->SetDepthStencilSurface(depthStencil);
         mAppliedDepthbufferSerial = depthbufferSerial;
+        mAppliedStencilbufferSerial = stencilbufferSerial;
     }
 
     D3DVIEWPORT9 viewport;
@@ -1690,7 +1604,8 @@ bool Context::applyRenderTarget(bool ignoreViewport)
                          mState.scissorY,
                          mState.scissorX + mState.scissorWidth,
                          mState.scissorY + mState.scissorHeight};
-
+            rect.right = std::min(static_cast<UINT>(rect.right), desc.Width);
+            rect.bottom = std::min(static_cast<UINT>(rect.bottom), desc.Height);
             device->SetScissorRect(&rect);
             device->SetRenderState(D3DRS_SCISSORTESTENABLE, TRUE);
         }
@@ -1698,7 +1613,7 @@ bool Context::applyRenderTarget(bool ignoreViewport)
         {
             device->SetRenderState(D3DRS_SCISSORTESTENABLE, FALSE);
         }
-        
+
         mScissorStateDirty = false;
     }
 
@@ -1710,7 +1625,7 @@ bool Context::applyRenderTarget(bool ignoreViewport)
         GLfloat xy[2] = {1.0f / viewport.Width, 1.0f / viewport.Height};
         programObject->setUniform2fv(halfPixelSize, 1, (GLfloat*)&xy);
 
-        GLint window = programObject->getDxWindowLocation();
+        GLint window = programObject->getDxViewportLocation();
         GLfloat whxy[4] = {mState.viewportWidth / 2.0f, mState.viewportHeight / 2.0f, 
                           (float)mState.viewportX + mState.viewportWidth / 2.0f, 
                           (float)mState.viewportY + mState.viewportHeight / 2.0f};
@@ -1748,6 +1663,8 @@ void Context::applyState(GLenum drawMode)
     GLint alwaysFront = !isTriangleMode(drawMode);
     programObject->setUniform1iv(pointsOrLines, 1, &alwaysFront);
 
+    Framebuffer *framebufferObject = getDrawFramebuffer();
+
     if (mCullStateDirty || mFrontFaceDirty)
     {
         if (mState.cullFace)
@@ -1764,7 +1681,7 @@ void Context::applyState(GLenum drawMode)
 
     if (mDepthStateDirty)
     {
-        if (mState.depthTest)
+        if (mState.depthTest && framebufferObject->getDepthbufferType() != GL_NONE)
         {
             device->SetRenderState(D3DRS_ZENABLE, D3DZB_TRUE);
             device->SetRenderState(D3DRS_ZFUNC, es2dx::ConvertComparison(mState.depthFunc));
@@ -1826,7 +1743,7 @@ void Context::applyState(GLenum drawMode)
 
     if (mStencilStateDirty || mFrontFaceDirty)
     {
-        if (mState.stencilTest && hasStencil())
+        if (mState.stencilTest && framebufferObject->hasStencil())
         {
             device->SetRenderState(D3DRS_STENCILENABLE, TRUE);
             device->SetRenderState(D3DRS_TWOSIDEDSTENCILMODE, TRUE);
@@ -1844,8 +1761,7 @@ void Context::applyState(GLenum drawMode)
             }
 
             // get the maximum size of the stencil ref
-            gl::Framebuffer *framebuffer = getFramebuffer();
-            gl::Stencilbuffer *stencilbuffer = framebuffer->getStencilbuffer();
+            gl::DepthStencilbuffer *stencilbuffer = framebufferObject->getStencilbuffer();
             GLuint maxStencil = (1 << stencilbuffer->getStencilSize()) - 1;
 
             device->SetRenderState(mState.frontFace == GL_CCW ? D3DRS_STENCILWRITEMASK : D3DRS_CCW_STENCILWRITEMASK, mState.stencilWritemask);
@@ -1897,7 +1813,7 @@ void Context::applyState(GLenum drawMode)
     {
         if (mState.polygonOffsetFill)
         {
-            gl::Depthbuffer *depthbuffer = getFramebuffer()->getDepthbuffer();
+            gl::DepthStencilbuffer *depthbuffer = framebufferObject->getDepthbuffer();
             if (depthbuffer)
             {
                 device->SetRenderState(D3DRS_SLOPESCALEDEPTHBIAS, *((DWORD*)&mState.polygonOffsetFactor));
@@ -1914,7 +1830,7 @@ void Context::applyState(GLenum drawMode)
         mPolygonOffsetStateDirty = false;
     }
 
-    if (mConfig->mMultiSample != 0 && mSampleStateDirty)
+    if (framebufferObject->isMultisample() && mSampleStateDirty)
     {
         if (mState.sampleAlphaToCoverage)
         {
@@ -1923,7 +1839,34 @@ void Context::applyState(GLenum drawMode)
 
         if (mState.sampleCoverage)
         {
-            FIXME("Sample coverage is unimplemented.");
+            device->SetRenderState(D3DRS_MULTISAMPLEANTIALIAS, TRUE);
+            unsigned int mask = 0;
+            if (mState.sampleCoverageValue != 0)
+            {
+                float threshold = 0.5f;
+
+                for (int i = 0; i < framebufferObject->getSamples(); ++i)
+                {
+                    mask <<= 1;
+
+                    if ((i + 1) * mState.sampleCoverageValue >= threshold)
+                    {
+                        threshold += 1.0f;
+                        mask |= 1;
+                    }
+                }
+            }
+            
+            if (mState.sampleCoverageInvert)
+            {
+                mask = ~mask;
+            }
+
+            device->SetRenderState(D3DRS_MULTISAMPLEMASK, mask);
+        }
+        else
+        {
+            device->SetRenderState(D3DRS_MULTISAMPLEANTIALIAS, FALSE);
         }
 
         mSampleStateDirty = false;
@@ -2005,7 +1948,7 @@ GLenum Context::applyVertexBuffer(const TranslatedIndexData &indexInfo)
 // Applies the indices and element array bindings to the Direct3D 9 device
 GLenum Context::applyIndexBuffer(const void *indices, GLsizei count, GLenum mode, GLenum type, TranslatedIndexData *indexInfo)
 {
-    GLenum err = mIndexDataManager->preRenderValidate(mode, type, count, getBuffer(mState.elementArrayBuffer), indices, indexInfo);
+    GLenum err = mIndexDataManager->preRenderValidate(mode, type, count, mState.elementArrayBuffer.get(), indices, indexInfo);
 
     if (err == GL_NO_ERROR)
     {
@@ -2092,7 +2035,18 @@ void Context::applyTextures()
 
 void Context::readPixels(GLint x, GLint y, GLsizei width, GLsizei height, GLenum format, GLenum type, void* pixels)
 {
-    Framebuffer *framebuffer = getFramebuffer();
+    Framebuffer *framebuffer = getReadFramebuffer();
+
+    if (framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
+    {
+        return error(GL_INVALID_FRAMEBUFFER_OPERATION);
+    }
+
+    if (getReadFramebufferHandle() != 0 && framebuffer->getSamples() != 0)
+    {
+        return error(GL_INVALID_OPERATION);
+    }
+
     IDirect3DSurface9 *renderTarget = framebuffer->getRenderTarget();
     IDirect3DDevice9 *device = getDevice();
 
@@ -2155,6 +2109,19 @@ void Context::readPixels(GLint x, GLint y, GLsizei width, GLsizei height, GLenum
 
     for (int j = 0; j < rect.bottom - rect.top; j++)
     {
+        if (desc.Format == D3DFMT_A8R8G8B8 &&
+            format == GL_BGRA_EXT &&
+            type == GL_UNSIGNED_BYTE)
+        {
+            // Fast path for EXT_read_format_bgra, given
+            // an RGBA source buffer.  Note that buffers with no
+            // alpha go through the slow path below.
+            memcpy(dest + j * outputPitch,
+                   source + j * lock.Pitch,
+                   (rect.right - rect.left) * 4);
+            continue;
+        }
+
         for (int i = 0; i < rect.right - rect.left; i++)
         {
             float r;
@@ -2243,6 +2210,46 @@ void Context::readPixels(GLint x, GLint y, GLsizei width, GLsizei height, GLenum
                   default: UNREACHABLE();
                 }
                 break;
+              case GL_BGRA_EXT:
+                switch (type)
+                {
+                  case GL_UNSIGNED_BYTE:
+                    dest[4 * i + j * outputPitch + 0] = (unsigned char)(255 * b + 0.5f);
+                    dest[4 * i + j * outputPitch + 1] = (unsigned char)(255 * g + 0.5f);
+                    dest[4 * i + j * outputPitch + 2] = (unsigned char)(255 * r + 0.5f);
+                    dest[4 * i + j * outputPitch + 3] = (unsigned char)(255 * a + 0.5f);
+                    break;
+                  case GL_UNSIGNED_SHORT_4_4_4_4_REV_EXT:
+                    // According to the desktop GL spec in the "Transfer of Pixel Rectangles" section
+                    // this type is packed as follows:
+                    //   15   14   13   12   11   10    9    8    7    6    5    4    3    2    1    0
+                    //  --------------------------------------------------------------------------------
+                    // |       4th         |        3rd         |        2nd        |   1st component   |
+                    //  --------------------------------------------------------------------------------
+                    // in the case of BGRA_EXT, B is the first component, G the second, and so forth.
+                    dest16[i + j * outputPitch / sizeof(unsigned short)] =
+                        ((unsigned short)(15 * a + 0.5f) << 12)|
+                        ((unsigned short)(15 * r + 0.5f) << 8) |
+                        ((unsigned short)(15 * g + 0.5f) << 4) |
+                        ((unsigned short)(15 * b + 0.5f) << 0);
+                    break;
+                  case GL_UNSIGNED_SHORT_1_5_5_5_REV_EXT:
+                    // According to the desktop GL spec in the "Transfer of Pixel Rectangles" section
+                    // this type is packed as follows:
+                    //   15   14   13   12   11   10    9    8    7    6    5    4    3    2    1    0
+                    //  --------------------------------------------------------------------------------
+                    // | 4th |          3rd           |           2nd          |      1st component     |
+                    //  --------------------------------------------------------------------------------
+                    // in the case of BGRA_EXT, B is the first component, G the second, and so forth.
+                    dest16[i + j * outputPitch / sizeof(unsigned short)] =
+                        ((unsigned short)(     a + 0.5f) << 15) |
+                        ((unsigned short)(31 * r + 0.5f) << 10) |
+                        ((unsigned short)(31 * g + 0.5f) << 5) |
+                        ((unsigned short)(31 * b + 0.5f) << 0);
+                    break;
+                  default: UNREACHABLE();
+                }
+                break;
               case GL_RGB:   // IMPLEMENTATION_COLOR_READ_FORMAT
                 switch (type)
                 {
@@ -2267,7 +2274,7 @@ void Context::readPixels(GLint x, GLint y, GLsizei width, GLsizei height, GLenum
 
 void Context::clear(GLbitfield mask)
 {
-    Framebuffer *framebufferObject = getFramebuffer();
+    Framebuffer *framebufferObject = getDrawFramebuffer();
 
     if (!framebufferObject || framebufferObject->completeness() != GL_FRAMEBUFFER_COMPLETE)
     {
@@ -2299,22 +2306,24 @@ void Context::clear(GLbitfield mask)
         }
     }
 
-    IDirect3DSurface9 *depthStencil = framebufferObject->getDepthStencil();
-
     GLuint stencilUnmasked = 0x0;
 
-    if ((mask & GL_STENCIL_BUFFER_BIT) && depthStencil)
+    if (mask & GL_STENCIL_BUFFER_BIT)
     {
-        D3DSURFACE_DESC desc;
-        depthStencil->GetDesc(&desc);
-
         mask &= ~GL_STENCIL_BUFFER_BIT;
-        unsigned int stencilSize = es2dx::GetStencilSize(desc.Format);
-        stencilUnmasked = (0x1 << stencilSize) - 1;
-
-        if (stencilUnmasked != 0x0)
+        if (framebufferObject->getStencilbufferType() != GL_NONE)
         {
-            flags |= D3DCLEAR_STENCIL;
+            IDirect3DSurface9 *depthStencil = framebufferObject->getStencilbuffer()->getDepthStencil();
+            D3DSURFACE_DESC desc;
+            depthStencil->GetDesc(&desc);
+
+            unsigned int stencilSize = es2dx::GetStencilSize(desc.Format);
+            stencilUnmasked = (0x1 << stencilSize) - 1;
+
+            if (stencilUnmasked != 0x0)
+            {
+                flags |= D3DCLEAR_STENCIL;
+            }
         }
     }
 
@@ -2618,7 +2627,8 @@ void Context::finish()
         IDirect3DStateBlock9 *savedState = NULL;
         device->CreateStateBlock(D3DSBT_ALL, &savedState);
 
-        occlusionQuery->Issue(D3DISSUE_BEGIN);
+        HRESULT result = occlusionQuery->Issue(D3DISSUE_BEGIN);
+        ASSERT(SUCCEEDED(result));
 
         // Render something outside the render target
         device->SetStreamSourceFreq(0, 1);
@@ -2629,7 +2639,8 @@ void Context::finish()
         display->startScene();
         device->DrawPrimitiveUP(D3DPT_POINTLIST, 1, data, sizeof(data));
 
-        occlusionQuery->Issue(D3DISSUE_END);
+        result = occlusionQuery->Issue(D3DISSUE_END);
+        ASSERT(SUCCEEDED(result));
 
         while (occlusionQuery->GetData(NULL, 0, D3DGETDATA_FLUSH) == S_FALSE)
         {
@@ -2663,15 +2674,16 @@ void Context::flush()
 
     if (eventQuery)
     {
-        eventQuery->Issue(D3DISSUE_END);
+        HRESULT result = eventQuery->Issue(D3DISSUE_END);
+        ASSERT(SUCCEEDED(result));
 
-        while (eventQuery->GetData(NULL, 0, D3DGETDATA_FLUSH) == S_FALSE)
+        result = eventQuery->GetData(NULL, 0, D3DGETDATA_FLUSH);
+        eventQuery->Release();
+
+        if (result == D3DERR_DEVICELOST)
         {
-            // Keep polling, but allow other threads to do something useful first
-            Sleep(0);
+            error(GL_OUT_OF_MEMORY);
         }
-
-        eventQuery->Release();
     }
 }
 
@@ -2742,14 +2754,43 @@ GLenum Context::getError()
     return GL_NO_ERROR;
 }
 
-const char *Context::getPixelShaderProfile()
+bool Context::supportsShaderModel3() const
 {
-    return mPsProfile;
+    return mSupportsShaderModel3;
 }
 
-const char *Context::getVertexShaderProfile()
+int Context::getMaxSupportedSamples() const
 {
-    return mVsProfile;
+    return mMaxSupportedSamples;
+}
+
+int Context::getNearestSupportedSamples(D3DFORMAT format, int requested) const
+{
+    if (requested == 0)
+    {
+        return requested;
+    }
+
+    std::map<D3DFORMAT, bool *>::const_iterator itr = mMultiSampleSupport.find(format);
+    if (itr == mMultiSampleSupport.end())
+    {
+        return -1;
+    }
+
+    for (int i = requested; i <= D3DMULTISAMPLE_16_SAMPLES; ++i)
+    {
+        if (itr->second[i] && i != D3DMULTISAMPLE_NONMASKABLE)
+        {
+            return i;
+        }
+    }
+
+    return -1;
+}
+
+bool Context::supportsCompressedTextures() const
+{
+    return mSupportsCompressedTextures;
 }
 
 void Context::detachBuffer(GLuint buffer)
@@ -2758,21 +2799,21 @@ void Context::detachBuffer(GLuint buffer)
     // If a buffer object is deleted while it is bound, all bindings to that object in the current context
     // (i.e. in the thread that called Delete-Buffers) are reset to zero.
 
-    if (mState.arrayBuffer == buffer)
+    if (mState.arrayBuffer.id() == buffer)
     {
-        mState.arrayBuffer = 0;
+        mState.arrayBuffer.set(NULL);
     }
 
-    if (mState.elementArrayBuffer == buffer)
+    if (mState.elementArrayBuffer.id() == buffer)
     {
-        mState.elementArrayBuffer = 0;
+        mState.elementArrayBuffer.set(NULL);
     }
 
     for (int attribute = 0; attribute < MAX_VERTEX_ATTRIBS; attribute++)
     {
-        if (mState.vertexAttribute[attribute].mBoundBuffer == buffer)
+        if (mState.vertexAttribute[attribute].mBoundBuffer.id() == buffer)
         {
-            mState.vertexAttribute[attribute].mBoundBuffer = 0;
+            mState.vertexAttribute[attribute].mBoundBuffer.set(NULL);
         }
     }
 }
@@ -2787,9 +2828,9 @@ void Context::detachTexture(GLuint texture)
     {
         for (int sampler = 0; sampler < MAX_TEXTURE_IMAGE_UNITS; sampler++)
         {
-            if (mState.samplerTexture[type][sampler] == texture)
+            if (mState.samplerTexture[type][sampler].id() == texture)
             {
-                mState.samplerTexture[type][sampler] = 0;
+                mState.samplerTexture[type][sampler].set(NULL);
             }
         }
     }
@@ -2799,11 +2840,17 @@ void Context::detachTexture(GLuint texture)
     // as if FramebufferTexture2D had been called, with a texture of 0, for each attachment point to which this
     // image was attached in the currently bound framebuffer.
 
-    Framebuffer *framebuffer = getFramebuffer();
+    Framebuffer *readFramebuffer = getReadFramebuffer();
+    Framebuffer *drawFramebuffer = getDrawFramebuffer();
 
-    if (framebuffer)
+    if (readFramebuffer)
     {
-        framebuffer->detachTexture(texture);
+        readFramebuffer->detachTexture(texture);
+    }
+
+    if (drawFramebuffer && drawFramebuffer != readFramebuffer)
+    {
+        drawFramebuffer->detachTexture(texture);
     }
 }
 
@@ -2813,9 +2860,14 @@ void Context::detachFramebuffer(GLuint framebuffer)
     // If a framebuffer that is currently bound to the target FRAMEBUFFER is deleted, it is as though
     // BindFramebuffer had been executed with the target of FRAMEBUFFER and framebuffer of zero.
 
-    if (mState.framebuffer == framebuffer)
+    if (mState.readFramebuffer == framebuffer)
+    {
+        bindReadFramebuffer(0);
+    }
+
+    if (mState.drawFramebuffer == framebuffer)
     {
-        bindFramebuffer(0);
+        bindDrawFramebuffer(0);
     }
 }
 
@@ -2825,7 +2877,7 @@ void Context::detachRenderbuffer(GLuint renderbuffer)
     // If a renderbuffer that is currently bound to RENDERBUFFER is deleted, it is as though BindRenderbuffer
     // had been executed with the target RENDERBUFFER and name of zero.
 
-    if (mState.renderbuffer == renderbuffer)
+    if (mState.renderbuffer.id() == renderbuffer)
     {
         bindRenderbuffer(0);
     }
@@ -2835,11 +2887,17 @@ void Context::detachRenderbuffer(GLuint renderbuffer)
     // then it is as if FramebufferRenderbuffer had been called, with a renderbuffer of 0, for each attachment
     // point to which this image was attached in the currently bound framebuffer.
 
-    Framebuffer *framebuffer = getFramebuffer();
+    Framebuffer *readFramebuffer = getReadFramebuffer();
+    Framebuffer *drawFramebuffer = getDrawFramebuffer();
+
+    if (readFramebuffer)
+    {
+        readFramebuffer->detachRenderbuffer(renderbuffer);
+    }
 
-    if (framebuffer)
+    if (drawFramebuffer && drawFramebuffer != readFramebuffer)
     {
-        framebuffer->detachRenderbuffer(renderbuffer);
+        drawFramebuffer->detachRenderbuffer(renderbuffer);
     }
 }
 
@@ -2859,7 +2917,7 @@ Texture *Context::getIncompleteTexture(SamplerType type)
 
           case SAMPLER_2D:
             {
-                Texture2D *incomplete2d = new Texture2D(this);
+                Texture2D *incomplete2d = new Texture2D(Texture::INCOMPLETE_TEXTURE_ID);
                 incomplete2d->setImage(0, GL_RGBA, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, 1, color);
                 t = incomplete2d;
             }
@@ -2867,7 +2925,7 @@ Texture *Context::getIncompleteTexture(SamplerType type)
 
           case SAMPLER_CUBE:
             {
-              TextureCubeMap *incompleteCube = new TextureCubeMap(this);
+              TextureCubeMap *incompleteCube = new TextureCubeMap(Texture::INCOMPLETE_TEXTURE_ID);
 
               incompleteCube->setImagePosX(0, GL_RGBA, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, 1, color);
               incompleteCube->setImageNegX(0, GL_RGBA, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, 1, color);
@@ -2911,23 +2969,6 @@ bool Context::isTriangleMode(GLenum drawMode)
     return false;
 }
 
-bool Context::hasStencil()
-{
-    Framebuffer *framebufferObject = getFramebuffer();
-
-    if (framebufferObject)
-    {
-        Stencilbuffer *stencilbufferObject = framebufferObject->getStencilbuffer();
-
-        if (stencilbufferObject)
-        {
-            return stencilbufferObject->getStencilSize() > 0;
-        }
-    }
-
-    return false;
-}
-
 void Context::setVertexAttrib(GLuint index, const GLfloat *values)
 {
     ASSERT(index < gl::MAX_VERTEX_ATTRIBS);
@@ -2942,6 +2983,22 @@ void Context::setVertexAttrib(GLuint index, const GLfloat *values)
 
 void Context::initExtensionString()
 {
+    mExtensionString += "GL_OES_packed_depth_stencil ";
+    mExtensionString += "GL_EXT_texture_format_BGRA8888 ";
+    mExtensionString += "GL_EXT_read_format_bgra ";
+    mExtensionString += "GL_ANGLE_framebuffer_blit ";
+    mExtensionString += "GL_OES_rgb8_rgba8 ";
+
+    if (supportsCompressedTextures())
+    {
+        mExtensionString += "GL_EXT_texture_compression_dxt1 ";
+    }
+
+    if (getMaxSupportedSamples() != 0)
+    {
+        mExtensionString += "GL_ANGLE_framebuffer_multisample ";
+    }
+
     if (mBufferBackEnd->supportIntIndices())
     {
         mExtensionString += "GL_OES_element_index_uint ";
@@ -2959,13 +3016,285 @@ const char *Context::getExtensionString() const
     return mExtensionString.c_str();
 }
 
+void Context::blitFramebuffer(GLint srcX0, GLint srcY0, GLint srcX1, GLint srcY1, 
+                              GLint dstX0, GLint dstY0, GLint dstX1, GLint dstY1,
+                              GLbitfield mask)
+{
+    IDirect3DDevice9 *device = getDevice();
+
+    Framebuffer *readFramebuffer = getReadFramebuffer();
+    Framebuffer *drawFramebuffer = getDrawFramebuffer();
+
+    if (!readFramebuffer || readFramebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE ||
+        !drawFramebuffer || drawFramebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
+    {
+        return error(GL_INVALID_FRAMEBUFFER_OPERATION);
+    }
+
+    if (drawFramebuffer->getSamples() != 0)
+    {
+        return error(GL_INVALID_OPERATION);
+    }
+
+    RECT sourceRect;
+    RECT destRect;
+
+    if (srcX0 < srcX1)
+    {
+        sourceRect.left = srcX0;
+        sourceRect.right = srcX1;
+        destRect.left = dstX0;
+        destRect.right = dstX1;
+    }
+    else
+    {
+        sourceRect.left = srcX1;
+        destRect.left = dstX1;
+        sourceRect.right = srcX0;
+        destRect.right = dstX0;
+    }
+
+    // Arguments to StretchRect must be in D3D-style (0-top) coordinates, so we must 
+    // flip our Y-values here
+    if (srcY0 < srcY1)
+    {
+        sourceRect.bottom = srcY1;
+        destRect.bottom = dstY1;
+        sourceRect.top = srcY0;
+        destRect.top = dstY0;
+    }
+    else
+    {
+        sourceRect.bottom = srcY0;
+        destRect.bottom = dstY0;
+        sourceRect.top = srcY1;
+        destRect.top = dstY1;
+    }
+
+    RECT sourceScissoredRect = sourceRect;
+    RECT destScissoredRect = destRect;
+
+    if (mState.scissorTest)
+    {
+        // Only write to parts of the destination framebuffer which pass the scissor test
+        // Please note: the destRect is now in D3D-style coordinates, so the *top* of the
+        // rect will be checked against scissorY, rather than the bottom.
+        if (destRect.left < mState.scissorX)
+        {
+            int xDiff = mState.scissorX - destRect.left;
+            destScissoredRect.left = mState.scissorX;
+            sourceScissoredRect.left += xDiff;
+        }
+
+        if (destRect.right > mState.scissorX + mState.scissorWidth)
+        {
+            int xDiff = destRect.right - (mState.scissorX + mState.scissorWidth);
+            destScissoredRect.right = mState.scissorX + mState.scissorWidth;
+            sourceScissoredRect.right -= xDiff;
+        }
+
+        if (destRect.top < mState.scissorY)
+        {
+            int yDiff = mState.scissorY - destRect.top;
+            destScissoredRect.top = mState.scissorY;
+            sourceScissoredRect.top += yDiff;
+        }
+
+        if (destRect.bottom > mState.scissorY + mState.scissorHeight)
+        {
+            int yDiff = destRect.bottom - (mState.scissorY + mState.scissorHeight);
+            destScissoredRect.bottom = mState.scissorY + mState.scissorHeight;
+            sourceScissoredRect.bottom -= yDiff;
+        }
+    }
+
+    bool blitRenderTarget = false;
+    bool blitDepthStencil = false;
+
+    RECT sourceTrimmedRect = sourceScissoredRect;
+    RECT destTrimmedRect = destScissoredRect;
+
+    // The source & destination rectangles also may need to be trimmed if they fall out of the bounds of 
+    // the actual draw and read surfaces.
+    if (sourceTrimmedRect.left < 0)
+    {
+        int xDiff = 0 - sourceTrimmedRect.left;
+        sourceTrimmedRect.left = 0;
+        destTrimmedRect.left += xDiff;
+    }
+
+    int readBufferWidth = readFramebuffer->getColorbuffer()->getWidth();
+    int readBufferHeight = readFramebuffer->getColorbuffer()->getHeight();
+    int drawBufferWidth = drawFramebuffer->getColorbuffer()->getWidth();
+    int drawBufferHeight = drawFramebuffer->getColorbuffer()->getHeight();
+
+    if (sourceTrimmedRect.right > readBufferWidth)
+    {
+        int xDiff = sourceTrimmedRect.right - readBufferWidth;
+        sourceTrimmedRect.right = readBufferWidth;
+        destTrimmedRect.right -= xDiff;
+    }
+
+    if (sourceTrimmedRect.top < 0)
+    {
+        int yDiff = 0 - sourceTrimmedRect.top;
+        sourceTrimmedRect.top = 0;
+        destTrimmedRect.top += yDiff;
+    }
+
+    if (sourceTrimmedRect.bottom > readBufferHeight)
+    {
+        int yDiff = sourceTrimmedRect.bottom - readBufferHeight;
+        sourceTrimmedRect.bottom = readBufferHeight;
+        destTrimmedRect.bottom -= yDiff;
+    }
+
+    if (destTrimmedRect.left < 0)
+    {
+        int xDiff = 0 - destTrimmedRect.left;
+        destTrimmedRect.left = 0;
+        sourceTrimmedRect.left += xDiff;
+    }
+
+    if (destTrimmedRect.right > drawBufferWidth)
+    {
+        int xDiff = destTrimmedRect.right - drawBufferWidth;
+        destTrimmedRect.right = drawBufferWidth;
+        sourceTrimmedRect.right -= xDiff;
+    }
+
+    if (destTrimmedRect.top < 0)
+    {
+        int yDiff = 0 - destTrimmedRect.top;
+        destTrimmedRect.top = 0;
+        sourceTrimmedRect.top += yDiff;
+    }
+
+    if (destTrimmedRect.bottom > drawBufferHeight)
+    {
+        int yDiff = destTrimmedRect.bottom - drawBufferHeight;
+        destTrimmedRect.bottom = drawBufferHeight;
+        sourceTrimmedRect.bottom -= yDiff;
+    }
+
+    bool partialBufferCopy = false;
+    if (sourceTrimmedRect.bottom - sourceTrimmedRect.top < readFramebuffer->getColorbuffer()->getHeight() ||
+        sourceTrimmedRect.right - sourceTrimmedRect.left < readFramebuffer->getColorbuffer()->getWidth() || 
+        destTrimmedRect.bottom - destTrimmedRect.top < drawFramebuffer->getColorbuffer()->getHeight() ||
+        destTrimmedRect.right - destTrimmedRect.left < drawFramebuffer->getColorbuffer()->getWidth() ||
+        sourceTrimmedRect.top != 0 || destTrimmedRect.top != 0 || sourceTrimmedRect.left != 0 || destTrimmedRect.left != 0)
+    {
+        partialBufferCopy = true;
+    }
+
+    if (mask & GL_COLOR_BUFFER_BIT)
+    {
+        if (readFramebuffer->getColorbufferType() != drawFramebuffer->getColorbufferType() ||
+            readFramebuffer->getColorbuffer()->getD3DFormat() != drawFramebuffer->getColorbuffer()->getD3DFormat())
+        {
+            ERR("Color buffer format conversion in BlitFramebufferANGLE not supported by this implementation");
+            return error(GL_INVALID_OPERATION);
+        }
+        
+        if (partialBufferCopy && readFramebuffer->getSamples() != 0)
+        {
+            return error(GL_INVALID_OPERATION);
+        }
+
+        blitRenderTarget = true;
+
+    }
+
+    if (mask & (GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT))
+    {
+        DepthStencilbuffer *readDSBuffer = NULL;
+        DepthStencilbuffer *drawDSBuffer = NULL;
+
+        // We support OES_packed_depth_stencil, and do not support a separately attached depth and stencil buffer, so if we have
+        // both a depth and stencil buffer, it will be the same buffer.
+
+        if (mask & GL_DEPTH_BUFFER_BIT)
+        {
+            if (readFramebuffer->getDepthbuffer() && drawFramebuffer->getDepthbuffer())
+            {
+                if (readFramebuffer->getDepthbufferType() != drawFramebuffer->getDepthbufferType() ||
+                    readFramebuffer->getDepthbuffer()->getD3DFormat() != drawFramebuffer->getDepthbuffer()->getD3DFormat())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                blitDepthStencil = true;
+                readDSBuffer = readFramebuffer->getDepthbuffer();
+                drawDSBuffer = drawFramebuffer->getDepthbuffer();
+            }
+        }
+
+        if (mask & GL_STENCIL_BUFFER_BIT)
+        {
+            if (readFramebuffer->getStencilbuffer() && drawFramebuffer->getStencilbuffer())
+            {
+                if (readFramebuffer->getStencilbufferType() != drawFramebuffer->getStencilbufferType() ||
+                    readFramebuffer->getStencilbuffer()->getD3DFormat() != drawFramebuffer->getStencilbuffer()->getD3DFormat())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                blitDepthStencil = true;
+                readDSBuffer = readFramebuffer->getStencilbuffer();
+                drawDSBuffer = drawFramebuffer->getStencilbuffer();
+            }
+        }
+
+        if (partialBufferCopy)
+        {
+            ERR("Only whole-buffer depth and stencil blits are supported by this implementation.");
+            return error(GL_INVALID_OPERATION); // only whole-buffer copies are permitted
+        }
+
+        if ((drawDSBuffer && drawDSBuffer->getSamples() != 0) || 
+            (readDSBuffer && readDSBuffer->getSamples() != 0))
+        {
+            return error(GL_INVALID_OPERATION);
+        }
+    }
+
+    if (blitRenderTarget || blitDepthStencil)
+    {
+        egl::Display *display = getDisplay();
+        display->endScene();
+
+        if (blitRenderTarget)
+        {
+            HRESULT result = device->StretchRect(readFramebuffer->getRenderTarget(), &sourceTrimmedRect, 
+                                                 drawFramebuffer->getRenderTarget(), &destTrimmedRect, D3DTEXF_NONE);
+
+            if (FAILED(result))
+            {
+                ERR("BlitFramebufferANGLE failed: StretchRect returned %x.", result);
+                return;
+            }
+        }
+
+        if (blitDepthStencil)
+        {
+            HRESULT result = device->StretchRect(readFramebuffer->getDepthStencil(), NULL, drawFramebuffer->getDepthStencil(), NULL, D3DTEXF_NONE);
+
+            if (FAILED(result))
+            {
+                ERR("BlitFramebufferANGLE failed: StretchRect returned %x.", result);
+                return;
+            }
+        }
+    }
+}
+
 }
 
 extern "C"
 {
-gl::Context *glCreateContext(const egl::Config *config)
+gl::Context *glCreateContext(const egl::Config *config, const gl::Context *shareContext)
 {
-    return new gl::Context(config);
+    return new gl::Context(config, shareContext);
 }
 
 void glDestroyContext(gl::Context *context)
diff --git a/ANGLE/src/libGLESv2/Context.h b/ANGLE/src/libGLESv2/Context.h
index 913fae2..6bca756 100644
--- a/ANGLE/src/libGLESv2/Context.h
+++ b/ANGLE/src/libGLESv2/Context.h
@@ -7,8 +7,8 @@
 // Context.h: Defines the gl::Context class, managing all GL state and performing
 // rendering operations. It is the GLES2 specific implementation of EGLContext.
 
-#ifndef INCLUDE_CONTEXT_H_
-#define INCLUDE_CONTEXT_H_
+#ifndef LIBGLESV2_CONTEXT_H_
+#define LIBGLESV2_CONTEXT_H_
 
 #define GL_APICALL
 #include <GLES2/gl2.h>
@@ -19,6 +19,8 @@
 #include <map>
 
 #include "common/angleutils.h"
+#include "libGLESv2/ResourceManager.h"
+#include "libGLESv2/RefCountObject.h"
 
 namespace egl
 {
@@ -40,9 +42,11 @@ class Texture2D;
 class TextureCubeMap;
 class Framebuffer;
 class Renderbuffer;
+class RenderbufferStorage;
 class Colorbuffer;
 class Depthbuffer;
 class Stencilbuffer;
+class DepthStencilbuffer;
 class VertexDataManager;
 class IndexDataManager;
 class BufferBackEnd;
@@ -67,15 +71,8 @@ enum
 const float ALIASED_LINE_WIDTH_RANGE_MIN = 1.0f;
 const float ALIASED_LINE_WIDTH_RANGE_MAX = 1.0f;
 const float ALIASED_POINT_SIZE_RANGE_MIN = 1.0f;
-const float ALIASED_POINT_SIZE_RANGE_MAX = 1.0f;
-
-enum SamplerType
-{
-    SAMPLER_2D,
-    SAMPLER_CUBE,
-
-    SAMPLER_TYPE_COUNT
-};
+const float ALIASED_POINT_SIZE_RANGE_MAX_SM2 = 1.0f;
+const float ALIASED_POINT_SIZE_RANGE_MAX_SM3 = 64.0f;
 
 struct Color
 {
@@ -90,7 +87,7 @@ class AttributeState
 {
   public:
     AttributeState()
-        : mType(GL_FLOAT), mSize(0), mNormalized(false), mStride(0), mPointer(NULL), mBoundBuffer(0), mEnabled(false)
+        : mType(GL_FLOAT), mSize(0), mNormalized(false), mStride(0), mPointer(NULL), mEnabled(false)
     {
         mCurrentValue[0] = 0;
         mCurrentValue[1] = 0;
@@ -105,7 +102,7 @@ class AttributeState
     GLsizei mStride; // 0 means natural stride
     const void *mPointer;
 
-    GLuint mBoundBuffer; // Captured when VertexArrayPointer is called.
+    BindingPointer<Buffer> mBoundBuffer; // Captured when VertexArrayPointer is called.
 
     bool mEnabled; // From Enable/DisableVertexAttribArray
 
@@ -180,16 +177,17 @@ struct State
     bool depthMask;
 
     int activeSampler;   // Active texture unit selector - GL_TEXTURE0
-    GLuint arrayBuffer;
-    GLuint elementArrayBuffer;
-    GLuint texture2D;
-    GLuint textureCubeMap;
-    GLuint framebuffer;
-    GLuint renderbuffer;
+    BindingPointer<Buffer> arrayBuffer;
+    BindingPointer<Buffer> elementArrayBuffer;
+    BindingPointer<Texture> texture2D;
+    BindingPointer<Texture> textureCubeMap;
+    GLuint readFramebuffer;
+    GLuint drawFramebuffer;
+    BindingPointer<Renderbuffer> renderbuffer;
     GLuint currentProgram;
 
     AttributeState vertexAttribute[MAX_VERTEX_ATTRIBS];
-    GLuint samplerTexture[SAMPLER_TYPE_COUNT][MAX_TEXTURE_IMAGE_UNITS];
+    BindingPointer<Texture> samplerTexture[SAMPLER_TYPE_COUNT][MAX_TEXTURE_IMAGE_UNITS];
 
     GLint unpackAlignment;
     GLint packAlignment;
@@ -198,7 +196,7 @@ struct State
 class Context
 {
   public:
-    Context(const egl::Config *config);
+    Context(const egl::Config *config, const gl::Context *shareContext);
 
     ~Context();
 
@@ -276,14 +274,15 @@ class Context
 
     void setActiveSampler(int active);
 
-    GLuint getFramebufferHandle() const;
+    GLuint getReadFramebufferHandle() const;
+    GLuint getDrawFramebufferHandle() const;
     GLuint getRenderbufferHandle() const;
 
     GLuint getArrayBufferHandle() const;
 
     void setVertexAttribEnabled(unsigned int attribNum, bool enabled);
     const AttributeState &getVertexAttribState(unsigned int attribNum);
-    void setVertexAttribState(unsigned int attribNum, GLuint boundBuffer, GLint size, GLenum type,
+    void setVertexAttribState(unsigned int attribNum, Buffer *boundBuffer, GLint size, GLenum type,
                               bool normalized, GLsizei stride, const void *pointer);
     const void *getVertexAttribPointer(unsigned int attribNum) const;
 
@@ -295,33 +294,36 @@ class Context
     void setPackAlignment(GLint alignment);
     GLint getPackAlignment() const;
 
+    // These create  and destroy methods are merely pass-throughs to 
+    // ResourceManager, which owns these object types
     GLuint createBuffer();
     GLuint createShader(GLenum type);
     GLuint createProgram();
     GLuint createTexture();
-    GLuint createFramebuffer();
     GLuint createRenderbuffer();
 
     void deleteBuffer(GLuint buffer);
     void deleteShader(GLuint shader);
     void deleteProgram(GLuint program);
     void deleteTexture(GLuint texture);
-    void deleteFramebuffer(GLuint framebuffer);
     void deleteRenderbuffer(GLuint renderbuffer);
 
+    // Framebuffers are owned by the Context, so these methods do not pass through
+    GLuint createFramebuffer();
+    void deleteFramebuffer(GLuint framebuffer);
+
     void bindArrayBuffer(GLuint buffer);
     void bindElementArrayBuffer(GLuint buffer);
     void bindTexture2D(GLuint texture);
     void bindTextureCubeMap(GLuint texture);
-    void bindFramebuffer(GLuint framebuffer);
+    void bindReadFramebuffer(GLuint framebuffer);
+    void bindDrawFramebuffer(GLuint framebuffer);
     void bindRenderbuffer(GLuint renderbuffer);
     void useProgram(GLuint program);
 
     void setFramebufferZero(Framebuffer *framebuffer);
-    void setColorbufferZero(Colorbuffer *renderbuffer);
-    void setDepthbufferZero(Depthbuffer *depthBuffer);
-    void setStencilbufferZero(Stencilbuffer *stencilBuffer);
-    void setRenderbuffer(Renderbuffer *renderbuffer);
+
+    void setRenderbufferStorage(RenderbufferStorage *renderbuffer);
 
     void setVertexAttrib(GLuint index, const GLfloat *values);
 
@@ -331,9 +333,6 @@ class Context
     Texture *getTexture(GLuint handle);
     Framebuffer *getFramebuffer(GLuint handle);
     Renderbuffer *getRenderbuffer(GLuint handle);
-    Colorbuffer *getColorbuffer(GLuint handle);
-    Depthbuffer *getDepthbuffer(GLuint handle);
-    Stencilbuffer *getStencilbuffer(GLuint handle);
 
     Buffer *getArrayBuffer();
     Buffer *getElementArrayBuffer();
@@ -341,7 +340,8 @@ class Context
     Texture2D *getTexture2D();
     TextureCubeMap *getTextureCubeMap();
     Texture *getSamplerTexture(unsigned int sampler, SamplerType type);
-    Framebuffer *getFramebuffer();
+    Framebuffer *getReadFramebuffer();
+    Framebuffer *getDrawFramebuffer();
 
     bool getFloatv(GLenum pname, GLfloat *params);
     bool getIntegerv(GLenum pname, GLint *params);
@@ -373,10 +373,15 @@ class Context
 
     GLenum getError();
 
-    const char *getPixelShaderProfile();
-    const char *getVertexShaderProfile();
-
+    bool supportsShaderModel3() const;
+    GLsizei getMaxSupportedSamples() const;
+    int getNearestSupportedSamples(D3DFORMAT format, int requested) const;
     const char *getExtensionString() const;
+    bool supportsCompressedTextures() const;
+
+    void blitFramebuffer(GLint srcX0, GLint srcY0, GLint srcX1, GLint srcY1, 
+                         GLint dstX0, GLint dstY0, GLint dstX1, GLint dstY1,
+                         GLbitfield mask);
 
     Blit *getBlitter() { return mBlit; }
 
@@ -396,7 +401,6 @@ class Context
 
     bool cullSkipsDraw(GLenum drawMode);
     bool isTriangleMode(GLenum drawMode);
-    bool hasStencil();
 
     const egl::Config *const mConfig;
 
@@ -406,27 +410,11 @@ class Context
     TextureCubeMap *mTextureCubeMapZero;
 
     Colorbuffer *mColorbufferZero;
-    Depthbuffer *mDepthbufferZero;
-    Stencilbuffer *mStencilbufferZero;
-
-    typedef std::map<GLuint, Buffer*> BufferMap;
-    BufferMap mBufferMap;
-
-    typedef std::map<GLuint, Shader*> ShaderMap;
-    ShaderMap mShaderMap;
-
-    typedef std::map<GLuint, Program*> ProgramMap;
-    ProgramMap mProgramMap;
-
-    typedef std::map<GLuint, Texture*> TextureMap;
-    TextureMap mTextureMap;
+    DepthStencilbuffer *mDepthStencilbufferZero;
 
     typedef std::map<GLuint, Framebuffer*> FramebufferMap;
     FramebufferMap mFramebufferMap;
 
-    typedef std::map<GLuint, Renderbuffer*> RenderbufferMap;
-    RenderbufferMap mRenderbufferMap;
-
     void initExtensionString();
     std::string mExtensionString;
 
@@ -435,7 +423,7 @@ class Context
     IndexDataManager *mIndexDataManager;
 
     Blit *mBlit;
-
+    
     Texture *mIncompleteTextures[SAMPLER_TYPE_COUNT];
 
     // Recorded errors
@@ -450,9 +438,12 @@ class Context
     unsigned int mAppliedProgram;
     unsigned int mAppliedRenderTargetSerial;
     unsigned int mAppliedDepthbufferSerial;
+    unsigned int mAppliedStencilbufferSerial;
 
-    const char *mPsProfile;
-    const char *mVsProfile;
+    bool mSupportsShaderModel3;
+    std::map<D3DFORMAT, bool *> mMultiSampleSupport;
+    GLsizei mMaxSupportedSamples;
+    bool mSupportsCompressedTextures;
 
     // state caching flags
     bool mClearStateDirty;
@@ -471,13 +462,15 @@ class Context
     IDirect3DStateBlock9 *mMaskedClearSavedState;
 
     D3DCAPS9 mDeviceCaps;
+
+    ResourceManager *mResourceManager;
 };
 }
 
 extern "C"
 {
 // Exported functions for use by EGL
-gl::Context *glCreateContext(const egl::Config *config);
+gl::Context *glCreateContext(const egl::Config *config, const gl::Context *shareContext);
 void glDestroyContext(gl::Context *context);
 void glMakeCurrent(gl::Context *context, egl::Display *display, egl::Surface *surface);
 gl::Context *glGetCurrentContext();
diff --git a/ANGLE/src/libGLESv2/Framebuffer.cpp b/ANGLE/src/libGLESv2/Framebuffer.cpp
index 1a3b01e..5c4bc99 100644
--- a/ANGLE/src/libGLESv2/Framebuffer.cpp
+++ b/ANGLE/src/libGLESv2/Framebuffer.cpp
@@ -16,85 +16,109 @@
 
 namespace gl
 {
+
 Framebuffer::Framebuffer()
 {
     mColorbufferType = GL_NONE;
-    mColorbufferHandle = 0;
-
     mDepthbufferType = GL_NONE;
-    mDepthbufferHandle = 0;
-
     mStencilbufferType = GL_NONE;
-    mStencilbufferHandle = 0;
 }
 
 Framebuffer::~Framebuffer()
 {
+    mColorbufferPointer.set(NULL);
+    mDepthbufferPointer.set(NULL);
+    mStencilbufferPointer.set(NULL);
+}
+
+Renderbuffer *Framebuffer::lookupRenderbuffer(GLenum type, GLuint handle) const
+{
+    gl::Context *context = gl::getContext();
+    Renderbuffer *buffer = NULL;
+
+    if (type == GL_NONE)
+    {
+        buffer = NULL;
+    }
+    else if (type == GL_RENDERBUFFER)
+    {
+        buffer = context->getRenderbuffer(handle);
+    }
+    else if (IsTextureTarget(type))
+    {
+        buffer = context->getTexture(handle)->getColorbuffer(type);
+    }
+    else
+    {
+        UNREACHABLE();
+    }
+
+    return buffer;
 }
 
 void Framebuffer::setColorbuffer(GLenum type, GLuint colorbuffer)
 {
     mColorbufferType = type;
-    mColorbufferHandle = colorbuffer;
+    mColorbufferPointer.set(lookupRenderbuffer(type, colorbuffer));
 }
 
 void Framebuffer::setDepthbuffer(GLenum type, GLuint depthbuffer)
 {
     mDepthbufferType = type;
-    mDepthbufferHandle = depthbuffer;
+    mDepthbufferPointer.set(lookupRenderbuffer(type, depthbuffer));
 }
 
 void Framebuffer::setStencilbuffer(GLenum type, GLuint stencilbuffer)
 {
     mStencilbufferType = type;
-    mStencilbufferHandle = stencilbuffer;
+    mStencilbufferPointer.set(lookupRenderbuffer(type, stencilbuffer));
 }
 
 void Framebuffer::detachTexture(GLuint texture)
 {
-    if (mColorbufferHandle == texture && IsTextureTarget(mColorbufferType))
+    if (mColorbufferPointer.id() == texture && IsTextureTarget(mColorbufferType))
     {
         mColorbufferType = GL_NONE;
-        mColorbufferHandle = 0;
+        mColorbufferPointer.set(NULL);
     }
 
-    if (mDepthbufferHandle == texture && IsTextureTarget(mDepthbufferType))
+    if (mDepthbufferPointer.id() == texture && IsTextureTarget(mDepthbufferType))
     {
         mDepthbufferType = GL_NONE;
-        mDepthbufferHandle = 0;
+        mDepthbufferPointer.set(NULL);
     }
 
-    if (mStencilbufferHandle == texture && IsTextureTarget(mStencilbufferType))
+    if (mStencilbufferPointer.id() == texture && IsTextureTarget(mStencilbufferType))
     {
         mStencilbufferType = GL_NONE;
-        mStencilbufferHandle = 0;
+        mStencilbufferPointer.set(NULL);
     }
 }
 
 void Framebuffer::detachRenderbuffer(GLuint renderbuffer)
 {
-    if (mColorbufferHandle == renderbuffer && mColorbufferType == GL_RENDERBUFFER)
+    if (mColorbufferPointer.id() == renderbuffer && mColorbufferType == GL_RENDERBUFFER)
     {
         mColorbufferType = GL_NONE;
-        mColorbufferHandle = 0;
+        mColorbufferPointer.set(NULL);
     }
 
-    if (mDepthbufferHandle == renderbuffer && mDepthbufferType == GL_RENDERBUFFER)
+    if (mDepthbufferPointer.id() == renderbuffer && mDepthbufferType == GL_RENDERBUFFER)
     {
         mDepthbufferType = GL_NONE;
-        mDepthbufferHandle = 0;
+        mDepthbufferPointer.set(NULL);
     }
 
-    if (mStencilbufferHandle == renderbuffer && mStencilbufferType == GL_RENDERBUFFER)
+    if (mStencilbufferPointer.id() == renderbuffer && mStencilbufferType == GL_RENDERBUFFER)
     {
         mStencilbufferType = GL_NONE;
-        mStencilbufferHandle = 0;
+        mStencilbufferPointer.set(NULL);
     }
 }
 
 unsigned int Framebuffer::getRenderTargetSerial()
 {
-    Renderbuffer *colorbuffer = getColorbuffer();
+    Renderbuffer *colorbuffer = mColorbufferPointer.get();
 
     if (colorbuffer)
     {
@@ -106,7 +130,7 @@ unsigned int Framebuffer::getRenderTargetSerial()
 
 IDirect3DSurface9 *Framebuffer::getRenderTarget()
 {
-    Renderbuffer *colorbuffer = getColorbuffer();
+    Renderbuffer *colorbuffer = mColorbufferPointer.get();
 
     if (colorbuffer)
     {
@@ -116,10 +140,26 @@ IDirect3DSurface9 *Framebuffer::getRenderTarget()
     return NULL;
 }
 
+IDirect3DSurface9 *Framebuffer::getDepthStencil()
+{
+    Renderbuffer *depthstencilbuffer = mDepthbufferPointer.get();
+    
+    if (!depthstencilbuffer)
+    {
+        depthstencilbuffer = mStencilbufferPointer.get();
+    }
+
+    if (depthstencilbuffer)
+    {
+        return depthstencilbuffer->getDepthStencil();
+    }
+
+    return NULL;
+}
+
 unsigned int Framebuffer::getDepthbufferSerial()
 {
-    gl::Context *context = gl::getContext();
-    Depthbuffer *depthbuffer = context->getDepthbuffer(mDepthbufferHandle);
+    Renderbuffer *depthbuffer = mDepthbufferPointer.get();
 
     if (depthbuffer)
     {
@@ -129,70 +169,58 @@ unsigned int Framebuffer::getDepthbufferSerial()
     return 0;
 }
 
-IDirect3DSurface9 *Framebuffer::getDepthStencil()
+unsigned int Framebuffer::getStencilbufferSerial()
 {
-    gl::Context *context = gl::getContext();
-    Depthbuffer *depthbuffer = context->getDepthbuffer(mDepthbufferHandle);
+    Renderbuffer *stencilbuffer = mStencilbufferPointer.get();
 
-    if (depthbuffer)
+    if (stencilbuffer)
     {
-        return depthbuffer->getDepthStencil();
+        return stencilbuffer->getSerial();
     }
 
-    return NULL;
+    return 0;
 }
 
 Colorbuffer *Framebuffer::getColorbuffer()
 {
-    gl::Context *context = gl::getContext();
-    Colorbuffer *colorbuffer = NULL;
+    Renderbuffer *rb = mColorbufferPointer.get();
 
-    if (mColorbufferType == GL_NONE)
+    if (rb != NULL && rb->isColorbuffer())
     {
-        UNREACHABLE();
-        colorbuffer = NULL;
-    }
-    else if (mColorbufferType == GL_RENDERBUFFER)
-    {
-        colorbuffer = context->getColorbuffer(mColorbufferHandle);
+        return static_cast<Colorbuffer*>(rb->getStorage());
     }
     else
     {
-        colorbuffer = context->getTexture(mColorbufferHandle)->getColorbuffer(mColorbufferType);
-    }
-
-    if (colorbuffer && colorbuffer->isColorbuffer())
-    {
-        return colorbuffer;
+        return NULL;
     }
-
-    return NULL;
 }
 
-Depthbuffer *Framebuffer::getDepthbuffer()
+DepthStencilbuffer *Framebuffer::getDepthbuffer()
 {
-    gl::Context *context = gl::getContext();
-    Depthbuffer *depthbuffer = context->getDepthbuffer(mDepthbufferHandle);
+    Renderbuffer *rb = mDepthbufferPointer.get();
 
-    if (depthbuffer && depthbuffer->isDepthbuffer())
+    if (rb != NULL && rb->isDepthbuffer())
     {
-        return depthbuffer;
+        return static_cast<DepthStencilbuffer*>(rb->getStorage());
+    }
+    else
+    {
+        return NULL;
     }
-
-    return NULL;
 }
 
-Stencilbuffer *Framebuffer::getStencilbuffer()
+DepthStencilbuffer *Framebuffer::getStencilbuffer()
 {
-    gl::Context *context = gl::getContext();
-    Stencilbuffer *stencilbuffer = context->getStencilbuffer(mStencilbufferHandle);
+    Renderbuffer *rb = mStencilbufferPointer.get();
 
-    if (stencilbuffer && stencilbuffer->isStencilbuffer())
+    if (rb != NULL && rb->isStencilbuffer())
     {
-        return stencilbuffer;
+        return static_cast<DepthStencilbuffer*>(rb->getStorage());
+    }
+    else
+    {
+        return NULL;
     }
-
-    return NULL;
 }
 
 GLenum Framebuffer::getColorbufferType()
@@ -212,25 +240,56 @@ GLenum Framebuffer::getStencilbufferType()
 
 GLuint Framebuffer::getColorbufferHandle()
 {
-    return mColorbufferHandle;
+    return mColorbufferPointer.id();
 }
 
 GLuint Framebuffer::getDepthbufferHandle()
 {
-    return mDepthbufferHandle;
+    return mDepthbufferPointer.id();
 }
 
 GLuint Framebuffer::getStencilbufferHandle()
 {
-    return mStencilbufferHandle;
+    return mStencilbufferPointer.id();
 }
 
-GLenum Framebuffer::completeness()
+bool Framebuffer::hasStencil()
 {
-    gl::Context *context = gl::getContext();
+    if (mStencilbufferType != GL_NONE)
+    {
+        DepthStencilbuffer *stencilbufferObject = getStencilbuffer();
 
+        if (stencilbufferObject)
+        {
+            return stencilbufferObject->getStencilSize() > 0;
+        }
+    }
+
+    return false;
+}
+
+bool Framebuffer::isMultisample()
+{
+    // If the framebuffer is not complete, attachment samples may be mismatched, and it
+    // cannot be used as a multisample framebuffer. If it is complete, it is required to
+    // have a color attachment, and all its attachments must have the same number of samples,
+    // so the number of samples for the colorbuffer will indicate whether the framebuffer is
+    // multisampled.
+    if (completeness() == GL_FRAMEBUFFER_COMPLETE && getColorbuffer()->getSamples() > 0)
+    {
+        return true;
+    }
+    else
+    {
+        return false;
+    }
+}
+
+GLenum Framebuffer::completeness()
+{
     int width = 0;
     int height = 0;
+    int samples = -1;
 
     if (mColorbufferType != GL_NONE)
     {
@@ -246,13 +305,29 @@ GLenum Framebuffer::completeness()
             return GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT;
         }
 
+        if (IsTextureTarget(mColorbufferType))
+        {
+            if (IsCompressed(colorbuffer->getFormat()))
+            {
+                return GL_FRAMEBUFFER_UNSUPPORTED;
+            }
+        }
+
         width = colorbuffer->getWidth();
         height = colorbuffer->getHeight();
+        samples = colorbuffer->getSamples();
     }
+    else
+    {
+        return GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT;
+    }
+
+    DepthStencilbuffer *depthbuffer = NULL;
+    DepthStencilbuffer *stencilbuffer = NULL;
 
     if (mDepthbufferType != GL_NONE)
     {
-        Depthbuffer *depthbuffer = context->getDepthbuffer(mDepthbufferHandle);
+        depthbuffer = getDepthbuffer();
 
         if (!depthbuffer)
         {
@@ -273,11 +348,28 @@ GLenum Framebuffer::completeness()
         {
             return GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS;
         }
+
+        if (samples == -1)
+        {
+            samples = depthbuffer->getSamples();
+        }
+        else if (samples != depthbuffer->getSamples())
+        {
+            return GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE_ANGLE;
+        }
+        
+        if (IsTextureTarget(mDepthbufferType))
+        {
+            if (IsCompressed(depthbuffer->getFormat()))
+            {
+                return GL_FRAMEBUFFER_UNSUPPORTED;
+            }
+        }
     }
 
     if (mStencilbufferType != GL_NONE)
     {
-        Stencilbuffer *stencilbuffer = context->getStencilbuffer(mStencilbufferHandle);
+        stencilbuffer = getStencilbuffer();
 
         if (!stencilbuffer)
         {
@@ -298,8 +390,66 @@ GLenum Framebuffer::completeness()
         {
             return GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS;
         }
+
+        if (samples == -1)
+        {
+            samples = stencilbuffer->getSamples();
+        }
+        else if (samples != stencilbuffer->getSamples())
+        {
+            return GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE_ANGLE;
+        }
+        
+        if (IsTextureTarget(mStencilbufferType))
+        {
+            if (IsCompressed(stencilbuffer->getFormat()))
+            {
+                return GL_FRAMEBUFFER_UNSUPPORTED;
+            }
+        }
+    }
+
+    if (mDepthbufferType == GL_RENDERBUFFER && mStencilbufferType == GL_RENDERBUFFER)
+    {
+        if (depthbuffer->getFormat() != GL_DEPTH24_STENCIL8_OES ||
+            stencilbuffer->getFormat() != GL_DEPTH24_STENCIL8_OES ||
+            depthbuffer->getSerial() != stencilbuffer->getSerial())
+        {
+            return GL_FRAMEBUFFER_UNSUPPORTED;
+        }
+    }
+
+    return GL_FRAMEBUFFER_COMPLETE;
+}
+
+DefaultFramebuffer::DefaultFramebuffer(Colorbuffer *color, DepthStencilbuffer *depthStencil)
+{
+    mColorbufferType = GL_RENDERBUFFER;
+    mDepthbufferType = GL_RENDERBUFFER;
+    mStencilbufferType = GL_RENDERBUFFER;
+
+    mColorbufferPointer.set(new Renderbuffer(0, color));
+
+    Renderbuffer *depthStencilRenderbuffer = new Renderbuffer(0, depthStencil);
+    mDepthbufferPointer.set(depthStencilRenderbuffer);
+    mStencilbufferPointer.set(depthStencilRenderbuffer);
+}
+
+int Framebuffer::getSamples()
+{
+    if (completeness() == GL_FRAMEBUFFER_COMPLETE)
+    {
+        return getColorbuffer()->getSamples();
+    }
+    else
+    {
+        return 0;
     }
+}
 
+GLenum DefaultFramebuffer::completeness()
+{
     return GL_FRAMEBUFFER_COMPLETE;
 }
+
 }
diff --git a/ANGLE/src/libGLESv2/Framebuffer.h b/ANGLE/src/libGLESv2/Framebuffer.h
index c35f940..0995145 100644
--- a/ANGLE/src/libGLESv2/Framebuffer.h
+++ b/ANGLE/src/libGLESv2/Framebuffer.h
@@ -15,19 +15,22 @@
 #include <d3d9.h>
 
 #include "common/angleutils.h"
+#include "libGLESv2/RefCountObject.h"
 
 namespace gl
 {
+class Renderbuffer;
 class Colorbuffer;
 class Depthbuffer;
 class Stencilbuffer;
+class DepthStencilbuffer;
 
 class Framebuffer
 {
   public:
     Framebuffer();
 
-    ~Framebuffer();
+    virtual ~Framebuffer();
 
     void setColorbuffer(GLenum type, GLuint colorbuffer);
     void setDepthbuffer(GLenum type, GLuint depthbuffer);
@@ -41,10 +44,11 @@ class Framebuffer
 
     unsigned int getRenderTargetSerial();
     unsigned int getDepthbufferSerial();
+    unsigned int getStencilbufferSerial();
 
     Colorbuffer *getColorbuffer();
-    Depthbuffer *getDepthbuffer();
-    Stencilbuffer *getStencilbuffer();
+    DepthStencilbuffer *getDepthbuffer();
+    DepthStencilbuffer *getStencilbuffer();
 
     GLenum getColorbufferType();
     GLenum getDepthbufferType();
@@ -54,20 +58,39 @@ class Framebuffer
     GLuint getDepthbufferHandle();
     GLuint getStencilbufferHandle();
 
-    GLenum completeness();
+    bool hasStencil();
+    bool isMultisample();
+    int getSamples();
 
-  private:
-    DISALLOW_COPY_AND_ASSIGN(Framebuffer);
+    virtual GLenum completeness();
 
-    GLuint mColorbufferHandle;
+  protected:
     GLenum mColorbufferType;
+    BindingPointer<Renderbuffer> mColorbufferPointer;
 
-    GLuint mDepthbufferHandle;
     GLenum mDepthbufferType;
+    BindingPointer<Renderbuffer> mDepthbufferPointer;
 
-    GLuint mStencilbufferHandle;
     GLenum mStencilbufferType;
+    BindingPointer<Renderbuffer> mStencilbufferPointer;
+
+  private:
+    DISALLOW_COPY_AND_ASSIGN(Framebuffer);
+
+    Renderbuffer *lookupRenderbuffer(GLenum type, GLuint handle) const;
+};
+
+class DefaultFramebuffer : public Framebuffer
+{
+  public:
+    DefaultFramebuffer(Colorbuffer *color, DepthStencilbuffer *depthStencil);
+
+    virtual GLenum completeness();
+
+  private:
+    DISALLOW_COPY_AND_ASSIGN(DefaultFramebuffer);
 };
+
 }
 
 #endif   // LIBGLESV2_FRAMEBUFFER_H_
diff --git a/ANGLE/src/libGLESv2/Program.cpp b/ANGLE/src/libGLESv2/Program.cpp
index 78253c7..a32bc9f 100644
--- a/ANGLE/src/libGLESv2/Program.cpp
+++ b/ANGLE/src/libGLESv2/Program.cpp
@@ -45,7 +45,7 @@ UniformLocation::UniformLocation(const std::string &name, unsigned int element,
 {
 }
 
-Program::Program()
+Program::Program(ResourceManager *manager, GLuint handle) : mResourceManager(manager), mHandle(handle)
 {
     mFragmentShader = NULL;
     mVertexShader = NULL;
@@ -62,6 +62,8 @@ Program::Program()
 
     mDeleteStatus = false;
 
+    mRefCount = 0;
+
     mSerial = issueSerial();
 }
 
@@ -71,12 +73,12 @@ Program::~Program()
 
     if (mVertexShader != NULL)
     {
-        mVertexShader->detach();
+        mVertexShader->release();
     }
 
     if (mFragmentShader != NULL)
     {
-        mFragmentShader->detach();
+        mFragmentShader->release();
     }
 }
 
@@ -90,7 +92,7 @@ bool Program::attachShader(Shader *shader)
         }
 
         mVertexShader = (VertexShader*)shader;
-        mVertexShader->attach();
+        mVertexShader->addRef();
     }
     else if (shader->getType() == GL_FRAGMENT_SHADER)
     {
@@ -100,7 +102,7 @@ bool Program::attachShader(Shader *shader)
         }
 
         mFragmentShader = (FragmentShader*)shader;
-        mFragmentShader->attach();
+        mFragmentShader->addRef();
     }
     else UNREACHABLE();
 
@@ -116,7 +118,7 @@ bool Program::detachShader(Shader *shader)
             return false;
         }
 
-        mVertexShader->detach();
+        mVertexShader->release();
         mVertexShader = NULL;
     }
     else if (shader->getType() == GL_FRAGMENT_SHADER)
@@ -126,7 +128,7 @@ bool Program::detachShader(Shader *shader)
             return false;
         }
 
-        mFragmentShader->detach();
+        mFragmentShader->release();
         mFragmentShader = NULL;
     }
     else UNREACHABLE();
@@ -1195,6 +1197,10 @@ bool Program::linkVaryings()
         }
     }
 
+    Context *context = getContext();
+    bool sm3 = context->supportsShaderModel3();
+    std::string varyingSemantic = (sm3 ? "COLOR" : "TEXCOORD");
+
     mVertexHLSL += "struct VS_INPUT\n"
                    "{\n";
 
@@ -1228,12 +1234,17 @@ bool Program::linkVaryings()
     {
         int registerSize = packing[r][3] ? 4 : (packing[r][2] ? 3 : (packing[r][1] ? 2 : 1));
 
-        mVertexHLSL += "    float" + str(registerSize) + " v" + str(r) + " : TEXCOORD" + str(r) + ";\n";
+        mVertexHLSL += "    float" + str(registerSize) + " v" + str(r) + " : " + varyingSemantic + str(r) + ";\n";
     }
 
     if (mFragmentShader->mUsesFragCoord)
     {
-        mVertexHLSL += "    float4 gl_FragCoord : TEXCOORD" + str(registers) + ";\n";
+        mVertexHLSL += "    float4 gl_FragCoord : " + varyingSemantic + str(registers) + ";\n";
+    }
+
+    if (mVertexShader->mUsesPointSize && sm3)
+    {
+        mVertexHLSL += "    float gl_PointSize : PSIZE;\n";
     }
 
     mVertexHLSL += "};\n"
@@ -1262,6 +1273,11 @@ bool Program::linkVaryings()
                    "    output.gl_Position.z = (gl_Position.z + gl_Position.w) * 0.5;\n"
                    "    output.gl_Position.w = gl_Position.w;\n";
 
+    if (mVertexShader->mUsesPointSize && sm3)
+    {
+        mVertexHLSL += "    output.gl_PointSize = clamp(gl_PointSize, 1.0, " + str((int)ALIASED_POINT_SIZE_RANGE_MAX_SM3) + ");\n";
+    }
+
     if (mFragmentShader->mUsesFragCoord)
     {
         mVertexHLSL += "    output.gl_FragCoord = gl_Position;\n";
@@ -1345,7 +1361,7 @@ bool Program::linkVaryings()
                 for (int j = 0; j < rows; j++)
                 {
                     std::string n = str(varying->reg + i * rows + j);
-                    mPixelHLSL += "    float4 v" + n + " : TEXCOORD" + n + ";\n";
+                    mPixelHLSL += "    float4 v" + n + " : " + varyingSemantic + n + ";\n";
                 }
             }
         }
@@ -1354,9 +1370,14 @@ bool Program::linkVaryings()
 
     if (mFragmentShader->mUsesFragCoord)
     {
-        mPixelHLSL += "    float4 gl_FragCoord : TEXCOORD" + str(registers) + ";\n";
+        mPixelHLSL += "    float4 gl_FragCoord : " + varyingSemantic + str(registers) + ";\n";
+    }
+
+    if (mFragmentShader->mUsesPointCoord && sm3)
+    {
+        mPixelHLSL += "    float2 gl_PointCoord : TEXCOORD0;\n";
     }
-        
+
     if (mFragmentShader->mUsesFrontFacing)
     {
         mPixelHLSL += "    float vFace : VFACE;\n";
@@ -1375,12 +1396,17 @@ bool Program::linkVaryings()
     if (mFragmentShader->mUsesFragCoord)
     {
         mPixelHLSL += "    float rhw = 1.0 / input.gl_FragCoord.w;\n"
-                      "    gl_FragCoord.x = (input.gl_FragCoord.x * rhw) * dx_Window.x + dx_Window.z;\n"
-                      "    gl_FragCoord.y = (input.gl_FragCoord.y * rhw) * dx_Window.y + dx_Window.w;\n"
+                      "    gl_FragCoord.x = (input.gl_FragCoord.x * rhw) * dx_Viewport.x + dx_Viewport.z;\n"
+                      "    gl_FragCoord.y = (input.gl_FragCoord.y * rhw) * dx_Viewport.y + dx_Viewport.w;\n"
                       "    gl_FragCoord.z = (input.gl_FragCoord.z * rhw) * dx_Depth.x + dx_Depth.y;\n"
                       "    gl_FragCoord.w = rhw;\n";
     }
 
+    if (mFragmentShader->mUsesPointCoord && sm3)
+    {
+        mPixelHLSL += "    gl_PointCoord = float2(input.gl_PointCoord.x, 1.0 - input.gl_PointCoord.y);\n";
+    }
+
     if (mFragmentShader->mUsesFrontFacing)
     {
         mPixelHLSL += "    gl_FrontFacing = dx_PointsOrLines || (dx_FrontCCW ? (input.vFace >= 0.0) : (input.vFace <= 0.0));\n";
@@ -1447,10 +1473,6 @@ void Program::link()
         return;
     }
 
-    Context *context = getContext();
-    const char *vertexProfile = context->getVertexShaderProfile();
-    const char *pixelProfile = context->getPixelShaderProfile();
-
     mPixelHLSL = mFragmentShader->getHLSL();
     mVertexHLSL = mVertexShader->getHLSL();
 
@@ -1459,6 +1481,10 @@ void Program::link()
         return;
     }
 
+    Context *context = getContext();
+    const char *vertexProfile = context->supportsShaderModel3() ? "vs_3_0" : "vs_2_0";
+    const char *pixelProfile = context->supportsShaderModel3() ? "ps_3_0" : "ps_2_0";
+
     ID3DXBuffer *vertexBinary = compileToBinary(mVertexHLSL.c_str(), vertexProfile, &mConstantTableVS);
     ID3DXBuffer *pixelBinary = compileToBinary(mPixelHLSL.c_str(), pixelProfile, &mConstantTablePS);
 
@@ -1503,7 +1529,7 @@ void Program::link()
             mDepthRangeFarLocation = getUniformLocation("gl_DepthRange.far", true);
             mDepthRangeDiffLocation = getUniformLocation("gl_DepthRange.diff", true);
             mDxDepthLocation = getUniformLocation("dx_Depth", true);
-            mDxWindowLocation = getUniformLocation("dx_Window", true);
+            mDxViewportLocation = getUniformLocation("dx_Viewport", true);
             mDxHalfPixelSizeLocation = getUniformLocation("dx_HalfPixelSize", true);
             mDxFrontCCWLocation = getUniformLocation("dx_FrontCCW", true);
             mDxPointsOrLinesLocation = getUniformLocation("dx_PointsOrLines", true);
@@ -2355,13 +2381,13 @@ void Program::unlink(bool destroy)
     {
         if (mFragmentShader)
         {
-            mFragmentShader->detach();
+            mFragmentShader->release();
             mFragmentShader = NULL;
         }
 
         if (mVertexShader)
         {
-            mVertexShader->detach();
+            mVertexShader->release();
             mVertexShader = NULL;
         }
     }
@@ -2412,7 +2438,7 @@ void Program::unlink(bool destroy)
     mDepthRangeNearLocation = -1;
     mDepthRangeFarLocation = -1;
     mDxDepthLocation = -1;
-    mDxWindowLocation = -1;
+    mDxViewportLocation = -1;
     mDxHalfPixelSizeLocation = -1;
     mDxFrontCCWLocation = -1;
     mDxPointsOrLinesLocation = -1;
@@ -2438,6 +2464,26 @@ bool Program::isValidated() const
     return mValidated;
 }
 
+void Program::release()
+{
+    mRefCount--;
+
+    if (mRefCount == 0 && mDeleteStatus)
+    {
+        mResourceManager->deleteProgram(mHandle);
+    }
+}
+
+void Program::addRef()
+{
+    mRefCount++;
+}
+
+unsigned int Program::getRefCount() const
+{
+    return mRefCount;
+}
+
 unsigned int Program::getSerial() const
 {
     return mSerial;
@@ -2737,9 +2783,9 @@ GLint Program::getDxDepthLocation() const
     return mDxDepthLocation;
 }
 
-GLint Program::getDxWindowLocation() const
+GLint Program::getDxViewportLocation() const
 {
-    return mDxWindowLocation;
+    return mDxViewportLocation;
 }
 
 GLint Program::getDxHalfPixelSizeLocation() const
diff --git a/ANGLE/src/libGLESv2/Program.h b/ANGLE/src/libGLESv2/Program.h
index e52f20e..3021b7a 100644
--- a/ANGLE/src/libGLESv2/Program.h
+++ b/ANGLE/src/libGLESv2/Program.h
@@ -20,6 +20,7 @@
 
 namespace gl
 {
+class ResourceManager;
 class FragmentShader;
 class VertexShader;
 
@@ -55,7 +56,7 @@ struct UniformLocation
 class Program
 {
   public:
-    Program();
+    Program(ResourceManager *manager, GLuint handle);
 
     ~Program();
 
@@ -97,7 +98,7 @@ class Program
     GLint getDepthRangeNearLocation() const;
     GLint getDepthRangeFarLocation() const;
     GLint getDxDepthLocation() const;
-    GLint getDxWindowLocation() const;
+    GLint getDxViewportLocation() const;
     GLint getDxHalfPixelSizeLocation() const;
     GLint getDxFrontCCWLocation() const;
     GLint getDxPointsOrLinesLocation() const;
@@ -119,6 +120,9 @@ class Program
     GLint getActiveUniformCount();
     GLint getActiveUniformMaxLength();
 
+    void addRef();
+    void release();
+    unsigned int getRefCount() const;
     void flagForDeletion();
     bool isFlaggedForDeletion() const;
 
@@ -204,7 +208,7 @@ class Program
     GLint mDepthRangeNearLocation;
     GLint mDepthRangeFarLocation;
     GLint mDxDepthLocation;
-    GLint mDxWindowLocation;
+    GLint mDxViewportLocation;
     GLint mDxHalfPixelSizeLocation;
     GLint mDxFrontCCWLocation;
     GLint mDxPointsOrLinesLocation;
@@ -214,9 +218,14 @@ class Program
     char *mInfoLog;
     bool mValidated;
 
+    unsigned int mRefCount;
+
     unsigned int mSerial;
 
     static unsigned int mCurrentSerial;
+
+    ResourceManager *mResourceManager;
+    const GLuint mHandle;
 };
 }
 
diff --git a/ANGLE/src/libGLESv2/RefCountObject.cpp b/ANGLE/src/libGLESv2/RefCountObject.cpp
new file mode 100644
index 0000000..e3fd36e
--- /dev/null
+++ b/ANGLE/src/libGLESv2/RefCountObject.cpp
@@ -0,0 +1,51 @@
+//
+// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// RefCountObject.cpp: Defines the gl::RefCountObject base class that provides
+// lifecycle support for GL objects using the traditional BindObject scheme, but
+// that need to be reference counted for correct cross-context deletion.
+// (Concretely, textures, buffers and renderbuffers.)
+
+#include "RefCountObject.h"
+
+namespace gl
+{
+
+RefCountObject::RefCountObject(GLuint id)
+{
+    mId = id;
+    mRefCount = 0;
+}
+
+RefCountObject::~RefCountObject()
+{
+}
+
+void RefCountObject::addRef() const
+{
+    mRefCount++;
+}
+
+void RefCountObject::release() const
+{
+    ASSERT(mRefCount > 0);
+
+    if (--mRefCount == 0)
+    {
+        delete this;
+    }
+}
+
+void RefCountObjectBindingPointer::set(RefCountObject *newObject)
+{
+    // addRef first in case newObject == mObject and this is the last reference to it.
+    if (newObject != NULL) newObject->addRef();
+    if (mObject != NULL) mObject->release();
+
+    mObject = newObject;
+}
+
+}
diff --git a/ANGLE/src/libGLESv2/RefCountObject.h b/ANGLE/src/libGLESv2/RefCountObject.h
new file mode 100644
index 0000000..a149350
--- /dev/null
+++ b/ANGLE/src/libGLESv2/RefCountObject.h
@@ -0,0 +1,70 @@
+//
+// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// RefCountObject.h: Defines the gl::RefCountObject base class that provides
+// lifecycle support for GL objects using the traditional BindObject scheme, but
+// that need to be reference counted for correct cross-context deletion.
+// (Concretely, textures, buffers and renderbuffers.)
+
+#ifndef LIBGLESV2_REFCOUNTOBJECT_H_
+#define LIBGLESV2_REFCOUNTOBJECT_H_
+
+#include <cstddef>
+
+#define GL_APICALL
+#include <GLES2/gl2.h>
+
+#include "common/debug.h"
+
+namespace gl
+{
+
+class RefCountObject
+{
+  public:
+    explicit RefCountObject(GLuint id);
+    virtual ~RefCountObject();
+
+    virtual void addRef() const;
+    virtual void release() const;
+
+    GLuint id() const { return mId; }
+    
+  private:
+    GLuint mId;
+
+    mutable std::size_t mRefCount;
+};
+
+class RefCountObjectBindingPointer
+{
+  protected:
+    RefCountObjectBindingPointer() : mObject(NULL) { }
+    ~RefCountObjectBindingPointer() { ASSERT(mObject == NULL); } // Objects have to be released before the resource manager is destroyed, so they must be explicitly cleaned up.
+
+    void set(RefCountObject *newObject);
+    RefCountObject *get() const { return mObject; }
+
+  public:
+    GLuint id() const { return (mObject != NULL) ? mObject->id() : 0; }
+    bool operator ! () const { return (get() == NULL); }
+
+  private:
+    RefCountObject *mObject;
+};
+
+template <class ObjectType>
+class BindingPointer : public RefCountObjectBindingPointer
+{
+  public:
+    void set(ObjectType *newObject) { RefCountObjectBindingPointer::set(newObject); }
+    ObjectType *get() const { return static_cast<ObjectType*>(RefCountObjectBindingPointer::get()); }
+    ObjectType *operator -> () const { return get(); }
+};
+
+}
+
+#endif   // LIBGLESV2_REFCOUNTOBJECT_H_
diff --git a/ANGLE/src/libGLESv2/Renderbuffer.cpp b/ANGLE/src/libGLESv2/Renderbuffer.cpp
index edd38ec..0eb4637 100644
--- a/ANGLE/src/libGLESv2/Renderbuffer.cpp
+++ b/ANGLE/src/libGLESv2/Renderbuffer.cpp
@@ -15,73 +15,148 @@
 
 namespace gl
 {
-unsigned int Renderbuffer::mCurrentSerial = 1;
+unsigned int RenderbufferStorage::mCurrentSerial = 1;
 
-Renderbuffer::Renderbuffer()
+Renderbuffer::Renderbuffer(GLuint id, RenderbufferStorage *storage) : RefCountObject(id)
 {
-    mWidth = 0;
-    mHeight = 0;
-    mFormat = GL_RGBA4; // default format, needs to be one of the expected renderbuffer formats
-    mSerial = issueSerial();
+    ASSERT(storage != NULL);
+    mStorage = storage;
 }
 
 Renderbuffer::~Renderbuffer()
 {
+    delete mStorage;
+}
+
+bool Renderbuffer::isColorbuffer() const
+{
+    return mStorage->isColorbuffer();
+}
+
+bool Renderbuffer::isDepthbuffer() const
+{
+    return mStorage->isDepthbuffer();
+}
+
+bool Renderbuffer::isStencilbuffer() const
+{
+    return mStorage->isStencilbuffer();
+}
+
+IDirect3DSurface9 *Renderbuffer::getRenderTarget()
+{
+    return mStorage->getRenderTarget();
+}
+
+IDirect3DSurface9 *Renderbuffer::getDepthStencil()
+{
+    return mStorage->getDepthStencil();
+}
+
+int Renderbuffer::getWidth() const
+{
+    return mStorage->getWidth();
+}
+
+int Renderbuffer::getHeight() const
+{
+    return mStorage->getHeight();
+}
+
+GLenum Renderbuffer::getFormat() const
+{
+    return mStorage->getFormat();
+}
+
+D3DFORMAT Renderbuffer::getD3DFormat() const
+{
+    return mStorage->getD3DFormat();
+}
+
+unsigned int Renderbuffer::getSerial() const
+{
+    return mStorage->getSerial();
+}
+
+void Renderbuffer::setStorage(RenderbufferStorage *newStorage)
+{
+    ASSERT(newStorage != NULL);
+
+    delete mStorage;
+    mStorage = newStorage;
+}
+
+RenderbufferStorage::RenderbufferStorage()
+{
+    mSerial = issueSerial();
+}
+
+RenderbufferStorage::~RenderbufferStorage()
+{
 }
 
-bool Renderbuffer::isColorbuffer()
+bool RenderbufferStorage::isColorbuffer() const
 {
     return false;
 }
 
-bool Renderbuffer::isDepthbuffer()
+bool RenderbufferStorage::isDepthbuffer() const
 {
     return false;
 }
 
-bool Renderbuffer::isStencilbuffer()
+bool RenderbufferStorage::isStencilbuffer() const
 {
     return false;
 }
 
-IDirect3DSurface9 *Renderbuffer::getRenderTarget()
+IDirect3DSurface9 *RenderbufferStorage::getRenderTarget()
 {
     return NULL;
 }
 
-IDirect3DSurface9 *Renderbuffer::getDepthStencil()
+IDirect3DSurface9 *RenderbufferStorage::getDepthStencil()
 {
     return NULL;
 }
 
-int Renderbuffer::getWidth()
+int RenderbufferStorage::getWidth() const
 {
     return mWidth;
 }
 
-int Renderbuffer::getHeight()
+int RenderbufferStorage::getHeight() const
 {
     return mHeight;
 }
 
-void Renderbuffer::setSize(int width, int height)
+void RenderbufferStorage::setSize(int width, int height)
 {
     mWidth = width;
     mHeight = height;
 }
 
-
-GLenum Renderbuffer::getFormat()
+GLenum RenderbufferStorage::getFormat() const
 {
     return mFormat;
 }
 
-unsigned int Renderbuffer::getSerial() const
+D3DFORMAT RenderbufferStorage::getD3DFormat() const
+{
+    return mD3DFormat;
+}
+
+GLsizei RenderbufferStorage::getSamples() const
+{
+    return mSamples;
+}
+
+unsigned int RenderbufferStorage::getSerial() const
 {
     return mSerial;
 }
 
-unsigned int Renderbuffer::issueSerial()
+unsigned int RenderbufferStorage::issueSerial()
 {
     return mCurrentSerial++;
 }
@@ -96,36 +171,59 @@ Colorbuffer::Colorbuffer(IDirect3DSurface9 *renderTarget) : mRenderTarget(render
         renderTarget->GetDesc(&description);
 
         setSize(description.Width, description.Height);
+        mD3DFormat = description.Format;
+        mSamples = es2dx::GetSamplesFromMultisampleType(description.MultiSampleType);
+    }
+    else
+    {
+        mD3DFormat = D3DFMT_UNKNOWN;
+        mSamples = 0;
     }
-
 }
 
-Colorbuffer::Colorbuffer(int width, int height, GLenum format)
+Colorbuffer::Colorbuffer(int width, int height, GLenum format, GLsizei samples)
 {
     IDirect3DDevice9 *device = getDevice();
 
     mRenderTarget = NULL;
-    HRESULT result = device->CreateRenderTarget(width, height, es2dx::ConvertRenderbufferFormat(format), 
-                                                D3DMULTISAMPLE_NONE, 0, FALSE, &mRenderTarget, NULL);
+    D3DFORMAT requestedFormat = es2dx::ConvertRenderbufferFormat(format);
+    int supportedSamples = getContext()->getNearestSupportedSamples(requestedFormat, samples);
 
-    if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
+    if (supportedSamples == -1)
     {
         error(GL_OUT_OF_MEMORY);
 
         return;
     }
 
-    ASSERT(SUCCEEDED(result));
+    if (width > 0 && height > 0)
+    {
+        HRESULT result = device->CreateRenderTarget(width, height, requestedFormat, 
+                                                    es2dx::GetMultisampleTypeFromSamples(supportedSamples), 0, FALSE, &mRenderTarget, NULL);
+
+        if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
+        {
+            error(GL_OUT_OF_MEMORY);
+
+            return;
+        }
+
+        ASSERT(SUCCEEDED(result));
+    }
 
     if (mRenderTarget)
     {
         setSize(width, height);
         mFormat = format;
+        mD3DFormat = requestedFormat;
+        mSamples = supportedSamples;
     }
     else
     {
         setSize(0, 0);
         mFormat = GL_RGBA4;
+        mD3DFormat = D3DFMT_UNKNOWN;
+        mSamples = 0;
     }
 }
 
@@ -137,12 +235,12 @@ Colorbuffer::~Colorbuffer()
     }
 }
 
-bool Colorbuffer::isColorbuffer()
+bool Colorbuffer::isColorbuffer() const
 {
     return true;
 }
 
-GLuint Colorbuffer::getRedSize()
+GLuint Colorbuffer::getRedSize() const
 {
     if (mRenderTarget)
     {
@@ -155,7 +253,7 @@ GLuint Colorbuffer::getRedSize()
     return 0;
 }
 
-GLuint Colorbuffer::getGreenSize()
+GLuint Colorbuffer::getGreenSize() const
 {
     if (mRenderTarget)
     {
@@ -168,7 +266,7 @@ GLuint Colorbuffer::getGreenSize()
     return 0;
 }
 
-GLuint Colorbuffer::getBlueSize()
+GLuint Colorbuffer::getBlueSize() const
 {
     if (mRenderTarget)
     {
@@ -181,7 +279,7 @@ GLuint Colorbuffer::getBlueSize()
     return 0;
 }
 
-GLuint Colorbuffer::getAlphaSize()
+GLuint Colorbuffer::getAlphaSize() const
 {
     if (mRenderTarget)
     {
@@ -199,7 +297,7 @@ IDirect3DSurface9 *Colorbuffer::getRenderTarget()
     return mRenderTarget;
 }
 
-Depthbuffer::Depthbuffer(IDirect3DSurface9 *depthStencil) : mDepthStencil(depthStencil)
+DepthStencilbuffer::DepthStencilbuffer(IDirect3DSurface9 *depthStencil) : mDepthStencil(depthStencil)
 {
     if (depthStencil)
     {
@@ -209,18 +307,34 @@ Depthbuffer::Depthbuffer(IDirect3DSurface9 *depthStencil) : mDepthStencil(depthS
         depthStencil->GetDesc(&description);
 
         setSize(description.Width, description.Height);
-        mFormat = GL_DEPTH_COMPONENT16; // If the renderbuffer parameters are queried, the calling function
-                                        // will expect one of the valid renderbuffer formats for use in 
-                                        // glRenderbufferStorage
+        mFormat = (description.Format == D3DFMT_D16 ? GL_DEPTH_COMPONENT16 : GL_DEPTH24_STENCIL8_OES);
+        mSamples = es2dx::GetSamplesFromMultisampleType(description.MultiSampleType); 
+        mD3DFormat = description.Format;
+    }
+    else
+    {
+        mD3DFormat = D3DFMT_UNKNOWN; 
+        mSamples = 0;
     }
 }
 
-Depthbuffer::Depthbuffer(int width, int height)
+DepthStencilbuffer::DepthStencilbuffer(int width, int height, GLsizei samples)
 {
     IDirect3DDevice9 *device = getDevice();
 
     mDepthStencil = NULL;
-    HRESULT result = device->CreateDepthStencilSurface(width, height, D3DFMT_D24S8, D3DMULTISAMPLE_NONE, 0, FALSE, &mDepthStencil, 0);
+    
+    int supportedSamples = getContext()->getNearestSupportedSamples(D3DFMT_D24S8, samples);
+
+    if (supportedSamples == -1)
+    {
+        error(GL_OUT_OF_MEMORY);
+
+        return;
+    }
+
+    HRESULT result = device->CreateDepthStencilSurface(width, height, D3DFMT_D24S8, es2dx::GetMultisampleTypeFromSamples(supportedSamples),
+                                                       0, FALSE, &mDepthStencil, 0);
 
     if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
     {
@@ -234,18 +348,20 @@ Depthbuffer::Depthbuffer(int width, int height)
     if (mDepthStencil)
     {
         setSize(width, height);
-        mFormat = GL_DEPTH_COMPONENT16; // If the renderbuffer parameters are queried, the calling function
-                                        // will expect one of the valid renderbuffer formats for use in 
-                                        // glRenderbufferStorage
+        mFormat = GL_DEPTH24_STENCIL8_OES;
+        mD3DFormat = D3DFMT_D24S8;
+        mSamples = supportedSamples;
     }
     else
     {
         setSize(0, 0);
         mFormat = GL_RGBA4; //default format
+        mD3DFormat = D3DFMT_UNKNOWN;
+        mSamples = 0;
     }
 }
 
-Depthbuffer::~Depthbuffer()
+DepthStencilbuffer::~DepthStencilbuffer()
 {
     if (mDepthStencil)
     {
@@ -253,12 +369,17 @@ Depthbuffer::~Depthbuffer()
     }
 }
 
-bool Depthbuffer::isDepthbuffer()
+bool DepthStencilbuffer::isDepthbuffer() const
+{
+    return true;
+}
+
+bool DepthStencilbuffer::isStencilbuffer() const
 {
     return true;
 }
 
-GLuint Depthbuffer::getDepthSize()
+GLuint DepthStencilbuffer::getDepthSize() const
 {
     if (mDepthStencil)
     {
@@ -271,85 +392,93 @@ GLuint Depthbuffer::getDepthSize()
     return 0;
 }
 
-IDirect3DSurface9 *Depthbuffer::getDepthStencil()
+GLuint DepthStencilbuffer::getStencilSize() const
+{
+    if (mDepthStencil)
+    {
+        D3DSURFACE_DESC description;
+        mDepthStencil->GetDesc(&description);
+
+        return es2dx::GetStencilSize(description.Format);
+    }
+
+    return 0;
+}
+
+IDirect3DSurface9 *DepthStencilbuffer::getDepthStencil()
 {
     return mDepthStencil;
 }
 
-Stencilbuffer::Stencilbuffer(IDirect3DSurface9 *depthStencil) : mDepthStencil(depthStencil)
+Depthbuffer::Depthbuffer(IDirect3DSurface9 *depthStencil) : DepthStencilbuffer(depthStencil)
 {
     if (depthStencil)
     {
-        depthStencil->AddRef();
-
-        D3DSURFACE_DESC description;
-        depthStencil->GetDesc(&description);
-
-        setSize(description.Width, description.Height);
-        mFormat = GL_STENCIL_INDEX8; // If the renderbuffer parameters are queried, the calling function
-                                     // will expect one of the valid renderbuffer formats for use in 
-                                     // glRenderbufferStorage
+        mFormat = GL_DEPTH_COMPONENT16; // If the renderbuffer parameters are queried, the calling function
+                                        // will expect one of the valid renderbuffer formats for use in 
+                                        // glRenderbufferStorage
     }
 }
 
-Stencilbuffer::Stencilbuffer(int width, int height)
+Depthbuffer::Depthbuffer(int width, int height, GLsizei samples) : DepthStencilbuffer(width, height, samples)
 {
-    IDirect3DDevice9 *device = getDevice();
-
-    mDepthStencil = NULL;
-    HRESULT result = device->CreateDepthStencilSurface(width, height, D3DFMT_D24S8, D3DMULTISAMPLE_NONE, 0, FALSE, &mDepthStencil, 0);
-
-    if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
+    if (getDepthStencil())
     {
-        error(GL_OUT_OF_MEMORY);
-
-        return;
+        mFormat = GL_DEPTH_COMPONENT16; // If the renderbuffer parameters are queried, the calling function
+                                        // will expect one of the valid renderbuffer formats for use in 
+                                        // glRenderbufferStorage
     }
+}
 
-    ASSERT(SUCCEEDED(result));
+Depthbuffer::~Depthbuffer()
+{
+}
 
-    if (mDepthStencil)
+bool Depthbuffer::isDepthbuffer() const
+{
+    return true;
+}
+
+bool Depthbuffer::isStencilbuffer() const
+{
+    return false;
+}
+
+Stencilbuffer::Stencilbuffer(IDirect3DSurface9 *depthStencil) : DepthStencilbuffer(depthStencil)
+{
+    if (depthStencil)
     {
-        setSize(width, height);
         mFormat = GL_STENCIL_INDEX8; // If the renderbuffer parameters are queried, the calling function
                                      // will expect one of the valid renderbuffer formats for use in 
                                      // glRenderbufferStorage
     }
     else
     {
-        setSize(0, 0);
         mFormat = GL_RGBA4; //default format
     }
 }
 
-Stencilbuffer::~Stencilbuffer()
+Stencilbuffer::Stencilbuffer(int width, int height, GLsizei samples) : DepthStencilbuffer(width, height, samples)
 {
-    if (mDepthStencil)
+    if (getDepthStencil())
     {
-        mDepthStencil->Release();
+        mFormat = GL_STENCIL_INDEX8; // If the renderbuffer parameters are queried, the calling function
+                                     // will expect one of the valid renderbuffer formats for use in 
+                                     // glRenderbufferStorage
     }
 }
 
-GLuint Stencilbuffer::getStencilSize()
+Stencilbuffer::~Stencilbuffer()
 {
-    if (mDepthStencil)
-    {
-        D3DSURFACE_DESC description;
-        mDepthStencil->GetDesc(&description);
-
-        return es2dx::GetStencilSize(description.Format);
-    }
-
-    return 0;
 }
 
-bool Stencilbuffer::isStencilbuffer()
+bool Stencilbuffer::isDepthbuffer() const
 {
-    return true;
+    return false;
 }
 
-IDirect3DSurface9 *Stencilbuffer::getDepthStencil()
+bool Stencilbuffer::isStencilbuffer() const
 {
-    return mDepthStencil;
+    return true;
 }
 }
diff --git a/ANGLE/src/libGLESv2/Renderbuffer.h b/ANGLE/src/libGLESv2/Renderbuffer.h
index 2c70ce9..cb8c06a 100644
--- a/ANGLE/src/libGLESv2/Renderbuffer.h
+++ b/ANGLE/src/libGLESv2/Renderbuffer.h
@@ -4,8 +4,9 @@
 // found in the LICENSE file.
 //
 
-// Renderbuffer.h: Defines the virtual gl::Renderbuffer class and its derived
-// classes Colorbuffer, Depthbuffer and Stencilbuffer. Implements GL renderbuffer
+// Renderbuffer.h: Defines the wrapper class gl::Renderbuffer, as well as the
+// class hierarchy used to store its contents: RenderbufferStorage, Colorbuffer,
+// DepthStencilbuffer, Depthbuffer and Stencilbuffer. Implements GL renderbuffer
 // objects and related functionality. [OpenGL ES 2.0.24] section 4.4.3 page 108.
 
 #ifndef LIBGLESV2_RENDERBUFFER_H_
@@ -16,26 +17,33 @@
 #include <d3d9.h>
 
 #include "common/angleutils.h"
+#include "libGLESv2/RefCountObject.h"
 
 namespace gl
 {
-class Renderbuffer
+
+// A class derived from RenderbufferStorage is created whenever glRenderbufferStorage
+// is called. The specific concrete type depends on whether the internal format is
+// colour depth, stencil or packed depth/stencil.
+class RenderbufferStorage
 {
   public:
-    Renderbuffer();
+    RenderbufferStorage();
 
-    virtual ~Renderbuffer();
+    virtual ~RenderbufferStorage() = 0;
 
-    virtual bool isColorbuffer();
-    virtual bool isDepthbuffer();
-    virtual bool isStencilbuffer();
+    virtual bool isColorbuffer() const;
+    virtual bool isDepthbuffer() const;
+    virtual bool isStencilbuffer() const;
 
     virtual IDirect3DSurface9 *getRenderTarget();
     virtual IDirect3DSurface9 *getDepthStencil();
 
-    virtual int getWidth();
-    virtual int getHeight();
-    GLenum getFormat();
+    virtual int getWidth() const;
+    virtual int getHeight() const;
+    virtual GLenum getFormat() const;
+    D3DFORMAT getD3DFormat() const;
+    GLsizei getSamples() const;
     unsigned int getSerial() const;
 
     static unsigned int issueSerial();
@@ -43,10 +51,12 @@ class Renderbuffer
   protected:
     void setSize(int width, int height);
     GLenum mFormat;
+    D3DFORMAT mD3DFormat;
+    GLsizei mSamples;
     unsigned int mSerial;
 
   private:
-    DISALLOW_COPY_AND_ASSIGN(Renderbuffer);
+    DISALLOW_COPY_AND_ASSIGN(RenderbufferStorage);
 
     static unsigned int mCurrentSerial;
 
@@ -54,20 +64,52 @@ class Renderbuffer
     int mHeight;
 };
 
-class Colorbuffer : public Renderbuffer
+// Renderbuffer implements the GL renderbuffer object.
+// It's only a wrapper for a RenderbufferStorage, but the internal object
+// can change whenever glRenderbufferStorage is called.
+class Renderbuffer : public RefCountObject
+{
+  public:
+    Renderbuffer(GLuint id, RenderbufferStorage *storage);
+
+    ~Renderbuffer();
+
+    bool isColorbuffer() const;
+    bool isDepthbuffer() const;
+    bool isStencilbuffer() const;
+
+    IDirect3DSurface9 *getRenderTarget();
+    IDirect3DSurface9 *getDepthStencil();
+
+    int getWidth() const;
+    int getHeight() const;
+    GLenum getFormat() const;
+    D3DFORMAT getD3DFormat() const;
+    unsigned int getSerial() const;
+
+    void setStorage(RenderbufferStorage *newStorage);
+    RenderbufferStorage *getStorage() { return mStorage; }
+
+  private:
+    DISALLOW_COPY_AND_ASSIGN(Renderbuffer);
+
+    RenderbufferStorage *mStorage;
+};
+
+class Colorbuffer : public RenderbufferStorage
 {
   public:
     explicit Colorbuffer(IDirect3DSurface9 *renderTarget);
-    Colorbuffer(int width, int height, GLenum format);
+    Colorbuffer(int width, int height, GLenum format, GLsizei samples);
 
     ~Colorbuffer();
 
-    bool isColorbuffer();
+    bool isColorbuffer() const;
 
-    GLuint getRedSize();
-    GLuint getGreenSize();
-    GLuint getBlueSize();
-    GLuint getAlphaSize();
+    GLuint getRedSize() const;
+    GLuint getGreenSize() const;
+    GLuint getBlueSize() const;
+    GLuint getAlphaSize() const;
 
     IDirect3DSurface9 *getRenderTarget();
 
@@ -78,42 +120,55 @@ class Colorbuffer : public Renderbuffer
     DISALLOW_COPY_AND_ASSIGN(Colorbuffer);
 };
 
-class Depthbuffer : public Renderbuffer
+class DepthStencilbuffer : public RenderbufferStorage
 {
   public:
-    explicit Depthbuffer(IDirect3DSurface9 *depthStencil);
-    Depthbuffer(int width, int height);
+    explicit DepthStencilbuffer(IDirect3DSurface9 *depthStencil);
+    DepthStencilbuffer(int width, int height, GLsizei samples);
 
-    ~Depthbuffer();
+    ~DepthStencilbuffer();
 
-    bool isDepthbuffer();
+    virtual bool isDepthbuffer() const;
+    virtual bool isStencilbuffer() const;
 
-    GLuint getDepthSize();
+    GLuint getDepthSize() const;
+    GLuint getStencilSize() const;
 
     IDirect3DSurface9 *getDepthStencil();
 
   private:
-    DISALLOW_COPY_AND_ASSIGN(Depthbuffer);
+    DISALLOW_COPY_AND_ASSIGN(DepthStencilbuffer);
     IDirect3DSurface9 *mDepthStencil;
 };
 
-class Stencilbuffer : public Renderbuffer
+class Depthbuffer : public DepthStencilbuffer
 {
   public:
-    explicit Stencilbuffer(IDirect3DSurface9 *depthStencil);
-    Stencilbuffer(int width, int height);
+    explicit Depthbuffer(IDirect3DSurface9 *depthStencil);
+    Depthbuffer(int width, int height, GLsizei samples);
 
-    ~Stencilbuffer();
+    ~Depthbuffer();
+
+    bool isDepthbuffer() const;
+    bool isStencilbuffer() const;
+
+  private:
+    DISALLOW_COPY_AND_ASSIGN(Depthbuffer);
+};
 
-    bool isStencilbuffer();
+class Stencilbuffer : public DepthStencilbuffer
+{
+  public:
+    explicit Stencilbuffer(IDirect3DSurface9 *depthStencil);
+    Stencilbuffer(int width, int height, GLsizei samples);
 
-    GLuint getStencilSize();
+    ~Stencilbuffer();
 
-    IDirect3DSurface9 *getDepthStencil();
+    bool isDepthbuffer() const;
+    bool isStencilbuffer() const;
 
   private:
     DISALLOW_COPY_AND_ASSIGN(Stencilbuffer);
-    IDirect3DSurface9 *mDepthStencil;
 };
 }
 
diff --git a/ANGLE/src/libGLESv2/ResourceManager.cpp b/ANGLE/src/libGLESv2/ResourceManager.cpp
new file mode 100644
index 0000000..12a86c1
--- /dev/null
+++ b/ANGLE/src/libGLESv2/ResourceManager.cpp
@@ -0,0 +1,340 @@
+//
+// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// ResourceManager.cpp: Implements the gl::ResourceManager class, which tracks and 
+// retrieves objects which may be shared by multiple Contexts.
+
+#include "libGLESv2/ResourceManager.h"
+
+#include "libGLESv2/Buffer.h"
+#include "libGLESv2/Program.h"
+#include "libGLESv2/RenderBuffer.h"
+#include "libGLESv2/Shader.h"
+#include "libGLESv2/Texture.h"
+
+namespace gl
+{
+ResourceManager::ResourceManager()
+{
+    mRefCount = 1;
+}
+
+ResourceManager::~ResourceManager()
+{
+    while (!mBufferMap.empty())
+    {
+        deleteBuffer(mBufferMap.begin()->first);
+    }
+
+    while (!mProgramMap.empty())
+    {
+        deleteProgram(mProgramMap.begin()->first);
+    }
+
+    while (!mShaderMap.empty())
+    {
+        deleteShader(mShaderMap.begin()->first);
+    }
+
+    while (!mRenderbufferMap.empty())
+    {
+        deleteRenderbuffer(mRenderbufferMap.begin()->first);
+    }
+
+    while (!mTextureMap.empty())
+    {
+        deleteTexture(mTextureMap.begin()->first);
+    }
+}
+
+void ResourceManager::addRef()
+{
+    mRefCount++;
+}
+
+void ResourceManager::release()
+{
+    if (--mRefCount == 0)
+    {
+        delete this;
+    }
+}
+
+// Returns an unused buffer name
+GLuint ResourceManager::createBuffer()
+{
+    unsigned int handle = 1;
+
+    while (mBufferMap.find(handle) != mBufferMap.end())
+    {
+        handle++;
+    }
+
+    mBufferMap[handle] = NULL;
+
+    return handle;
+}
+
+// Returns an unused shader/program name
+GLuint ResourceManager::createShader(GLenum type)
+{
+    unsigned int handle = 1;
+
+    while (mShaderMap.find(handle) != mShaderMap.end() || mProgramMap.find(handle) != mProgramMap.end())   // Shared name space
+    {
+        handle++;
+    }
+
+    if (type == GL_VERTEX_SHADER)
+    {
+        mShaderMap[handle] = new VertexShader(this, handle);
+    }
+    else if (type == GL_FRAGMENT_SHADER)
+    {
+        mShaderMap[handle] = new FragmentShader(this, handle);
+    }
+    else UNREACHABLE();
+
+    return handle;
+}
+
+// Returns an unused program/shader name
+GLuint ResourceManager::createProgram()
+{
+    unsigned int handle = 1;
+
+    while (mProgramMap.find(handle) != mProgramMap.end() || mShaderMap.find(handle) != mShaderMap.end())   // Shared name space
+    {
+        handle++;
+    }
+
+    mProgramMap[handle] = new Program(this, handle);
+
+    return handle;
+}
+
+// Returns an unused texture name
+GLuint ResourceManager::createTexture()
+{
+    unsigned int handle = 1;
+
+    while (mTextureMap.find(handle) != mTextureMap.end())
+    {
+        handle++;
+    }
+
+    mTextureMap[handle] = NULL;
+
+    return handle;
+}
+
+// Returns an unused renderbuffer name
+GLuint ResourceManager::createRenderbuffer()
+{
+    unsigned int handle = 1;
+
+    while (mRenderbufferMap.find(handle) != mRenderbufferMap.end())
+    {
+        handle++;
+    }
+
+    mRenderbufferMap[handle] = NULL;
+
+    return handle;
+}
+
+void ResourceManager::deleteBuffer(GLuint buffer)
+{
+    BufferMap::iterator bufferObject = mBufferMap.find(buffer);
+
+    if (bufferObject != mBufferMap.end())
+    {
+        if (bufferObject->second) bufferObject->second->release();
+        mBufferMap.erase(bufferObject);
+    }
+}
+
+void ResourceManager::deleteShader(GLuint shader)
+{
+    ShaderMap::iterator shaderObject = mShaderMap.find(shader);
+
+    if (shaderObject != mShaderMap.end())
+    {
+        if (shaderObject->second->getRefCount() == 0)
+        {
+            delete shaderObject->second;
+            mShaderMap.erase(shaderObject);
+        }
+        else
+        {
+            shaderObject->second->flagForDeletion();
+        }
+    }
+}
+
+void ResourceManager::deleteProgram(GLuint program)
+{
+    ProgramMap::iterator programObject = mProgramMap.find(program);
+
+    if (programObject != mProgramMap.end())
+    {
+        if (programObject->second->getRefCount() == 0)
+        {
+            delete programObject->second;
+            mProgramMap.erase(programObject);
+        }
+        else
+        { 
+            programObject->second->flagForDeletion();
+        }
+    }
+}
+
+void ResourceManager::deleteTexture(GLuint texture)
+{
+    TextureMap::iterator textureObject = mTextureMap.find(texture);
+
+    if (textureObject != mTextureMap.end())
+    {
+        if (textureObject->second) textureObject->second->release();
+        mTextureMap.erase(textureObject);
+    }
+}
+
+void ResourceManager::deleteRenderbuffer(GLuint renderbuffer)
+{
+    RenderbufferMap::iterator renderbufferObject = mRenderbufferMap.find(renderbuffer);
+
+    if (renderbufferObject != mRenderbufferMap.end())
+    {
+        if (renderbufferObject->second) renderbufferObject->second->release();
+        mRenderbufferMap.erase(renderbufferObject);
+    }
+}
+
+Buffer *ResourceManager::getBuffer(unsigned int handle)
+{
+    BufferMap::iterator buffer = mBufferMap.find(handle);
+
+    if (buffer == mBufferMap.end())
+    {
+        return NULL;
+    }
+    else
+    {
+        return buffer->second;
+    }
+}
+
+Shader *ResourceManager::getShader(unsigned int handle)
+{
+    ShaderMap::iterator shader = mShaderMap.find(handle);
+
+    if (shader == mShaderMap.end())
+    {
+        return NULL;
+    }
+    else
+    {
+        return shader->second;
+    }
+}
+
+Texture *ResourceManager::getTexture(unsigned int handle)
+{
+    if (handle == 0) return NULL;
+
+    TextureMap::iterator texture = mTextureMap.find(handle);
+
+    if (texture == mTextureMap.end())
+    {
+        return NULL;
+    }
+    else
+    {
+        return texture->second;
+    }
+}
+
+Program *ResourceManager::getProgram(unsigned int handle)
+{
+    ProgramMap::iterator program = mProgramMap.find(handle);
+
+    if (program == mProgramMap.end())
+    {
+        return NULL;
+    }
+    else
+    {
+        return program->second;
+    }
+}
+
+Renderbuffer *ResourceManager::getRenderbuffer(unsigned int handle)
+{
+    RenderbufferMap::iterator renderbuffer = mRenderbufferMap.find(handle);
+
+    if (renderbuffer == mRenderbufferMap.end())
+    {
+        return NULL;
+    }
+    else
+    {
+        return renderbuffer->second;
+    }
+}
+
+void ResourceManager::setRenderbuffer(GLuint handle, Renderbuffer *buffer)
+{
+    mRenderbufferMap[handle] = buffer;
+}
+
+void ResourceManager::checkBufferAllocation(unsigned int buffer)
+{
+    if (buffer != 0 && !getBuffer(buffer))
+    {
+        Buffer *bufferObject = new Buffer(buffer);
+        mBufferMap[buffer] = bufferObject;
+        bufferObject->addRef();
+    }
+}
+
+void ResourceManager::checkTextureAllocation(GLuint texture, SamplerType type)
+{
+    if (!getTexture(texture) && texture != 0)
+    {
+        Texture *textureObject;
+
+        if (type == SAMPLER_2D)
+        {
+            textureObject = new Texture2D(texture);
+        }
+        else if (type == SAMPLER_CUBE)
+        {
+            textureObject = new TextureCubeMap(texture);
+        }
+        else
+        {
+            UNREACHABLE();
+            return;
+        }
+
+        mTextureMap[texture] = textureObject;
+        textureObject->addRef();
+    }
+}
+
+void ResourceManager::checkRenderbufferAllocation(GLuint renderbuffer)
+{
+    if (renderbuffer != 0 && !getRenderbuffer(renderbuffer))
+    {
+        Renderbuffer *renderbufferObject = new Renderbuffer(renderbuffer, new Colorbuffer(0, 0, GL_RGBA4, 0));
+        mRenderbufferMap[renderbuffer] = renderbufferObject;
+        renderbufferObject->addRef();
+    }
+}
+
+}
diff --git a/ANGLE/src/libGLESv2/ResourceManager.h b/ANGLE/src/libGLESv2/ResourceManager.h
new file mode 100644
index 0000000..346e51f
--- /dev/null
+++ b/ANGLE/src/libGLESv2/ResourceManager.h
@@ -0,0 +1,92 @@
+//
+// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+
+// ResourceManager.h : Defines the ResourceManager class, which tracks objects
+// shared by multiple GL contexts.
+
+#ifndef LIBGLESV2_RESOURCEMANAGER_H_
+#define LIBGLESV2_RESOURCEMANAGER_H_
+
+#define GL_APICALL
+#include <GLES2/gl2.h>
+
+#include <map>
+
+#include "common/angleutils.h"
+
+namespace gl
+{
+class Buffer;
+class Shader;
+class Program;
+class Texture;
+class Renderbuffer;
+
+enum SamplerType
+{
+    SAMPLER_2D,
+    SAMPLER_CUBE,
+
+    SAMPLER_TYPE_COUNT
+};
+
+class ResourceManager
+{
+  public:
+    ResourceManager();
+    ~ResourceManager();
+
+    void addRef();
+    void release();
+
+    GLuint createBuffer();
+    GLuint createShader(GLenum type);
+    GLuint createProgram();
+    GLuint createTexture();
+    GLuint createRenderbuffer();
+
+    void deleteBuffer(GLuint buffer);
+    void deleteShader(GLuint shader);
+    void deleteProgram(GLuint program);
+    void deleteTexture(GLuint texture);
+    void deleteRenderbuffer(GLuint renderbuffer);
+
+    Buffer *getBuffer(GLuint handle);
+    Shader *getShader(GLuint handle);
+    Program *getProgram(GLuint handle);
+    Texture *getTexture(GLuint handle);
+    Renderbuffer *getRenderbuffer(GLuint handle);
+    
+    void setRenderbuffer(GLuint handle, Renderbuffer *renderbuffer);
+
+    void checkBufferAllocation(unsigned int buffer);
+    void checkTextureAllocation(GLuint texture, SamplerType type);
+    void checkRenderbufferAllocation(GLuint renderbuffer);
+
+  private:
+    DISALLOW_COPY_AND_ASSIGN(ResourceManager);
+
+    std::size_t mRefCount;
+
+    typedef std::map<GLuint, Buffer*> BufferMap;
+    BufferMap mBufferMap;
+
+    typedef std::map<GLuint, Shader*> ShaderMap;
+    ShaderMap mShaderMap;
+
+    typedef std::map<GLuint, Program*> ProgramMap;
+    ProgramMap mProgramMap;
+
+    typedef std::map<GLuint, Texture*> TextureMap;
+    TextureMap mTextureMap;
+
+    typedef std::map<GLuint, Renderbuffer*> RenderbufferMap;
+    RenderbufferMap mRenderbufferMap;
+};
+
+}
+
+#endif // LIBGLESV2_RESOURCEMANAGER_H_
diff --git a/ANGLE/src/libGLESv2/Shader.cpp b/ANGLE/src/libGLESv2/Shader.cpp
index 730c1b5..b73ef2a 100644
--- a/ANGLE/src/libGLESv2/Shader.cpp
+++ b/ANGLE/src/libGLESv2/Shader.cpp
@@ -21,7 +21,7 @@ namespace gl
 void *Shader::mFragmentCompiler = NULL;
 void *Shader::mVertexCompiler = NULL;
 
-Shader::Shader(Context *context, GLuint handle) : mHandle(handle), mContext(context)
+Shader::Shader(ResourceManager *manager, GLuint handle) : mHandle(handle), mResourceManager(manager)
 {
     mSource = NULL;
     mHlsl = NULL;
@@ -35,21 +35,22 @@ Shader::Shader(Context *context, GLuint handle) : mHandle(handle), mContext(cont
         if (result)
         {
             TBuiltInResource resources;
-            resources.maxVertexAttribs = MAX_VERTEX_ATTRIBS;
-            resources.maxVertexUniformVectors = MAX_VERTEX_UNIFORM_VECTORS;
-            resources.maxVaryingVectors = MAX_VARYING_VECTORS;
-            resources.maxVertexTextureImageUnits = MAX_VERTEX_TEXTURE_IMAGE_UNITS;
-            resources.maxCombinedTextureImageUnits = MAX_COMBINED_TEXTURE_IMAGE_UNITS;
-            resources.maxTextureImageUnits = MAX_TEXTURE_IMAGE_UNITS;
-            resources.maxFragmentUniformVectors = MAX_FRAGMENT_UNIFORM_VECTORS;
-            resources.maxDrawBuffers = MAX_DRAW_BUFFERS;
+            ShInitBuiltInResource(&resources);
+            resources.MaxVertexAttribs = MAX_VERTEX_ATTRIBS;
+            resources.MaxVertexUniformVectors = MAX_VERTEX_UNIFORM_VECTORS;
+            resources.MaxVaryingVectors = MAX_VARYING_VECTORS;
+            resources.MaxVertexTextureImageUnits = MAX_VERTEX_TEXTURE_IMAGE_UNITS;
+            resources.MaxCombinedTextureImageUnits = MAX_COMBINED_TEXTURE_IMAGE_UNITS;
+            resources.MaxTextureImageUnits = MAX_TEXTURE_IMAGE_UNITS;
+            resources.MaxFragmentUniformVectors = MAX_FRAGMENT_UNIFORM_VECTORS;
+            resources.MaxDrawBuffers = MAX_DRAW_BUFFERS;
 
             mFragmentCompiler = ShConstructCompiler(EShLangFragment, EShSpecGLES2, &resources);
             mVertexCompiler = ShConstructCompiler(EShLangVertex, EShSpecGLES2, &resources);
         }
     }
 
-    mAttachCount = 0;
+    mRefCount = 0;
     mDeleteStatus = false;
 }
 
@@ -187,24 +188,24 @@ const char *Shader::getHLSL()
     return mHlsl;
 }
 
-void Shader::attach()
+void Shader::addRef()
 {
-    mAttachCount++;
+    mRefCount++;
 }
 
-void Shader::detach()
+void Shader::release()
 {
-    mAttachCount--;
+    mRefCount--;
 
-    if (mAttachCount == 0 && mDeleteStatus)
+    if (mRefCount == 0 && mDeleteStatus)
     {
-        mContext->deleteShader(mHandle);
+        mResourceManager->deleteShader(mHandle);
     }
 }
 
-bool Shader::isAttached() const
+unsigned int Shader::getRefCount() const
 {
-    return mAttachCount > 0;
+    return mRefCount;
 }
 
 bool Shader::isFlaggedForDeletion() const
@@ -262,6 +263,8 @@ void Shader::parseVaryings()
 
         mUsesFragCoord = strstr(mHlsl, "GL_USES_FRAG_COORD") != NULL;
         mUsesFrontFacing = strstr(mHlsl, "GL_USES_FRONT_FACING") != NULL;
+        mUsesPointSize = strstr(mHlsl, "GL_USES_POINT_SIZE") != NULL;
+        mUsesPointCoord = strstr(mHlsl, "GL_USES_POINT_COORD") != NULL;
     }
 }
 
@@ -415,7 +418,7 @@ bool Shader::compareVarying(const Varying &x, const Varying &y)
     return false;
 }
 
-VertexShader::VertexShader(Context *context, GLuint handle) : Shader(context, handle)
+VertexShader::VertexShader(ResourceManager *manager, GLuint handle) : Shader(manager, handle)
 {
 }
 
@@ -479,7 +482,7 @@ void VertexShader::parseAttributes()
     }
 }
 
-FragmentShader::FragmentShader(Context *context, GLuint handle) : Shader(context, handle)
+FragmentShader::FragmentShader(ResourceManager *manager, GLuint handle) : Shader(manager, handle)
 {
 }
 
diff --git a/ANGLE/src/libGLESv2/Shader.h b/ANGLE/src/libGLESv2/Shader.h
index 777c236..5eaa053 100644
--- a/ANGLE/src/libGLESv2/Shader.h
+++ b/ANGLE/src/libGLESv2/Shader.h
@@ -18,7 +18,7 @@
 #include <list>
 #include <vector>
 
-#include "libGLESv2/Context.h"
+#include "libGLESv2/ResourceManager.h"
 
 namespace gl
 {
@@ -45,7 +45,7 @@ class Shader
     friend Program;
 
   public:
-    Shader(Context *context, GLuint handle);
+    Shader(ResourceManager *manager, GLuint handle);
 
     virtual ~Shader();
 
@@ -63,9 +63,9 @@ class Shader
     bool isCompiled();
     const char *getHLSL();
 
-    void attach();
-    void detach();
-    bool isAttached() const;
+    void addRef();
+    void release();
+    unsigned int getRefCount() const;
     bool isFlaggedForDeletion() const;
     void flagForDeletion();
 
@@ -82,8 +82,8 @@ class Shader
     static bool compareVarying(const Varying &x, const Varying &y);
 
     const GLuint mHandle;
-    int mAttachCount;     // Number of program objects this shader is attached to
-    bool mDeleteStatus;   // Flag to indicate that the shader can be deleted when no longer in use
+    unsigned int mRefCount;     // Number of program objects this shader is attached to
+    bool mDeleteStatus;         // Flag to indicate that the shader can be deleted when no longer in use
 
     char *mSource;
     char *mHlsl;
@@ -93,8 +93,10 @@ class Shader
 
     bool mUsesFragCoord;
     bool mUsesFrontFacing;
+    bool mUsesPointSize;
+    bool mUsesPointCoord;
 
-    Context *mContext;
+    ResourceManager *mResourceManager;
 
     static void *mFragmentCompiler;
     static void *mVertexCompiler;
@@ -121,7 +123,7 @@ class VertexShader : public Shader
     friend Program;
 
   public:
-    VertexShader(Context *context, GLuint handle);
+    VertexShader(ResourceManager *manager, GLuint handle);
 
     ~VertexShader();
 
@@ -140,7 +142,7 @@ class VertexShader : public Shader
 class FragmentShader : public Shader
 {
   public:
-    FragmentShader(Context *context, GLuint handle);
+    FragmentShader(ResourceManager *manager, GLuint handle);
 
     ~FragmentShader();
 
diff --git a/ANGLE/src/libGLESv2/Texture.cpp b/ANGLE/src/libGLESv2/Texture.cpp
index 4079d43..2e0b1e3 100644
--- a/ANGLE/src/libGLESv2/Texture.cpp
+++ b/ANGLE/src/libGLESv2/Texture.cpp
@@ -23,7 +23,7 @@ namespace gl
 {
 
 Texture::Image::Image()
-  : width(0), height(0), dirty(false), surface(NULL)
+  : width(0), height(0), dirty(false), surface(NULL), format(GL_NONE)
 {
 }
 
@@ -32,13 +32,16 @@ Texture::Image::~Image()
   if (surface) surface->Release();
 }
 
-Texture::Texture(Context *context) : mContext(context)
+Texture::Texture(GLuint id) : RefCountObject(id)
 {
     mMinFilter = GL_NEAREST_MIPMAP_LINEAR;
     mMagFilter = GL_LINEAR;
     mWrapS = GL_REPEAT;
     mWrapT = GL_REPEAT;
 
+    mWidth = 0;
+    mHeight = 0;
+
     mDirtyMetaData = true;
     mDirty = true;
     mIsRenderable = false;
@@ -51,7 +54,8 @@ Texture::~Texture()
 
 Blit *Texture::getBlitter()
 {
-    return mContext->getBlitter();
+    Context *context = getContext();
+    return context->getBlitter();
 }
 
 // Returns true on successful filter state update (valid enum parameter)
@@ -173,7 +177,15 @@ GLuint Texture::getHeight() const
 // Selects an internal Direct3D 9 format for storing an Image
 D3DFORMAT Texture::selectFormat(GLenum format)
 {
-    return D3DFMT_A8R8G8B8;
+    if (format == GL_COMPRESSED_RGB_S3TC_DXT1_EXT ||
+        format == GL_COMPRESSED_RGBA_S3TC_DXT1_EXT)
+    {
+        return D3DFMT_DXT1;
+    }
+    else
+    {
+        return D3DFMT_A8R8G8B8;
+    }
 }
 
 int Texture::imagePitch(const Image &img) const
@@ -188,126 +200,282 @@ void Texture::loadImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei
 {
     GLsizei inputPitch = ComputePitch(width, format, type, unpackAlignment);
 
+    switch (format)
+    {
+      case GL_ALPHA:
+        loadAlphaImageData(xoffset, yoffset, width, height, inputPitch, input, outputPitch, output);
+        break;
+
+      case GL_LUMINANCE:
+        loadLuminanceImageData(xoffset, yoffset, width, height, inputPitch, input, outputPitch, output);
+        break;
+
+      case GL_LUMINANCE_ALPHA:
+        loadLuminanceAlphaImageData(xoffset, yoffset, width, height, inputPitch, input, outputPitch, output);
+        break;
+
+      case GL_RGB:
+        switch (type)
+        {
+          case GL_UNSIGNED_BYTE:
+            loadRGBUByteImageData(xoffset, yoffset, width, height, inputPitch, input, outputPitch, output);
+            break;
+
+          case GL_UNSIGNED_SHORT_5_6_5:
+            loadRGB565ImageData(xoffset, yoffset, width, height, inputPitch, input, outputPitch, output);
+            break;
+
+          default: UNREACHABLE();
+        }
+        break;
+
+      case GL_RGBA:
+        switch (type)
+        {
+          case GL_UNSIGNED_BYTE:
+            loadRGBAUByteImageData(xoffset, yoffset, width, height, inputPitch, input, outputPitch, output);
+            break;
+
+          case GL_UNSIGNED_SHORT_4_4_4_4:
+            loadRGBA4444ImageData(xoffset, yoffset, width, height, inputPitch, input, outputPitch, output);
+            break;
+
+          case GL_UNSIGNED_SHORT_5_5_5_1:
+            loadRGBA5551ImageData(xoffset, yoffset, width, height, inputPitch, input, outputPitch, output);
+            break;
+
+          default: UNREACHABLE();
+        }
+        break;
+      case GL_BGRA_EXT:
+        switch (type)
+        {
+          case GL_UNSIGNED_BYTE:
+            loadBGRAImageData(xoffset, yoffset, width, height, inputPitch, input, outputPitch, output);
+            break;
+
+          default: UNREACHABLE();
+        }
+        break;
+      default: UNREACHABLE();
+    }
+}
+
+void Texture::loadAlphaImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                 size_t inputPitch, const void *input, size_t outputPitch, void *output) const
+{
+    const unsigned char *source = NULL;
+    unsigned char *dest = NULL;
+    
     for (int y = 0; y < height; y++)
     {
-        const unsigned char *source = static_cast<const unsigned char*>(input) + y * inputPitch;
-        const unsigned short *source16 = reinterpret_cast<const unsigned short*>(source);
-        unsigned char *dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
+        source = static_cast<const unsigned char*>(input) + y * inputPitch;
+        dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
+        for (int x = 0; x < width; x++)
+        {
+            dest[4 * x + 0] = 0;
+            dest[4 * x + 1] = 0;
+            dest[4 * x + 2] = 0;
+            dest[4 * x + 3] = source[x];
+        }
+    }
+}
 
+void Texture::loadLuminanceImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                     size_t inputPitch, const void *input, size_t outputPitch, void *output) const
+{
+    const unsigned char *source = NULL;
+    unsigned char *dest = NULL;
+
+    for (int y = 0; y < height; y++)
+    {
+        source = static_cast<const unsigned char*>(input) + y * inputPitch;
+        dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
         for (int x = 0; x < width; x++)
         {
-            unsigned char r;
-            unsigned char g;
-            unsigned char b;
-            unsigned char a;
+            dest[4 * x + 0] = source[x];
+            dest[4 * x + 1] = source[x];
+            dest[4 * x + 2] = source[x];
+            dest[4 * x + 3] = 0xFF;
+        }
+    }
+}
 
-            switch (format)
-            {
-              case GL_ALPHA:
-                a = source[x];
-                r = 0;
-                g = 0;
-                b = 0;
-                break;
-
-              case GL_LUMINANCE:
-                r = source[x];
-                g = source[x];
-                b = source[x];
-                a = 0xFF;
-                break;
-
-              case GL_LUMINANCE_ALPHA:
-                r = source[2*x+0];
-                g = source[2*x+0];
-                b = source[2*x+0];
-                a = source[2*x+1];
-                break;
-
-              case GL_RGB:
-                switch (type)
-                {
-                  case GL_UNSIGNED_BYTE:
-                    r = source[x * 3 + 0];
-                    g = source[x * 3 + 1];
-                    b = source[x * 3 + 2];
-                    a = 0xFF;
-                    break;
-
-                  case GL_UNSIGNED_SHORT_5_6_5:
-                    {
-                        unsigned short rgba = source16[x];
+void Texture::loadLuminanceAlphaImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                          size_t inputPitch, const void *input, size_t outputPitch, void *output) const
+{
+    const unsigned char *source = NULL;
+    unsigned char *dest = NULL;
 
-                        a = 0xFF;
-                        b = ((rgba & 0x001F) << 3) | ((rgba & 0x001F) >> 2);
-                        g = ((rgba & 0x07E0) >> 3) | ((rgba & 0x07E0) >> 9);
-                        r = ((rgba & 0xF800) >> 8) | ((rgba & 0xF800) >> 13);
-                    }
-                    break;
+    for (int y = 0; y < height; y++)
+    {
+        source = static_cast<const unsigned char*>(input) + y * inputPitch;
+        dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
+        for (int x = 0; x < width; x++)
+        {
+            dest[4 * x + 0] = source[2*x+0];
+            dest[4 * x + 1] = source[2*x+0];
+            dest[4 * x + 2] = source[2*x+0];
+            dest[4 * x + 3] = source[2*x+1];
+        }
+    }
+}
 
-                  default: UNREACHABLE();
-                }
-                break;
+void Texture::loadRGBUByteImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                    size_t inputPitch, const void *input, size_t outputPitch, void *output) const
+{
+    const unsigned char *source = NULL;
+    unsigned char *dest = NULL;
 
-              case GL_RGBA:
-                switch (type)
-                {
-                  case GL_UNSIGNED_BYTE:
-                    r = source[x * 4 + 0];
-                    g = source[x * 4 + 1];
-                    b = source[x * 4 + 2];
-                    a = source[x * 4 + 3];
-                    break;
-
-                  case GL_UNSIGNED_SHORT_4_4_4_4:
-                    {
-                        unsigned short rgba = source16[x];
+    for (int y = 0; y < height; y++)
+    {
+        source = static_cast<const unsigned char*>(input) + y * inputPitch;
+        dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
+        for (int x = 0; x < width; x++)
+        {
+            dest[4 * x + 0] = source[x * 3 + 2];
+            dest[4 * x + 1] = source[x * 3 + 1];
+            dest[4 * x + 2] = source[x * 3 + 0];
+            dest[4 * x + 3] = 0xFF;
+        }
+    }
+}
 
-                        a = ((rgba & 0x000F) << 4) | ((rgba & 0x000F) >> 0);
-                        b = ((rgba & 0x00F0) << 0) | ((rgba & 0x00F0) >> 4);
-                        g = ((rgba & 0x0F00) >> 4) | ((rgba & 0x0F00) >> 8);
-                        r = ((rgba & 0xF000) >> 8) | ((rgba & 0xF000) >> 12);
-                    }
-                    break;
+void Texture::loadRGB565ImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                  size_t inputPitch, const void *input, size_t outputPitch, void *output) const
+{
+    const unsigned short *source = NULL;
+    unsigned char *dest = NULL;
 
-                  case GL_UNSIGNED_SHORT_5_5_5_1:
-                    {
-                        unsigned short rgba = source16[x];
+    for (int y = 0; y < height; y++)
+    {
+        source = reinterpret_cast<const unsigned short*>(static_cast<const unsigned char*>(input) + y * inputPitch);
+        dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
+        for (int x = 0; x < width; x++)
+        {
+            unsigned short rgba = source[x];
+            dest[4 * x + 0] = ((rgba & 0x001F) << 3) | ((rgba & 0x001F) >> 2);
+            dest[4 * x + 1] = ((rgba & 0x07E0) >> 3) | ((rgba & 0x07E0) >> 9);
+            dest[4 * x + 2] = ((rgba & 0xF800) >> 8) | ((rgba & 0xF800) >> 13);
+            dest[4 * x + 3] = 0xFF;
+        }
+    }
+}
 
-                        a = (rgba & 0x0001) ? 0xFF : 0;
-                        b = ((rgba & 0x003E) << 2) | ((rgba & 0x003E) >> 3);
-                        g = ((rgba & 0x07C0) >> 3) | ((rgba & 0x07C0) >> 8);
-                        r = ((rgba & 0xF800) >> 8) | ((rgba & 0xF800) >> 13);
-                    }
-                    break;
+void Texture::loadRGBAUByteImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                     size_t inputPitch, const void *input, size_t outputPitch, void *output) const
+{
+    const unsigned char *source = NULL;
+    unsigned char *dest = NULL;
 
-                  default: UNREACHABLE();
-                }
-                break;
-              default: UNREACHABLE();
-            }
+    for (int y = 0; y < height; y++)
+    {
+        source = static_cast<const unsigned char*>(input) + y * inputPitch;
+        dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
+        for (int x = 0; x < width; x++)
+        {
+            dest[4 * x + 0] = source[x * 4 + 2];
+            dest[4 * x + 1] = source[x * 4 + 1];
+            dest[4 * x + 2] = source[x * 4 + 0];
+            dest[4 * x + 3] = source[x * 4 + 3];
+        }
+    }
+}
+
+void Texture::loadRGBA4444ImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                    size_t inputPitch, const void *input, size_t outputPitch, void *output) const
+{
+    const unsigned short *source = NULL;
+    unsigned char *dest = NULL;
 
-            dest[4 * x + 0] = b;
-            dest[4 * x + 1] = g;
-            dest[4 * x + 2] = r;
-            dest[4 * x + 3] = a;
+    for (int y = 0; y < height; y++)
+    {
+        source = reinterpret_cast<const unsigned short*>(static_cast<const unsigned char*>(input) + y * inputPitch);
+        dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
+        for (int x = 0; x < width; x++)
+        {
+            unsigned short rgba = source[x];
+            dest[4 * x + 0] = ((rgba & 0x00F0) << 0) | ((rgba & 0x00F0) >> 4);
+            dest[4 * x + 1] = ((rgba & 0x0F00) >> 4) | ((rgba & 0x0F00) >> 8);
+            dest[4 * x + 2] = ((rgba & 0xF000) >> 8) | ((rgba & 0xF000) >> 12);
+            dest[4 * x + 3] = ((rgba & 0x000F) << 4) | ((rgba & 0x000F) >> 0);
         }
     }
 }
 
-void Texture::setImage(GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels, Image *img)
+void Texture::loadRGBA5551ImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                    size_t inputPitch, const void *input, size_t outputPitch, void *output) const
+{
+    const unsigned short *source = NULL;
+    unsigned char *dest = NULL;
+
+    for (int y = 0; y < height; y++)
+    {
+        source = reinterpret_cast<const unsigned short*>(static_cast<const unsigned char*>(input) + y * inputPitch);
+        dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
+        for (int x = 0; x < width; x++)
+        {
+            unsigned short rgba = source[x];
+            dest[4 * x + 0] = ((rgba & 0x003E) << 2) | ((rgba & 0x003E) >> 3);
+            dest[4 * x + 1] = ((rgba & 0x07C0) >> 3) | ((rgba & 0x07C0) >> 8);
+            dest[4 * x + 2] = ((rgba & 0xF800) >> 8) | ((rgba & 0xF800) >> 13);
+            dest[4 * x + 3] = (rgba & 0x0001) ? 0xFF : 0;
+        }
+    }
+}
+
+void Texture::loadBGRAImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                size_t inputPitch, const void *input, size_t outputPitch, void *output) const
+{
+    const unsigned char *source = NULL;
+    unsigned char *dest = NULL;
+
+    for (int y = 0; y < height; y++)
+    {
+        source = static_cast<const unsigned char*>(input) + y * inputPitch;
+        dest = static_cast<unsigned char*>(output) + (y + yoffset) * outputPitch + xoffset * 4;
+        memcpy(dest, source, width*4);
+    }
+}
+
+void Texture::createSurface(GLsizei width, GLsizei height, GLenum format, Image *img)
 {
+    IDirect3DTexture9 *newTexture = NULL;
     IDirect3DSurface9 *newSurface = NULL;
 
     if (width != 0 && height != 0)
     {
-        HRESULT result = getDevice()->CreateOffscreenPlainSurface(width, height, selectFormat(format), D3DPOOL_SYSTEMMEM, &newSurface, NULL);
+        int levelToFetch = 0;
+        GLsizei requestWidth = width;
+        GLsizei requestHeight = height;
+        if (IsCompressed(format) && (width % 4 != 0 || height % 4 != 0))
+        {
+            bool isMult4 = false;
+            int upsampleCount = 0;
+            while (!isMult4)
+            {
+                requestWidth <<= 1;
+                requestHeight <<= 1;
+                upsampleCount++;
+                if (requestWidth % 4 == 0 && requestHeight % 4 == 0)
+                {
+                    isMult4 = true;
+                }
+            }
+            levelToFetch = upsampleCount;
+        }
+
+        HRESULT result = getDevice()->CreateTexture(requestWidth, requestHeight, levelToFetch + 1, NULL, selectFormat(format),
+                                                    D3DPOOL_SYSTEMMEM, &newTexture, NULL);
 
         if (FAILED(result))
         {
             ASSERT(result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY);
             return error(GL_OUT_OF_MEMORY);
         }
+
+        newTexture->GetSurfaceLevel(levelToFetch, &newSurface);
+        newTexture->Release();
     }
 
     if (img->surface) img->surface->Release();
@@ -316,18 +484,23 @@ void Texture::setImage(GLsizei width, GLsizei height, GLenum format, GLenum type
     img->width = width;
     img->height = height;
     img->format = format;
+}
 
-    if (pixels != NULL && newSurface != NULL)
+void Texture::setImage(GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels, Image *img)
+{
+    createSurface(width, height, format, img);
+
+    if (pixels != NULL && img->surface != NULL)
     {
         D3DLOCKED_RECT locked;
-        HRESULT result = newSurface->LockRect(&locked, NULL, 0);
+        HRESULT result = img->surface->LockRect(&locked, NULL, 0);
 
         ASSERT(SUCCEEDED(result));
 
         if (SUCCEEDED(result))
         {
             loadImageData(0, 0, width, height, format, type, unpackAlignment, pixels, locked.Pitch, locked.pBits);
-            newSurface->UnlockRect();
+            img->surface->UnlockRect();
         }
 
         img->dirty = true;
@@ -336,9 +509,36 @@ void Texture::setImage(GLsizei width, GLsizei height, GLenum format, GLenum type
     mDirtyMetaData = true;
 }
 
-void Texture::subImage(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels, Image *img)
+void Texture::setCompressedImage(GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const void *pixels, Image *img)
 {
-    if (width + xoffset > img->width || height + yoffset > img->height) return error(GL_INVALID_VALUE);
+    createSurface(width, height, format, img);
+
+    if (pixels != NULL && img->surface != NULL)
+    {
+        D3DLOCKED_RECT locked;
+        HRESULT result = img->surface->LockRect(&locked, NULL, 0);
+
+        ASSERT(SUCCEEDED(result));
+
+        if (SUCCEEDED(result))
+        {
+            memcpy(locked.pBits, pixels, imageSize);
+            img->surface->UnlockRect();
+        }
+
+        img->dirty = true;
+    }
+
+    mDirtyMetaData = true;
+}
+
+bool Texture::subImage(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels, Image *img)
+{
+    if (width + xoffset > img->width || height + yoffset > img->height)
+    {
+        error(GL_INVALID_VALUE);
+        return false;
+    }
 
     D3DLOCKED_RECT locked;
     HRESULT result = img->surface->LockRect(&locked, NULL, 0);
@@ -352,6 +552,47 @@ void Texture::subImage(GLint xoffset, GLint yoffset, GLsizei width, GLsizei heig
     }
 
     img->dirty = true;
+    return true;
+}
+
+bool Texture::subImageCompressed(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const void *pixels, Image *img)
+{
+    if (width + xoffset > img->width || height + yoffset > img->height)
+    {
+        error(GL_INVALID_VALUE);
+        return false;
+    }
+
+    if (format != getFormat())
+    {
+        error(GL_INVALID_OPERATION);
+        return false;
+    }
+
+    RECT updateRegion;
+    updateRegion.left = xoffset;
+    updateRegion.right = xoffset + width;
+    updateRegion.bottom = yoffset + height;
+    updateRegion.top = yoffset;
+
+    D3DLOCKED_RECT locked;
+    HRESULT result = img->surface->LockRect(&locked, &updateRegion, 0);
+
+    ASSERT(SUCCEEDED(result));
+
+    if (SUCCEEDED(result))
+    {
+        GLsizei inputPitch = ComputeCompressedPitch(width, format);
+        int rows = imageSize / inputPitch;
+        for (int i = 0; i < rows; ++i)
+        {
+            memcpy((void*)((BYTE*)locked.pBits + i * locked.Pitch), (void*)((BYTE*)pixels + i * inputPitch), inputPitch);
+        }
+        img->surface->UnlockRect();
+    }
+
+    img->dirty = true;
+    return true;
 }
 
 IDirect3DBaseTexture9 *Texture::getTexture()
@@ -442,7 +683,7 @@ int Texture::levelCount() const
     return mBaseTexture ? mBaseTexture->GetLevelCount() : 0;
 }
 
-Texture2D::Texture2D(Context *context) : Texture(context)
+Texture2D::Texture2D(GLuint id) : Texture(id)
 {
     mTexture = NULL;
     mColorbufferProxy = NULL;
@@ -464,6 +705,11 @@ GLenum Texture2D::getTarget() const
     return GL_TEXTURE_2D;
 }
 
+GLenum Texture2D::getFormat() const
+{
+    return mImageArray[0].format;
+}
+
 // While OpenGL doesn't check texture consistency until draw-time, D3D9 requires a complete texture
 // for render-to-texture (such as CopyTexImage). We have no way of keeping individual inconsistent levels.
 // Call this when a particular level of the texture must be defined with a specific format, width and height.
@@ -522,6 +768,13 @@ void Texture2D::setImage(GLint level, GLenum internalFormat, GLsizei width, GLsi
     Texture::setImage(width, height, format, type, unpackAlignment, pixels, &mImageArray[level]);
 }
 
+void Texture2D::setCompressedImage(GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLsizei imageSize, const void *pixels)
+{
+    redefineTexture(level, internalFormat, width, height);
+
+    Texture::setCompressedImage(width, height, internalFormat, imageSize, pixels, &mImageArray[level]);
+}
+
 void Texture2D::commitRect(GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height)
 {
     ASSERT(mImageArray[level].surface != NULL);
@@ -559,17 +812,31 @@ void Texture2D::commitRect(GLint level, GLint xoffset, GLint yoffset, GLsizei wi
 
 void Texture2D::subImage(GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels)
 {
-    Texture::subImage(xoffset, yoffset, width, height, format, type, unpackAlignment, pixels, &mImageArray[level]);
-    commitRect(level, xoffset, yoffset, width, height);
+    if (Texture::subImage(xoffset, yoffset, width, height, format, type, unpackAlignment, pixels, &mImageArray[level]))
+    {
+        commitRect(level, xoffset, yoffset, width, height);
+    }
+}
+
+void Texture2D::subImageCompressed(GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const void *pixels)
+{
+    if (Texture::subImageCompressed(xoffset, yoffset, width, height, format, imageSize, pixels, &mImageArray[level]))
+    {
+        commitRect(level, xoffset, yoffset, width, height);
+    }
 }
 
-void Texture2D::copyImage(GLint level, GLenum internalFormat, GLint x, GLint y, GLsizei width, GLsizei height, Renderbuffer *source)
+void Texture2D::copyImage(GLint level, GLenum internalFormat, GLint x, GLint y, GLsizei width, GLsizei height, RenderbufferStorage *source)
 {
     if (redefineTexture(level, internalFormat, width, height))
     {
         convertToRenderTarget();
         pushTexture(mTexture, true);
     }
+    else
+    {
+        needRenderTarget();
+    }
 
     if (width != 0 && height != 0 && level < levelCount())
     {
@@ -591,7 +858,7 @@ void Texture2D::copyImage(GLint level, GLenum internalFormat, GLint x, GLint y,
     mImageArray[level].format = internalFormat;
 }
 
-void Texture2D::copySubImage(GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, Renderbuffer *source)
+void Texture2D::copySubImage(GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, RenderbufferStorage *source)
 {
     if (xoffset + width > mImageArray[level].width || yoffset + height > mImageArray[level].height)
     {
@@ -689,6 +956,11 @@ bool Texture2D::isComplete() const
     return true;
 }
 
+bool Texture2D::isCompressed() const
+{
+    return IsCompressed(getFormat());
+}
+
 // Constructs a Direct3D 9 texture resource from the texture images, or returns an existing one
 IDirect3DBaseTexture9 *Texture2D::createTexture()
 {
@@ -871,16 +1143,17 @@ void Texture2D::generateMipmaps()
     }
 }
 
-Colorbuffer *Texture2D::getColorbuffer(GLenum target)
+Renderbuffer *Texture2D::getColorbuffer(GLenum target)
 {
     if (target != GL_TEXTURE_2D)
     {
-        return error(GL_INVALID_OPERATION, (Colorbuffer *)NULL);
+        return error(GL_INVALID_OPERATION, (Renderbuffer *)NULL);
     }
 
     if (mColorbufferProxy == NULL)
     {
-        mColorbufferProxy = new TextureColorbufferProxy(this, target);
+        mColorbufferProxy = new Renderbuffer(id(), new TextureColorbufferProxy(this, target));
+        mColorbufferProxy->addRef();
     }
 
     return mColorbufferProxy;
@@ -898,7 +1171,7 @@ IDirect3DSurface9 *Texture2D::getRenderTarget(GLenum target)
     return renderTarget;
 }
 
-TextureCubeMap::TextureCubeMap(Context *context) : Texture(context)
+TextureCubeMap::TextureCubeMap(GLuint id) : Texture(id)
 {
     mTexture = NULL;
 
@@ -927,6 +1200,11 @@ GLenum TextureCubeMap::getTarget() const
     return GL_TEXTURE_CUBE_MAP;
 }
 
+GLenum TextureCubeMap::getFormat() const
+{
+    return mImageArray[0][0].format;
+}
+
 void TextureCubeMap::setImagePosX(GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels)
 {
     setImage(0, level, internalFormat, width, height, format, type, unpackAlignment, pixels);
@@ -957,6 +1235,13 @@ void TextureCubeMap::setImageNegZ(GLint level, GLenum internalFormat, GLsizei wi
     setImage(5, level, internalFormat, width, height, format, type, unpackAlignment, pixels);
 }
 
+void TextureCubeMap::setCompressedImage(GLenum face, GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLsizei imageSize, const void *pixels)
+{
+    redefineTexture(level, internalFormat, width);
+
+    Texture::setCompressedImage(width, height, internalFormat, imageSize, pixels, &mImageArray[faceIndex(face)][level]);
+}
+
 void TextureCubeMap::commitRect(GLenum faceTarget, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height)
 {
     int face = faceIndex(faceTarget);
@@ -994,8 +1279,18 @@ void TextureCubeMap::commitRect(GLenum faceTarget, GLint level, GLint xoffset, G
 
 void TextureCubeMap::subImage(GLenum face, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels)
 {
-    Texture::subImage(xoffset, yoffset, width, height, format, type, unpackAlignment, pixels, &mImageArray[faceIndex(face)][level]);
-    commitRect(face, level, xoffset, yoffset, width, height);
+    if (Texture::subImage(xoffset, yoffset, width, height, format, type, unpackAlignment, pixels, &mImageArray[faceIndex(face)][level]))
+    {
+        commitRect(face, level, xoffset, yoffset, width, height);
+    }
+}
+
+void TextureCubeMap::subImageCompressed(GLenum face, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const void *pixels)
+{
+    if (Texture::subImageCompressed(xoffset, yoffset, width, height, format, imageSize, pixels, &mImageArray[faceIndex(face)][level]))
+    {
+        commitRect(face, level, xoffset, yoffset, width, height);
+    }
 }
 
 // Tests for GL texture object completeness. [OpenGL ES 2.0.24] section 3.7.10 page 81.
@@ -1064,6 +1359,11 @@ bool TextureCubeMap::isComplete() const
     return true;
 }
 
+bool TextureCubeMap::isCompressed() const
+{
+    return IsCompressed(getFormat());
+}
+
 // Constructs a Direct3D 9 texture resource from the texture images, or returns an existing one
 IDirect3DBaseTexture9 *TextureCubeMap::createTexture()
 {
@@ -1278,7 +1578,7 @@ bool TextureCubeMap::redefineTexture(GLint level, GLenum internalFormat, GLsizei
     return !textureOkay;
 }
 
-void TextureCubeMap::copyImage(GLenum face, GLint level, GLenum internalFormat, GLint x, GLint y, GLsizei width, GLsizei height, Renderbuffer *source)
+void TextureCubeMap::copyImage(GLenum face, GLint level, GLenum internalFormat, GLint x, GLint y, GLsizei width, GLsizei height, RenderbufferStorage *source)
 {
     unsigned int faceindex = faceIndex(face);
 
@@ -1287,6 +1587,10 @@ void TextureCubeMap::copyImage(GLenum face, GLint level, GLenum internalFormat,
         convertToRenderTarget();
         pushTexture(mTexture, true);
     }
+    else
+    {
+        needRenderTarget();
+    }
 
     ASSERT(width == height);
 
@@ -1340,7 +1644,7 @@ IDirect3DSurface9 *TextureCubeMap::getCubeMapSurface(unsigned int faceIdentifier
     return (SUCCEEDED(hr)) ? surface : NULL;
 }
 
-void TextureCubeMap::copySubImage(GLenum face, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, Renderbuffer *source)
+void TextureCubeMap::copySubImage(GLenum face, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, RenderbufferStorage *source)
 {
     GLsizei size = mImageArray[faceIndex(face)][level].width;
 
@@ -1356,7 +1660,7 @@ void TextureCubeMap::copySubImage(GLenum face, GLint level, GLint xoffset, GLint
     }
     else
     {
-        getRenderTarget(face);
+        needRenderTarget();
     }
 
     if (level < levelCount())
@@ -1440,18 +1744,19 @@ void TextureCubeMap::generateMipmaps()
     }
 }
 
-Colorbuffer *TextureCubeMap::getColorbuffer(GLenum target)
+Renderbuffer *TextureCubeMap::getColorbuffer(GLenum target)
 {
     if (!IsCubemapTextureTarget(target))
     {
-        return error(GL_INVALID_OPERATION, (Colorbuffer *)NULL);
+        return error(GL_INVALID_OPERATION, (Renderbuffer *)NULL);
     }
 
     unsigned int face = faceIndex(target);
 
     if (mFaceProxies[face] == NULL)
     {
-        mFaceProxies[face] = new TextureColorbufferProxy(this, target);
+        mFaceProxies[face] = new Renderbuffer(id(), new TextureColorbufferProxy(this, target));
+        mFaceProxies[face]->addRef();
     }
 
     return mFaceProxies[face];
@@ -1475,6 +1780,16 @@ Texture::TextureColorbufferProxy::TextureColorbufferProxy(Texture *texture, GLen
     ASSERT(target == GL_TEXTURE_2D || IsCubemapTextureTarget(target));
 }
 
+void Texture::TextureColorbufferProxy::addRef() const
+{
+    mTexture->addRef();
+}
+
+void Texture::TextureColorbufferProxy::release() const
+{
+    mTexture->release();
+}
+
 IDirect3DSurface9 *Texture::TextureColorbufferProxy::getRenderTarget()
 {
     if (mRenderTarget) mRenderTarget->Release();
@@ -1484,14 +1799,19 @@ IDirect3DSurface9 *Texture::TextureColorbufferProxy::getRenderTarget()
     return mRenderTarget;
 }
 
-int Texture::TextureColorbufferProxy::getWidth()
+int Texture::TextureColorbufferProxy::getWidth() const
 {
     return mTexture->getWidth();
 }
 
-int Texture::TextureColorbufferProxy::getHeight()
+int Texture::TextureColorbufferProxy::getHeight() const
 {
     return mTexture->getHeight();
 }
 
+GLenum Texture::TextureColorbufferProxy::getFormat() const
+{
+    return mTexture->getFormat();
+}
+
 }
diff --git a/ANGLE/src/libGLESv2/Texture.h b/ANGLE/src/libGLESv2/Texture.h
index 40fa11d..efa882c 100644
--- a/ANGLE/src/libGLESv2/Texture.h
+++ b/ANGLE/src/libGLESv2/Texture.h
@@ -23,7 +23,6 @@
 
 namespace gl
 {
-class Context;
 class Blit;
 
 enum
@@ -34,10 +33,10 @@ enum
     MAX_TEXTURE_LEVELS = 12   // 1+log2 of MAX_TEXTURE_SIZE
 };
 
-class Texture
+class Texture : public RefCountObject
 {
   public:
-    explicit Texture(Context *context);
+    explicit Texture(GLuint id);
 
     virtual ~Texture();
 
@@ -56,15 +55,19 @@ class Texture
     GLuint getWidth() const;
     GLuint getHeight() const;
 
+    virtual GLenum getFormat() const = 0;
     virtual bool isComplete() const = 0;
+    virtual bool isCompressed() const = 0;
 
     IDirect3DBaseTexture9 *getTexture();
-    virtual Colorbuffer *getColorbuffer(GLenum target) = 0;
+    virtual Renderbuffer *getColorbuffer(GLenum target) = 0;
 
     virtual void generateMipmaps() = 0;
 
     bool isDirty() const;
 
+    static const GLuint INCOMPLETE_TEXTURE_ID = static_cast<GLuint>(-1); // Every texture takes an id at creation time. The value is arbitrary because it is never registered with the resource manager.
+
   protected:
     class TextureColorbufferProxy;
     friend class TextureColorbufferProxy;
@@ -74,10 +77,14 @@ class Texture
         TextureColorbufferProxy(Texture *texture, GLenum target);
             // target is a 2D-like texture target (GL_TEXTURE_2D or one of the cube face targets)
 
+        virtual void addRef() const;
+        virtual void release() const;
+
         virtual IDirect3DSurface9 *getRenderTarget();
 
-        virtual int getWidth();
-        virtual int getHeight();
+        virtual int getWidth() const;
+        virtual int getHeight() const;
+        virtual GLenum getFormat() const;
 
       private:
         Texture *mTexture;
@@ -102,13 +109,10 @@ class Texture
     static D3DFORMAT selectFormat(GLenum format);
     int imagePitch(const Image& img) const;
 
-    GLenum mMinFilter;
-    GLenum mMagFilter;
-    GLenum mWrapS;
-    GLenum mWrapT;
-
     void setImage(GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels, Image *img);
-    void subImage(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels, Image *img);
+    bool subImage(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels, Image *img);
+    void setCompressedImage(GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const void *pixels, Image *img);
+    bool subImageCompressed(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const void *pixels, Image *img);
 
     void needRenderTarget();
 
@@ -128,45 +132,72 @@ class Texture
 
     Blit *getBlitter();
 
+    int levelCount() const;
+
     unsigned int mWidth;
     unsigned int mHeight;
-
-    int levelCount() const;
+    GLenum mMinFilter;
+    GLenum mMagFilter;
+    GLenum mWrapS;
+    GLenum mWrapT;
 
   private:
     DISALLOW_COPY_AND_ASSIGN(Texture);
 
-    Context *mContext;
+    void loadImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type,
+                       GLint unpackAlignment, const void *input, std::size_t outputPitch, void *output) const;
+
+    void loadAlphaImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                            size_t inputPitch, const void *input, size_t outputPitch, void *output) const;
+    void loadLuminanceImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                size_t inputPitch, const void *input, size_t outputPitch, void *output) const;
+    void loadLuminanceAlphaImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                     size_t inputPitch, const void *input, size_t outputPitch, void *output) const;
+    void loadRGBUByteImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                               size_t inputPitch, const void *input, size_t outputPitch, void *output) const;
+    void loadRGB565ImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                             size_t inputPitch, const void *input, size_t outputPitch, void *output) const;
+    void loadRGBAUByteImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                                size_t inputPitch, const void *input, size_t outputPitch, void *output) const;
+    void loadRGBA4444ImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                               size_t inputPitch, const void *input, size_t outputPitch, void *output) const;
+    void loadRGBA5551ImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                               size_t inputPitch, const void *input, size_t outputPitch, void *output) const;
+    void loadBGRAImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
+                           size_t inputPitch, const void *input, size_t outputPitch, void *output) const;
 
     IDirect3DBaseTexture9 *mBaseTexture; // This is a weak pointer. The derived class is assumed to own a strong pointer.
-    bool mDirtyMetaData;
-    bool mIsRenderable;
 
     bool mDirty;
+    bool mDirtyMetaData;
+    bool mIsRenderable;
 
-    void loadImageData(GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type,
-                       GLint unpackAlignment, const void *input, std::size_t outputPitch, void *output) const;
+    void createSurface(GLsizei width, GLsizei height, GLenum format, Image *img);
 };
 
 class Texture2D : public Texture
 {
   public:
-    explicit Texture2D(Context *context);
+    explicit Texture2D(GLuint id);
 
     ~Texture2D();
 
     GLenum getTarget() const;
+    GLenum getFormat() const;
 
     void setImage(GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels);
+    void setCompressedImage(GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLsizei imageSize, const void *pixels);
     void subImage(GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels);
-    void copyImage(GLint level, GLenum internalFormat, GLint x, GLint y, GLsizei width, GLsizei height, Renderbuffer *source);
-    void copySubImage(GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, Renderbuffer *source);
+    void subImageCompressed(GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const void *pixels);
+    void copyImage(GLint level, GLenum internalFormat, GLint x, GLint y, GLsizei width, GLsizei height, RenderbufferStorage *source);
+    void copySubImage(GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, RenderbufferStorage *source);
 
     bool isComplete() const;
+    bool isCompressed() const;
 
     virtual void generateMipmaps();
 
-    virtual Colorbuffer *getColorbuffer(GLenum target);
+    virtual Renderbuffer *getColorbuffer(GLenum target);
 
   private:
     DISALLOW_COPY_AND_ASSIGN(Texture2D);
@@ -174,30 +205,29 @@ class Texture2D : public Texture
     virtual IDirect3DBaseTexture9 *createTexture();
     virtual void updateTexture();
     virtual IDirect3DBaseTexture9 *convertToRenderTarget();
+    virtual IDirect3DSurface9 *getRenderTarget(GLenum target);
 
     virtual bool dirtyImageData() const;
 
+    bool redefineTexture(GLint level, GLenum internalFormat, GLsizei width, GLsizei height);
     void commitRect(GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height);
 
     Image mImageArray[MAX_TEXTURE_LEVELS];
 
     IDirect3DTexture9 *mTexture;
 
-    TextureColorbufferProxy *mColorbufferProxy;
-
-    bool redefineTexture(GLint level, GLenum internalFormat, GLsizei width, GLsizei height);
-
-    virtual IDirect3DSurface9 *getRenderTarget(GLenum target);
+    Renderbuffer *mColorbufferProxy;
 };
 
 class TextureCubeMap : public Texture
 {
   public:
-    explicit TextureCubeMap(Context *context);
+    explicit TextureCubeMap(GLuint id);
 
     ~TextureCubeMap();
 
     GLenum getTarget() const;
+    GLenum getFormat() const;
 
     void setImagePosX(GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels);
     void setImageNegX(GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels);
@@ -206,15 +236,19 @@ class TextureCubeMap : public Texture
     void setImagePosZ(GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels);
     void setImageNegZ(GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels);
 
+    void setCompressedImage(GLenum face, GLint level, GLenum internalFormat, GLsizei width, GLsizei height, GLsizei imageSize, const void *pixels);
+
     void subImage(GLenum face, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLenum type, GLint unpackAlignment, const void *pixels);
-    void copyImage(GLenum face, GLint level, GLenum internalFormat, GLint x, GLint y, GLsizei width, GLsizei height, Renderbuffer *source);
-    void copySubImage(GLenum face, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, Renderbuffer *source);
+    void subImageCompressed(GLenum face, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const void *pixels);
+    void copyImage(GLenum face, GLint level, GLenum internalFormat, GLint x, GLint y, GLsizei width, GLsizei height, RenderbufferStorage *source);
+    void copySubImage(GLenum face, GLint level, GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height, RenderbufferStorage *source);
 
     bool isComplete() const;
+    bool isCompressed() const;
 
     virtual void generateMipmaps();
 
-    virtual Colorbuffer *getColorbuffer(GLenum target);
+    virtual Renderbuffer *getColorbuffer(GLenum target);
 
   private:
     DISALLOW_COPY_AND_ASSIGN(TextureCubeMap);
@@ -222,6 +256,7 @@ class TextureCubeMap : public Texture
     virtual IDirect3DBaseTexture9 *createTexture();
     virtual void updateTexture();
     virtual IDirect3DBaseTexture9 *convertToRenderTarget();
+    virtual IDirect3DSurface9 *getRenderTarget(GLenum target);
 
     virtual bool dirtyImageData() const;
 
@@ -241,9 +276,7 @@ class TextureCubeMap : public Texture
 
     IDirect3DCubeTexture9 *mTexture;
 
-    TextureColorbufferProxy *mFaceProxies[6];
-
-    virtual IDirect3DSurface9 *getRenderTarget(GLenum target);
+    Renderbuffer *mFaceProxies[6];
 };
 }
 
diff --git a/ANGLE/src/libGLESv2/libGLESv2.cpp b/ANGLE/src/libGLESv2/libGLESv2.cpp
index a136bd3..25d083b 100644
--- a/ANGLE/src/libGLESv2/libGLESv2.cpp
+++ b/ANGLE/src/libGLESv2/libGLESv2.cpp
@@ -180,7 +180,7 @@ void __stdcall glBindFramebuffer(GLenum target, GLuint framebuffer)
 
     try
     {
-        if (target != GL_FRAMEBUFFER)
+        if (target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
         {
             return error(GL_INVALID_ENUM);
         }
@@ -189,7 +189,15 @@ void __stdcall glBindFramebuffer(GLenum target, GLuint framebuffer)
 
         if (context)
         {
-            context->bindFramebuffer(framebuffer);
+            if (target == GL_READ_FRAMEBUFFER_ANGLE || target == GL_FRAMEBUFFER)
+            {
+                context->bindReadFramebuffer(framebuffer);
+            }
+            
+            if (target == GL_DRAW_FRAMEBUFFER_ANGLE || target == GL_FRAMEBUFFER)
+            {
+                context->bindDrawFramebuffer(framebuffer);
+            }
         }
     }
     catch(std::bad_alloc&)
@@ -559,7 +567,7 @@ GLenum __stdcall glCheckFramebufferStatus(GLenum target)
 
     try
     {
-        if (target != GL_FRAMEBUFFER)
+        if (target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
         {
             return error(GL_INVALID_ENUM, 0);
         }
@@ -568,7 +576,15 @@ GLenum __stdcall glCheckFramebufferStatus(GLenum target)
 
         if (context)
         {
-            gl::Framebuffer *framebuffer = context->getFramebuffer();
+            gl::Framebuffer *framebuffer = NULL;
+            if (target == GL_READ_FRAMEBUFFER_ANGLE)
+            {
+                framebuffer = context->getReadFramebuffer();
+            }
+            else
+            {
+                framebuffer = context->getDrawFramebuffer();
+            }
 
             return framebuffer->completeness();
         }
@@ -720,22 +736,107 @@ void __stdcall glCompressedTexImage2D(GLenum target, GLint level, GLenum interna
 
     try
     {
-        if (!gl::IsTextureTarget(target))
+        if (level < 0 || level > gl::MAX_TEXTURE_LEVELS)
         {
-            return error(GL_INVALID_ENUM);
+            return error(GL_INVALID_VALUE);
         }
 
-        if (level < 0 || level > gl::MAX_TEXTURE_LEVELS)
+        if (width < 0 || height < 0 || (level > 0 && !gl::isPow2(width)) || (level > 0 && !gl::isPow2(height)) || border != 0 || imageSize < 0)
         {
             return error(GL_INVALID_VALUE);
         }
 
-        if (width < 0 || height < 0 || (level > 0 && !gl::isPow2(width)) || (level > 0 && !gl::isPow2(height)) || border != 0 || imageSize < 0)
+        switch (target)
+        {
+          case GL_TEXTURE_2D:
+            if (width > (gl::MAX_TEXTURE_SIZE >> level) || height > (gl::MAX_TEXTURE_SIZE >> level))
+            {
+                return error(GL_INVALID_VALUE);
+            }
+            break;
+          case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
+          case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
+          case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
+          case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
+          case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
+          case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
+            if (width != height)
+            {
+                return error(GL_INVALID_VALUE);
+            }
+
+            if (width > (gl::MAX_CUBE_MAP_TEXTURE_SIZE >> level) || height > (gl::MAX_CUBE_MAP_TEXTURE_SIZE >> level))
+            {
+                return error(GL_INVALID_VALUE);
+            }
+            break;
+          default:
+            return error(GL_INVALID_ENUM);
+        }
+
+        switch (internalformat)
+        {
+          case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
+          case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
+            break;
+          default:
+            return error(GL_INVALID_ENUM);
+        }
+
+        if (border != 0)
         {
             return error(GL_INVALID_VALUE);
         }
 
-        return error(GL_INVALID_ENUM); // ultimately we don't support compressed textures
+        gl::Context *context = gl::getContext();
+
+        if (context)
+        {
+            if (!context->supportsCompressedTextures())
+            {
+                return error(GL_INVALID_ENUM); // in this case, it's as though the internal format switch failed
+            }
+
+            if (imageSize != gl::ComputeCompressedSize(width, height, internalformat))
+            {
+                return error(GL_INVALID_VALUE);
+            }
+
+            if (target == GL_TEXTURE_2D)
+            {
+                gl::Texture2D *texture = context->getTexture2D();
+
+                if (!texture)
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                texture->setCompressedImage(level, internalformat, width, height, imageSize, data);
+            }
+            else
+            {
+                gl::TextureCubeMap *texture = context->getTextureCubeMap();
+
+                if (!texture)
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                switch (target)
+                {
+                  case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
+                  case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
+                  case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
+                  case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
+                  case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
+                  case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
+                    texture->setCompressedImage(target, level, internalformat, width, height, imageSize, data);
+                    break;
+                  default: UNREACHABLE();
+                }
+            }
+        }
+
     }
     catch(std::bad_alloc&)
     {
@@ -763,17 +864,95 @@ void __stdcall glCompressedTexSubImage2D(GLenum target, GLint level, GLint xoffs
             return error(GL_INVALID_VALUE);
         }
 
-        if (xoffset < 0 || yoffset < 0 || width < 0 || height < 0 || (level > 0 && !gl::isPow2(width)) || (level > 0 && !gl::isPow2(height)) || imageSize < 0)
+        if (xoffset < 0 || yoffset < 0 || width < 0 || height < 0 || 
+            (level > 0 && !gl::isPow2(width)) || (level > 0 && !gl::isPow2(height)) || imageSize < 0)
         {
             return error(GL_INVALID_VALUE);
         }
 
-        if (xoffset != 0 || yoffset != 0)
+        switch (format)
         {
-            return error(GL_INVALID_OPERATION);
+          case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
+          case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
+            break;
+          default:
+            return error(GL_INVALID_ENUM);
+        }
+
+        if (width == 0 || height == 0 || data == NULL)
+        {
+            return;
         }
 
-        return error(GL_INVALID_OPERATION); // The texture being operated on is not a compressed texture.
+        gl::Context *context = gl::getContext();
+
+        if (context)
+        {
+            if (!context->supportsCompressedTextures())
+            {
+                return error(GL_INVALID_ENUM); // in this case, it's as though the format switch has failed.
+            }
+
+            if (imageSize != gl::ComputeCompressedSize(width, height, format))
+            {
+                return error(GL_INVALID_VALUE);
+            }
+
+            if (xoffset % 4 != 0 || yoffset % 4 != 0)
+            {
+                return error(GL_INVALID_OPERATION); // we wait to check the offsets until this point, because the multiple-of-four restriction
+                                                    // does not exist unless DXT1 textures are supported.
+            }
+
+            if (target == GL_TEXTURE_2D)
+            {
+                gl::Texture2D *texture = context->getTexture2D();
+
+                if (!texture)
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                if (!texture->isCompressed())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                if ((width % 4 != 0 && width != texture->getWidth()) || 
+                    (height % 4 != 0 && height != texture->getHeight()))
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                texture->subImageCompressed(level, xoffset, yoffset, width, height, format, imageSize, data);
+            }
+            else if (gl::IsCubemapTextureTarget(target))
+            {
+                gl::TextureCubeMap *texture = context->getTextureCubeMap();
+
+                if (!texture)
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                if (!texture->isCompressed())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                if ((width % 4 != 0 && width != texture->getWidth()) || 
+                    (height % 4 != 0 && height != texture->getHeight()))
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                texture->subImageCompressed(target, level, xoffset, yoffset, width, height, format, imageSize, data);
+            }
+            else
+            {
+                UNREACHABLE();
+            }
+        }
     }
     catch(std::bad_alloc&)
     {
@@ -834,6 +1013,8 @@ void __stdcall glCopyTexImage2D(GLenum target, GLint level, GLenum internalforma
           case GL_LUMINANCE_ALPHA:
           case GL_RGB:
           case GL_RGBA:
+          case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:  // Compressed textures are not supported here, but if they are unsupported altogether,
+          case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT: // a different error is generated than otherwise. That is handled below.
             break;
           default:
             return error(GL_INVALID_VALUE);
@@ -848,8 +1029,31 @@ void __stdcall glCopyTexImage2D(GLenum target, GLint level, GLenum internalforma
 
         if (context)
         {
-            gl::Renderbuffer *source = context->getFramebuffer()->getColorbuffer();
+            if (internalformat == GL_COMPRESSED_RGB_S3TC_DXT1_EXT || 
+                internalformat == GL_COMPRESSED_RGBA_S3TC_DXT1_EXT)
+            {
+                if (context->supportsCompressedTextures())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+                else
+                {
+                    return error(GL_INVALID_ENUM);
+                }
+            }
+
+            gl::Framebuffer *framebuffer = context->getReadFramebuffer();
+            if (framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
+            {
+                return error(GL_INVALID_FRAMEBUFFER_OPERATION);
+            }
 
+            if (context->getReadFramebufferHandle() != 0 && framebuffer->getColorbuffer()->getSamples() != 0)
+            {
+                return error(GL_INVALID_OPERATION);
+            }
+
+            gl::Colorbuffer *source = framebuffer->getColorbuffer();
             if (target == GL_TEXTURE_2D)
             {
                 gl::Texture2D *texture = context->getTexture2D();
@@ -858,6 +1062,11 @@ void __stdcall glCopyTexImage2D(GLenum target, GLint level, GLenum internalforma
                 {
                     return error(GL_INVALID_OPERATION);
                 }
+                
+                if (texture->isCompressed())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
 
                 texture->copyImage(level, internalformat, x, y, width, height, source);
             }
@@ -870,6 +1079,11 @@ void __stdcall glCopyTexImage2D(GLenum target, GLint level, GLenum internalforma
                     return error(GL_INVALID_OPERATION);
                 }
 
+                if (texture->isCompressed())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
                 texture->copyImage(target, level, internalformat, x, y, width, height, source);
             }
             else
@@ -916,8 +1130,18 @@ void __stdcall glCopyTexSubImage2D(GLenum target, GLint level, GLint xoffset, GL
 
         if (context)
         {
-            gl::Renderbuffer *source = context->getFramebuffer()->getColorbuffer();
+            gl::Framebuffer *framebuffer = context->getReadFramebuffer();
+            if (framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
+            {
+                return error(GL_INVALID_FRAMEBUFFER_OPERATION);
+            }
+
+            if (context->getReadFramebufferHandle() != 0 && framebuffer->getColorbuffer()->getSamples() != 0)
+            {
+                return error(GL_INVALID_OPERATION);
+            }
 
+            gl::Colorbuffer *source = framebuffer->getColorbuffer();
             if (target == GL_TEXTURE_2D)
             {
                 gl::Texture2D *texture = context->getTexture2D();
@@ -927,6 +1151,11 @@ void __stdcall glCopyTexSubImage2D(GLenum target, GLint level, GLint xoffset, GL
                     return error(GL_INVALID_OPERATION);
                 }
 
+                if (texture->isCompressed())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
                 texture->copySubImage(level, xoffset, yoffset, x, y, width, height, source);
             }
             else if (gl::IsCubemapTextureTarget(target))
@@ -938,6 +1167,11 @@ void __stdcall glCopyTexSubImage2D(GLenum target, GLint level, GLint xoffset, GL
                     return error(GL_INVALID_OPERATION);
                 }
 
+                if (texture->isCompressed())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
                 texture->copySubImage(target, level, xoffset, yoffset, x, y, width, height, source);
             }
             else
@@ -1559,7 +1793,8 @@ void __stdcall glFramebufferRenderbuffer(GLenum target, GLenum attachment, GLenu
 
     try
     {
-        if (target != GL_FRAMEBUFFER || renderbuffertarget != GL_RENDERBUFFER)
+        if ((target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
+            || renderbuffertarget != GL_RENDERBUFFER)
         {
             return error(GL_INVALID_ENUM);
         }
@@ -1568,9 +1803,20 @@ void __stdcall glFramebufferRenderbuffer(GLenum target, GLenum attachment, GLenu
 
         if (context)
         {
-            gl::Framebuffer *framebuffer = context->getFramebuffer();
+            gl::Framebuffer *framebuffer = NULL;
+            GLuint framebufferHandle = 0;
+            if (target == GL_READ_FRAMEBUFFER_ANGLE)
+            {
+                framebuffer = context->getReadFramebuffer();
+                framebufferHandle = context->getReadFramebufferHandle();
+            }
+            else 
+            {
+                framebuffer = context->getDrawFramebuffer();
+                framebufferHandle = context->getDrawFramebufferHandle();
+            }
 
-            if (context->getFramebufferHandle() == 0 || !framebuffer)
+            if (framebufferHandle == 0 || !framebuffer)
             {
                 return error(GL_INVALID_OPERATION);
             }
@@ -1604,7 +1850,7 @@ void __stdcall glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum t
 
     try
     {
-        if (target != GL_FRAMEBUFFER)
+        if (target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
         {
             return error(GL_INVALID_ENUM);
         }
@@ -1636,6 +1882,11 @@ void __stdcall glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum t
                     return error(GL_INVALID_OPERATION);
                 }
 
+                if (tex->isCompressed())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
                 switch (textarget)
                 {
                   case GL_TEXTURE_2D:
@@ -1667,9 +1918,20 @@ void __stdcall glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum t
                 }
             }
 
-            gl::Framebuffer *framebuffer = context->getFramebuffer();
+            gl::Framebuffer *framebuffer = NULL;
+            GLuint framebufferHandle = 0;
+            if (target == GL_READ_FRAMEBUFFER_ANGLE)
+            {
+                framebuffer = context->getReadFramebuffer();
+                framebufferHandle = context->getReadFramebufferHandle();
+            }
+            else
+            {
+                framebuffer = context->getDrawFramebuffer();
+                framebufferHandle = context->getDrawFramebufferHandle();
+            }
 
-            if (context->getFramebufferHandle() == 0 || !framebuffer)
+            if (framebufferHandle == 0 || !framebuffer)
             {
                 return error(GL_INVALID_OPERATION);
             }
@@ -1770,6 +2032,11 @@ void __stdcall glGenerateMipmap(GLenum target)
                 return error(GL_INVALID_ENUM);
             }
 
+            if (texture->isCompressed())
+            {
+                return error(GL_INVALID_OPERATION);
+            }
+
             texture->generateMipmaps();
         }
     }
@@ -2225,14 +2492,29 @@ void __stdcall glGetFramebufferAttachmentParameteriv(GLenum target, GLenum attac
 
         if (context)
         {
-            if (context->getFramebufferHandle() == 0)
+            if (target != GL_FRAMEBUFFER && target != GL_DRAW_FRAMEBUFFER_ANGLE && target != GL_READ_FRAMEBUFFER_ANGLE)
             {
-                return error(GL_INVALID_OPERATION);
+                return error(GL_INVALID_ENUM);
             }
 
-            if (target != GL_FRAMEBUFFER)
+            gl::Framebuffer *framebuffer = NULL;
+            if (target == GL_READ_FRAMEBUFFER_ANGLE)
             {
-                return error(GL_INVALID_ENUM);
+                if(context->getReadFramebufferHandle() == 0)
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                framebuffer = context->getReadFramebuffer();
+            }
+            else 
+            {
+                if (context->getDrawFramebufferHandle() == 0)
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
+                framebuffer = context->getDrawFramebuffer();
             }
 
             GLenum attachmentType;
@@ -2240,16 +2522,16 @@ void __stdcall glGetFramebufferAttachmentParameteriv(GLenum target, GLenum attac
             switch (attachment)
             {
               case GL_COLOR_ATTACHMENT0:    
-                attachmentType = context->getFramebuffer()->getColorbufferType();
-                attachmentHandle = context->getFramebuffer()->getColorbufferHandle(); 
+                attachmentType = framebuffer->getColorbufferType();
+                attachmentHandle = framebuffer->getColorbufferHandle(); 
                 break;
               case GL_DEPTH_ATTACHMENT:     
-                attachmentType = context->getFramebuffer()->getDepthbufferType();
-                attachmentHandle = context->getFramebuffer()->getDepthbufferHandle();
+                attachmentType = framebuffer->getDepthbufferType();
+                attachmentHandle = framebuffer->getDepthbufferHandle();
                 break;
               case GL_STENCIL_ATTACHMENT:   
-                attachmentType = context->getFramebuffer()->getStencilbufferType();
-                attachmentHandle = context->getFramebuffer()->getStencilbufferHandle();
+                attachmentType = framebuffer->getStencilbufferType();
+                attachmentHandle = framebuffer->getStencilbufferHandle();
                 break;
               default: return error(GL_INVALID_ENUM);
             }
@@ -2508,7 +2790,7 @@ void __stdcall glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint*
               case GL_RENDERBUFFER_RED_SIZE:
                 if (renderbuffer->isColorbuffer())
                 {
-                    *params = static_cast<gl::Colorbuffer*>(renderbuffer)->getRedSize();
+                    *params = static_cast<gl::Colorbuffer*>(renderbuffer->getStorage())->getRedSize();
                 }
                 else
                 {
@@ -2518,7 +2800,7 @@ void __stdcall glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint*
               case GL_RENDERBUFFER_GREEN_SIZE:
                 if (renderbuffer->isColorbuffer())
                 {
-                    *params = static_cast<gl::Colorbuffer*>(renderbuffer)->getGreenSize();
+                    *params = static_cast<gl::Colorbuffer*>(renderbuffer->getStorage())->getGreenSize();
                 }
                 else
                 {
@@ -2528,7 +2810,7 @@ void __stdcall glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint*
               case GL_RENDERBUFFER_BLUE_SIZE:
                 if (renderbuffer->isColorbuffer())
                 {
-                    *params = static_cast<gl::Colorbuffer*>(renderbuffer)->getBlueSize();
+                    *params = static_cast<gl::Colorbuffer*>(renderbuffer->getStorage())->getBlueSize();
                 }
                 else
                 {
@@ -2538,7 +2820,7 @@ void __stdcall glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint*
               case GL_RENDERBUFFER_ALPHA_SIZE:
                 if (renderbuffer->isColorbuffer())
                 {
-                    *params = static_cast<gl::Colorbuffer*>(renderbuffer)->getAlphaSize();
+                    *params = static_cast<gl::Colorbuffer*>(renderbuffer->getStorage())->getAlphaSize();
                 }
                 else
                 {
@@ -2548,7 +2830,7 @@ void __stdcall glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint*
               case GL_RENDERBUFFER_DEPTH_SIZE:
                 if (renderbuffer->isDepthbuffer())
                 {
-                    *params = static_cast<gl::Depthbuffer*>(renderbuffer)->getDepthSize();
+                    *params = static_cast<gl::Depthbuffer*>(renderbuffer->getStorage())->getDepthSize();
                 }
                 else
                 {
@@ -2558,13 +2840,25 @@ void __stdcall glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint*
               case GL_RENDERBUFFER_STENCIL_SIZE:
                 if (renderbuffer->isStencilbuffer())
                 {
-                    *params = static_cast<gl::Stencilbuffer*>(renderbuffer)->getStencilSize();
+                    *params = static_cast<gl::Stencilbuffer*>(renderbuffer->getStorage())->getStencilSize();
                 }
                 else
                 {
                     *params = 0;
                 }
                 break;
+              case GL_RENDERBUFFER_SAMPLES_ANGLE:
+                {
+                    if (context->getMaxSupportedSamples() != 0)
+                    {
+                        *params = renderbuffer->getStorage()->getSamples();
+                    }
+                    else
+                    {
+                        return error(GL_INVALID_ENUM);
+                    }
+                }
+                break;
               default:
                 return error(GL_INVALID_ENUM);
             }
@@ -2993,7 +3287,7 @@ void __stdcall glGetVertexAttribfv(GLuint index, GLenum pname, GLfloat* params)
                 return error(GL_INVALID_VALUE);
             }
 
-            gl::AttributeState attribState = context->getVertexAttribState(index);
+            const gl::AttributeState &attribState = context->getVertexAttribState(index);
 
             switch (pname)
             {
@@ -3013,7 +3307,7 @@ void __stdcall glGetVertexAttribfv(GLuint index, GLenum pname, GLfloat* params)
                 *params = (GLfloat)(attribState.mNormalized ? GL_TRUE : GL_FALSE);
                 break;
               case GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING:
-                *params = (GLfloat)attribState.mBoundBuffer;
+                *params = (GLfloat)attribState.mBoundBuffer.id();
                 break;
               case GL_CURRENT_VERTEX_ATTRIB:
                 for (int i = 0; i < 4; ++i)
@@ -3046,7 +3340,7 @@ void __stdcall glGetVertexAttribiv(GLuint index, GLenum pname, GLint* params)
                 return error(GL_INVALID_VALUE);
             }
 
-            gl::AttributeState attribState = context->getVertexAttribState(index);
+            const gl::AttributeState &attribState = context->getVertexAttribState(index);
 
             switch (pname)
             {
@@ -3066,7 +3360,7 @@ void __stdcall glGetVertexAttribiv(GLuint index, GLenum pname, GLint* params)
                 *params = (attribState.mNormalized ? GL_TRUE : GL_FALSE);
                 break;
               case GL_VERTEX_ATTRIB_ARRAY_BUFFER_BINDING:
-                *params = attribState.mBoundBuffer;
+                *params = attribState.mBoundBuffer.id();
                 break;
               case GL_CURRENT_VERTEX_ATTRIB:
                 for (int i = 0; i < 4; ++i)
@@ -3481,6 +3775,17 @@ void __stdcall glReadPixels(GLint x, GLint y, GLsizei width, GLsizei height, GLe
                 return error(GL_INVALID_OPERATION);
             }
             break;
+          case GL_BGRA_EXT:
+            switch (type)
+            {
+              case GL_UNSIGNED_BYTE:
+              case GL_UNSIGNED_SHORT_4_4_4_4_REV_EXT:
+              case GL_UNSIGNED_SHORT_1_5_5_5_REV_EXT:
+                break;
+              default:
+                return error(GL_INVALID_OPERATION);
+            }
+            break;
           case gl::IMPLEMENTATION_COLOR_READ_FORMAT:
             switch (type)
             {
@@ -3521,10 +3826,10 @@ void __stdcall glReleaseShaderCompiler(void)
     }
 }
 
-void __stdcall glRenderbufferStorage(GLenum target, GLenum internalformat, GLsizei width, GLsizei height)
+void __stdcall glRenderbufferStorageMultisampleANGLE(GLenum target, GLsizei samples, GLenum internalformat, GLsizei width, GLsizei height)
 {
-    TRACE("(GLenum target = 0x%X, GLenum internalformat = 0x%X, GLsizei width = %d, GLsizei height = %d)",
-          target, internalformat, width, height);
+    TRACE("(GLenum target = 0x%X, GLsizei samples = %d, GLenum internalformat = 0x%X, GLsizei width = %d, GLsizei height = %d)",
+          target, samples, internalformat, width, height);
 
     try
     {
@@ -3543,12 +3848,15 @@ void __stdcall glRenderbufferStorage(GLenum target, GLenum internalformat, GLsiz
           case GL_RGB5_A1:
           case GL_RGB565:
           case GL_STENCIL_INDEX8:
+          case GL_DEPTH24_STENCIL8_OES:
+          case GL_RGB8_OES:
+          case GL_RGBA8_OES:
             break;
           default:
             return error(GL_INVALID_ENUM);
         }
 
-        if (width < 0 || height < 0 || width > gl::MAX_RENDERBUFFER_SIZE || height > gl::MAX_RENDERBUFFER_SIZE)
+        if (width < 0 || height < 0 || width > gl::MAX_RENDERBUFFER_SIZE || height > gl::MAX_RENDERBUFFER_SIZE || samples < 0)
         {
             return error(GL_INVALID_VALUE);
         }
@@ -3557,7 +3865,13 @@ void __stdcall glRenderbufferStorage(GLenum target, GLenum internalformat, GLsiz
 
         if (context)
         {
-            if (context->getRenderbufferHandle() == 0)
+            if (samples > context->getMaxSupportedSamples())
+            {
+                return error(GL_INVALID_VALUE);
+            }
+
+            GLuint handle = context->getRenderbufferHandle();
+            if (handle == 0)
             {
                 return error(GL_INVALID_OPERATION);
             }
@@ -3565,15 +3879,20 @@ void __stdcall glRenderbufferStorage(GLenum target, GLenum internalformat, GLsiz
             switch (internalformat)
             {
               case GL_DEPTH_COMPONENT16:
-                context->setRenderbuffer(new gl::Depthbuffer(width, height));
+                context->setRenderbufferStorage(new gl::Depthbuffer(width, height, samples));
                 break;
               case GL_RGBA4:
               case GL_RGB5_A1:
               case GL_RGB565:
-                context->setRenderbuffer(new gl::Colorbuffer(width, height, internalformat));
+              case GL_RGB8_OES:
+              case GL_RGBA8_OES:
+                context->setRenderbufferStorage(new gl::Colorbuffer(width, height, internalformat, samples));
                 break;
               case GL_STENCIL_INDEX8:
-                context->setRenderbuffer(new gl::Stencilbuffer(width, height));
+                context->setRenderbufferStorage(new gl::Stencilbuffer(width, height, samples));
+                break;
+              case GL_DEPTH24_STENCIL8_OES:
+                context->setRenderbufferStorage(new gl::DepthStencilbuffer(width, height, samples));
                 break;
               default:
                 return error(GL_INVALID_ENUM);
@@ -3586,6 +3905,11 @@ void __stdcall glRenderbufferStorage(GLenum target, GLenum internalformat, GLsiz
     }
 }
 
+void __stdcall glRenderbufferStorage(GLenum target, GLenum internalformat, GLsizei width, GLsizei height)
+{
+    glRenderbufferStorageMultisampleANGLE(target, 0, internalformat, width, height);
+}
+
 void __stdcall glSampleCoverage(GLclampf value, GLboolean invert)
 {
     TRACE("(GLclampf value = %f, GLboolean invert = %d)", value, invert);
@@ -3958,6 +4282,18 @@ void __stdcall glTexImage2D(GLenum target, GLint level, GLint internalformat, GL
                 return error(GL_INVALID_ENUM);
             }
             break;
+          case GL_BGRA_EXT:
+            switch (type)
+            {
+              case GL_UNSIGNED_BYTE:
+                break;
+              default:
+                return error(GL_INVALID_ENUM);
+            }
+            break;
+          case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:  // error cases for compressed textures are handled below
+          case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
+            break; 
           default:
             return error(GL_INVALID_VALUE);
         }
@@ -3971,6 +4307,19 @@ void __stdcall glTexImage2D(GLenum target, GLint level, GLint internalformat, GL
 
         if (context)
         {
+            if (internalformat == GL_COMPRESSED_RGB_S3TC_DXT1_EXT ||
+                internalformat == GL_COMPRESSED_RGBA_S3TC_DXT1_EXT)
+            {
+                if (context->supportsCompressedTextures())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+                else
+                {
+                    return error(GL_INVALID_ENUM);
+                }
+            }
+
             if (target == GL_TEXTURE_2D)
             {
                 gl::Texture2D *texture = context->getTexture2D();
@@ -4146,6 +4495,11 @@ void __stdcall glTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint
                     return error(GL_INVALID_OPERATION);
                 }
 
+                if (texture->isCompressed())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
                 texture->subImage(level, xoffset, yoffset, width, height, format, type, context->getUnpackAlignment(), pixels);
             }
             else if (gl::IsCubemapTextureTarget(target))
@@ -4157,6 +4511,11 @@ void __stdcall glTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint
                     return error(GL_INVALID_OPERATION);
                 }
 
+                if (texture->isCompressed())
+                {
+                    return error(GL_INVALID_OPERATION);
+                }
+
                 texture->subImage(target, level, xoffset, yoffset, width, height, format, type, context->getUnpackAlignment(), pixels);
             }
             else
@@ -4965,7 +5324,7 @@ void __stdcall glVertexAttribPointer(GLuint index, GLint size, GLenum type, GLbo
 
         if (context)
         {
-            context->setVertexAttribState(index, context->getArrayBufferHandle(), size, type, (normalized == GL_TRUE), stride, ptr);
+            context->setVertexAttribState(index, context->getArrayBuffer(), size, type, (normalized == GL_TRUE), stride, ptr);
         }
     }
     catch(std::bad_alloc&)
@@ -4998,6 +5357,54 @@ void __stdcall glViewport(GLint x, GLint y, GLsizei width, GLsizei height)
     }
 }
 
+void __stdcall glBlitFramebufferANGLE(GLint srcX0, GLint srcY0, GLint srcX1, GLint srcY1, GLint dstX0, GLint dstY0, GLint dstX1, GLint dstY1,
+                                      GLbitfield mask, GLenum filter)
+{
+    TRACE("(GLint srcX0 = %d, GLint srcY0 = %d, GLint srcX1 = %d, GLint srcY1 = %d, "
+          "GLint dstX0 = %d, GLint dstY0 = %d, GLint dstX1 = %d, GLint dstY1 = %d, "
+          "GLbitfield mask = 0x%X, GLenum filter = 0x%X)",
+          srcX0, srcY0, srcX1, srcX1, dstX0, dstY0, dstX1, dstY1, mask, filter);
+
+    try
+    {
+        switch (filter)
+        {
+          case GL_NEAREST:
+            break;
+          default:
+            return error(GL_INVALID_ENUM);
+        }
+
+        if ((mask & ~(GL_COLOR_BUFFER_BIT | GL_STENCIL_BUFFER_BIT | GL_DEPTH_BUFFER_BIT)) != 0)
+        {
+            return error(GL_INVALID_VALUE);
+        }
+
+        if (srcX1 - srcX0 != dstX1 - dstX0 || srcY1 - srcY0 != dstY1 - dstY0)
+        {
+            ERR("Scaling and flipping in BlitFramebufferANGLE not supported by this implementation");
+            return error(GL_INVALID_OPERATION);
+        }
+
+        gl::Context *context = gl::getContext();
+
+        if (context)
+        {
+            if (context->getReadFramebufferHandle() == context->getDrawFramebufferHandle())
+            {
+                ERR("Blits with the same source and destination framebuffer are not supported by this implementation.");
+                return error(GL_INVALID_OPERATION);
+            }
+
+            context->blitFramebuffer(srcX0, srcY0, srcX1, srcY1, dstX0, dstY0, dstX1, dstY1, mask);
+        }
+    }
+    catch(std::bad_alloc&)
+    {
+        return error(GL_OUT_OF_MEMORY);
+    }
+}
+
 void __stdcall glTexImage3DOES(GLenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLsizei depth,
                                GLint border, GLenum format, GLenum type, const GLvoid* pixels)
 {
@@ -5027,6 +5434,7 @@ __eglMustCastToProperFunctionPointerType __stdcall glGetProcAddress(const char *
     static const Extension glExtensions[] =
     {
         {"glTexImage3DOES", (__eglMustCastToProperFunctionPointerType)glTexImage3DOES},
+        {"glBlitFramebufferANGLE", (__eglMustCastToProperFunctionPointerType)glBlitFramebufferANGLE},
     };
 
     for (int ext = 0; ext < sizeof(glExtensions) / sizeof(Extension); ext++)
diff --git a/ANGLE/src/libGLESv2/libGLESv2.def b/ANGLE/src/libGLESv2/libGLESv2.def
index 0aaaa67..a043ed8 100644
--- a/ANGLE/src/libGLESv2/libGLESv2.def
+++ b/ANGLE/src/libGLESv2/libGLESv2.def
@@ -144,11 +144,13 @@ EXPORTS
     glViewport                      @142
 
     ; Extensions
-    glTexImage3DOES					@143
+    glTexImage3DOES                 @143
+    glBlitFramebufferANGLE          @149
+    glRenderbufferStorageMultisampleANGLE @150
     
     ; EGL dependencies
-    glCreateContext					@144 NONAME
-    glDestroyContext				@145 NONAME
-    glMakeCurrent					@146 NONAME
-    glGetCurrentContext				@147 NONAME
+    glCreateContext                 @144 NONAME
+    glDestroyContext                @145 NONAME
+    glMakeCurrent                   @146 NONAME
+    glGetCurrentContext             @147 NONAME
     glGetProcAddress                @148 NONAME
\ No newline at end of file
diff --git a/ANGLE/src/libGLESv2/libGLESv2.vcproj b/ANGLE/src/libGLESv2/libGLESv2.vcproj
index e994e05..f9e34d0 100644
--- a/ANGLE/src/libGLESv2/libGLESv2.vcproj
+++ b/ANGLE/src/libGLESv2/libGLESv2.vcproj
@@ -217,10 +217,18 @@
 				>
 			</File>
 			<File
+				RelativePath=".\RefCountObject.cpp"
+				>
+			</File>
+			<File
 				RelativePath=".\Renderbuffer.cpp"
 				>
 			</File>
 			<File
+				RelativePath=".\ResourceManager.cpp"
+				>
+			</File>
+			<File
 				RelativePath=".\Shader.cpp"
 				>
 			</File>
@@ -299,10 +307,18 @@
 				>
 			</File>
 			<File
+				RelativePath=".\RefCountObject.h"
+				>
+			</File>
+			<File
 				RelativePath=".\Renderbuffer.h"
 				>
 			</File>
 			<File
+				RelativePath=".\ResourceManager.h"
+				>
+			</File>
+			<File
 				RelativePath=".\Shader.h"
 				>
 			</File>
diff --git a/ANGLE/src/libGLESv2/main.h b/ANGLE/src/libGLESv2/main.h
index dec112a..7f9c880 100644
--- a/ANGLE/src/libGLESv2/main.h
+++ b/ANGLE/src/libGLESv2/main.h
@@ -11,6 +11,7 @@
 
 #define GL_APICALL
 #include <GLES2/gl2.h>
+#include <GLES2/gl2ext.h>
 
 #include "common/debug.h"
 #include "libEGL/Display.h"
diff --git a/ANGLE/src/libGLESv2/utilities.cpp b/ANGLE/src/libGLESv2/utilities.cpp
index f584588..7fc2bc4 100644
--- a/ANGLE/src/libGLESv2/utilities.cpp
+++ b/ANGLE/src/libGLESv2/utilities.cpp
@@ -183,6 +183,49 @@ GLsizei ComputePitch(GLsizei width, GLenum format, GLenum type, GLint alignment)
     return (rawPitch + alignment - 1) & ~(alignment - 1);
 }
 
+GLsizei ComputeCompressedPitch(GLsizei width, GLenum format)
+{
+    switch (format)
+    {
+      case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
+      case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
+        break;
+      default:
+        return 0;
+    }
+
+    ASSERT(width % 4 == 0);
+
+    return 8 * width / 4;
+}
+
+GLsizei ComputeCompressedSize(GLsizei width, GLsizei height, GLenum format)
+{
+    switch (format)
+    {
+      case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
+      case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
+        break;
+      default:
+        return 0;
+    }
+
+    return 8 * (GLsizei)ceil((float)width / 4.0f) * (GLsizei)ceil((float)height / 4.0f);
+}
+
+bool IsCompressed(GLenum format)
+{
+    if(format == GL_COMPRESSED_RGB_S3TC_DXT1_EXT ||
+       format == GL_COMPRESSED_RGBA_S3TC_DXT1_EXT)
+    {
+        return true;
+    }
+    else
+    {
+        return false;
+    }
+}
+
 // Returns the size, in bytes, of a single texel in an Image
 int ComputePixelSize(GLenum format, GLenum type)
 {
@@ -196,6 +239,7 @@ int ComputePixelSize(GLenum format, GLenum type)
           case GL_LUMINANCE_ALPHA: return sizeof(unsigned char) * 2;
           case GL_RGB:             return sizeof(unsigned char) * 3;
           case GL_RGBA:            return sizeof(unsigned char) * 4;
+          case GL_BGRA_EXT:        return sizeof(unsigned char) * 4;
           default: UNREACHABLE();
         }
         break;
@@ -228,6 +272,7 @@ bool CheckTextureFormatType(GLenum format, GLenum type)
         switch (format)
         {
           case GL_RGBA:
+          case GL_BGRA_EXT:
           case GL_RGB:
           case GL_ALPHA:
           case GL_LUMINANCE:
@@ -599,12 +644,31 @@ D3DFORMAT ConvertRenderbufferFormat(GLenum format)
     switch (format)
     {
       case GL_RGBA4:
-      case GL_RGB5_A1:              return D3DFMT_A8R8G8B8;
+      case GL_RGB5_A1:
+      case GL_RGBA8_OES:            return D3DFMT_A8R8G8B8;
       case GL_RGB565:               return D3DFMT_R5G6B5;
+      case GL_RGB8_OES:             return D3DFMT_X8R8G8B8;
       case GL_DEPTH_COMPONENT16:
-      case GL_STENCIL_INDEX8:       return D3DFMT_D24S8;
+      case GL_STENCIL_INDEX8:       
+      case GL_DEPTH24_STENCIL8_OES: return D3DFMT_D24S8;
       default: UNREACHABLE();       return D3DFMT_A8R8G8B8;
     }
 }
 
+GLsizei GetSamplesFromMultisampleType(D3DMULTISAMPLE_TYPE type)
+{
+    if (type == D3DMULTISAMPLE_NONMASKABLE)
+        return 0;
+    else
+        return type;
+}
+
+D3DMULTISAMPLE_TYPE GetMultisampleTypeFromSamples(GLsizei samples)
+{
+    if (samples <= 1)
+        return D3DMULTISAMPLE_NONE;
+    else
+        return (D3DMULTISAMPLE_TYPE)samples;
+}
+
 }
diff --git a/ANGLE/src/libGLESv2/utilities.h b/ANGLE/src/libGLESv2/utilities.h
index 6e6c140..b6c8ce5 100644
--- a/ANGLE/src/libGLESv2/utilities.h
+++ b/ANGLE/src/libGLESv2/utilities.h
@@ -11,6 +11,7 @@
 
 #define GL_APICALL
 #include <GLES2/gl2.h>
+#include <GLES2/gl2ext.h>
 #include <d3d9.h>
 
 namespace gl
@@ -28,6 +29,9 @@ int AllocateFirstFreeBits(unsigned int *bits, unsigned int allocationSize, unsig
 
 int ComputePixelSize(GLenum format, GLenum type);
 GLsizei ComputePitch(GLsizei width, GLenum format, GLenum type, GLint alignment);
+GLsizei ComputeCompressedPitch(GLsizei width, GLenum format);
+GLsizei ComputeCompressedSize(GLsizei width, GLsizei height, GLenum format);
+bool IsCompressed(GLenum format);
 bool IsCubemapTextureTarget(GLenum target);
 bool IsTextureTarget(GLenum target);
 bool CheckTextureFormatType(GLenum format, GLenum type);
@@ -56,6 +60,8 @@ unsigned int GetStencilSize(D3DFORMAT stencilFormat);
 bool ConvertPrimitiveType(GLenum primitiveType, GLsizei primitiveCount,
                           D3DPRIMITIVETYPE *d3dPrimitiveType, int *d3dPrimitiveCount);
 D3DFORMAT ConvertRenderbufferFormat(GLenum format);
+D3DMULTISAMPLE_TYPE GetMultisampleTypeFromSamples(GLsizei samples);
+GLsizei GetSamplesFromMultisampleType(D3DMULTISAMPLE_TYPE type);
 
 }
 
diff --git a/WebCore/ChangeLog b/WebCore/ChangeLog
index b744c82..249666c 100644
--- a/WebCore/ChangeLog
+++ b/WebCore/ChangeLog
@@ -1,3 +1,13 @@
+2010-09-01  Zhenyao Mo  <zmo at google.com>
+
+        Reviewed by Kenneth Russell.
+
+        Roll ANGLE under webkit to r402
+        https://bugs.webkit.org/show_bug.cgi?id=45004
+
+        * platform/graphics/mac/GraphicsContext3DMac.mm: Update the code to use newer ANGLE interface.
+        (WebCore::GraphicsContext3D::GraphicsContext3D):
+
 2010-09-02  Ilya Tikhonovsky  <loislo at chromium.org>
 
         Reviewed by Yury Semikhatsky.
diff --git a/WebCore/platform/graphics/mac/GraphicsContext3DMac.mm b/WebCore/platform/graphics/mac/GraphicsContext3DMac.mm
index ab4ef4b..54b261c 100644
--- a/WebCore/platform/graphics/mac/GraphicsContext3DMac.mm
+++ b/WebCore/platform/graphics/mac/GraphicsContext3DMac.mm
@@ -31,7 +31,6 @@
 
 #import "BlockExceptions.h"
 
-#include "ANGLE/ResourceLimits.h"
 #include "ArrayBuffer.h"
 #include "ArrayBufferView.h"
 #include "WebGLObject.h"
@@ -186,23 +185,23 @@ GraphicsContext3D::GraphicsContext3D(GraphicsContext3D::Attributes attrs, HostWi
 
     TBuiltInResource ANGLEResources;
 
-    ANGLEResources.maxVertexAttribs = 0;
-    getIntegerv(GraphicsContext3D::MAX_VERTEX_ATTRIBS, &ANGLEResources.maxVertexAttribs);
-    ANGLEResources.maxVertexUniformVectors = 0;
-    getIntegerv(GraphicsContext3D::MAX_VERTEX_UNIFORM_VECTORS, &ANGLEResources.maxVertexUniformVectors);
-    ANGLEResources.maxVaryingVectors = 0;
-    getIntegerv(GraphicsContext3D::MAX_VARYING_VECTORS, &ANGLEResources.maxVaryingVectors);
-    ANGLEResources.maxVertexTextureImageUnits = 0;
-    getIntegerv(GraphicsContext3D::MAX_VERTEX_TEXTURE_IMAGE_UNITS, &ANGLEResources.maxVertexTextureImageUnits);
-    ANGLEResources.maxCombinedTextureImageUnits = 0;
-    getIntegerv(GraphicsContext3D::MAX_COMBINED_TEXTURE_IMAGE_UNITS, &ANGLEResources.maxCombinedTextureImageUnits);
-    ANGLEResources.maxTextureImageUnits = 0;
-    getIntegerv(GraphicsContext3D::MAX_TEXTURE_IMAGE_UNITS, &ANGLEResources.maxTextureImageUnits);
-    ANGLEResources.maxFragmentUniformVectors = 0;
-    getIntegerv(GraphicsContext3D::MAX_FRAGMENT_UNIFORM_VECTORS, &ANGLEResources.maxFragmentUniformVectors);
+    ANGLEResources.MaxVertexAttribs = 0;
+    getIntegerv(GraphicsContext3D::MAX_VERTEX_ATTRIBS, &ANGLEResources.MaxVertexAttribs);
+    ANGLEResources.MaxVertexUniformVectors = 0;
+    getIntegerv(GraphicsContext3D::MAX_VERTEX_UNIFORM_VECTORS, &ANGLEResources.MaxVertexUniformVectors);
+    ANGLEResources.MaxVaryingVectors = 0;
+    getIntegerv(GraphicsContext3D::MAX_VARYING_VECTORS, &ANGLEResources.MaxVaryingVectors);
+    ANGLEResources.MaxVertexTextureImageUnits = 0;
+    getIntegerv(GraphicsContext3D::MAX_VERTEX_TEXTURE_IMAGE_UNITS, &ANGLEResources.MaxVertexTextureImageUnits);
+    ANGLEResources.MaxCombinedTextureImageUnits = 0;
+    getIntegerv(GraphicsContext3D::MAX_COMBINED_TEXTURE_IMAGE_UNITS, &ANGLEResources.MaxCombinedTextureImageUnits);
+    ANGLEResources.MaxTextureImageUnits = 0;
+    getIntegerv(GraphicsContext3D::MAX_TEXTURE_IMAGE_UNITS, &ANGLEResources.MaxTextureImageUnits);
+    ANGLEResources.MaxFragmentUniformVectors = 0;
+    getIntegerv(GraphicsContext3D::MAX_FRAGMENT_UNIFORM_VECTORS, &ANGLEResources.MaxFragmentUniformVectors);
 
     // Always set to 1 for OpenGL ES.
-    ANGLEResources.maxDrawBuffers = 1;
+    ANGLEResources.MaxDrawBuffers = 1;
     
     m_compiler.setResources(ANGLEResources);
     

-- 
WebKit Debian packaging



More information about the Pkg-webkit-commits mailing list