diff --git a/opengl/tools/glgen/specs/jsr239/glspec-1.1extpack b/opengl/tools/glgen/specs/jsr239/glspec-1.1extpack index ca9e6d2c5..d6012d946 100644 --- a/opengl/tools/glgen/specs/jsr239/glspec-1.1extpack +++ b/opengl/tools/glgen/specs/jsr239/glspec-1.1extpack @@ -7,14 +7,14 @@ void glBlendFuncSeparate ( GLint srcRGB, GLint dstRGB, GLint srcAlpha, GLint dst GLint glCheckFramebufferStatusOES ( GLint target ) void glCompressedTexImage2D ( GLenum target, GLint level, GLenum internalformat, GLsizei width, GLsizei height, GLint border, GLsizei imageSize, const GLvoid *data ) void glCopyTexImage2D ( GLint target, GLint level, GLint internalformat, GLint x, GLint y, GLint width, GLint height, GLint border ) -void glDeleteFramebuffersOES ( GLint n, GLint *framebuffers ) -void glDeleteRenderbuffersOES ( GLint n, GLint *renderbuffers ) +void glDeleteFramebuffersOES ( GLint n, GLuint *framebuffers ) +void glDeleteRenderbuffersOES ( GLint n, GLuint *renderbuffers ) void glEnable ( GLint cap ) void glFramebufferRenderbufferOES ( GLint target, GLint attachment, GLint renderbuffertarget, GLint renderbuffer ) void glFramebufferTexture2DOES ( GLint target, GLint attachment, GLint textarget, GLint texture, GLint level ) void glGenerateMipmapOES ( GLint target ) -void glGenFramebuffersOES ( GLint n, GLint *framebuffers ) -void glGenRenderbuffersOES ( GLint n, GLint *renderbuffers ) +void glGenFramebuffersOES ( GLint n, GLuint *framebuffers ) +void glGenRenderbuffersOES ( GLint n, GLuint *renderbuffers ) void glGetFramebufferAttachmentParameterivOES ( GLint target, GLint attachment, GLint pname, GLint *params ) void glGetIntegerv ( GLint pname, GLint *params ) void glGetRenderbufferParameterivOES ( GLint target, GLint pname, GLint *params ) diff --git a/opengl/tools/glgen/specs/jsr239/glspec-checks b/opengl/tools/glgen/specs/jsr239/glspec-checks index c28e40300..9f8a793cc 100644 --- a/opengl/tools/glgen/specs/jsr239/glspec-checks +++ b/opengl/tools/glgen/specs/jsr239/glspec-checks @@ -29,28 +29,28 @@ glDrawTexfvOES check coords 5 glDrawTexivOES check coords 5 glDrawTexsvOES check coords 5 glDrawTexxvOES check coords 5 -glBindFramebufferOES unsupported -glBindRenderbufferOES unsupported -glBlendEquation unsupported -glBlendEquationSeparate unsupported -glBlendFuncSeparate unsupported -glCheckFramebufferStatusOES unsupported return 0 -glDeleteFramebuffersOES unsupported -glDeleteRenderbuffersOES unsupported -glFramebufferRenderbufferOES unsupported -glFramebufferStorageOES unsupported -glFramebufferTexture2DOES unsupported -glGenFramebuffersOES unsupported -glGenRenderbuffersOES unsupported -glGenerateMipmapOES unsupported +glBindFramebufferOES requires OES_framebuffer_object +glBindRenderbufferOES requires OES_framebuffer_object +glBlendEquation requires OES_blend_subtract +glBlendEquationSeparate requires OES_blend_equation_separate +glBlendFuncSeparate requires OES_blend_equation_separate +glCheckFramebufferStatusOES requires OES_framebuffer_object return 0 +glDeleteFramebuffersOES requires OES_framebuffer_object check framebuffers n +glDeleteRenderbuffersOES requires OES_framebuffer_object check renderbuffers n +glFramebufferRenderbufferOES requires OES_framebuffer_object +glFramebufferStorageOES requires OES_framebuffer_object +glFramebufferTexture2DOES requires OES_framebuffer_object +glGenFramebuffersOES requires OES_framebuffer_object check framebuffers n +glGenRenderbuffersOES requires OES_framebuffer_object check renderbuffers n +glGenerateMipmapOES requires OES_framebuffer_object +glGetFramebufferAttachmentParameterivOES requires OES_framebuffer_object +glGetRenderbufferParameterivOES requires OES_framebuffer_object +glIsFramebufferOES requires OES_framebuffer_object return JNI_FALSE +glIsRenderbufferOES requires OES_framebuffer_object return JNI_FALSE +glRenderbufferStorageOES requires OES_framebuffer_object +glGetTexGen requires OES_texture_cube_map +glTexGen requires OES_texture_cube_map +glTexGenf requires OES_texture_cube_map +glTexGeni requires OES_texture_cube_map +glTexGenx requires OES_texture_cube_map glGetBufferParameter unsupported -glGetFramebufferAttachmentParameterivOES unsupported -glGetRenderbufferParameterivOES unsupported -glGetTexGen unsupported -glIsFramebufferOES unsupported return JNI_FALSE -glIsRenderbufferOES unsupported return JNI_FALSE -glRenderbufferStorageOES unsupported return false -glTexGen unsupported -glTexGenf unsupported -glTexGeni unsupported -glTexGenx unsupported diff --git a/opengl/tools/glgen/src/JniCodeEmitter.java b/opengl/tools/glgen/src/JniCodeEmitter.java index e79170a28..2db4e8d2e 100644 --- a/opengl/tools/glgen/src/JniCodeEmitter.java +++ b/opengl/tools/glgen/src/JniCodeEmitter.java @@ -211,6 +211,8 @@ public class JniCodeEmitter { index += 5; } else if (checks[index].equals("unsupported")) { index += 1; + } else if (checks[index].equals("requires")) { + index += 2; } else if (checks[index].equals("nullAllowed")) { return true; } else { @@ -243,6 +245,8 @@ public class JniCodeEmitter { index += 5; } else if (checks[index].equals("unsupported")) { index += 1; + } else if (checks[index].equals("requires")) { + index += 2; } else if (checks[index].equals("nullAllowed")) { index += 1; } else { @@ -263,6 +267,8 @@ public class JniCodeEmitter { while (index < checks.length) { if (checks[index].equals("unsupported")) { return true; + } else if (checks[index].equals("requires")) { + index += 2; } else if (checks[index].equals("return")) { index += 2; } else if (checks[index].startsWith("check")) { @@ -280,7 +286,34 @@ public class JniCodeEmitter { } return false; } - + + String isRequiresFunc(CFunc cfunc) { + String[] checks = mChecker.getChecks(cfunc.getName()); + int index = 1; + if (checks != null) { + while (index < checks.length) { + if (checks[index].equals("unsupported")) { + index += 1; + } else if (checks[index].equals("requires")) { + return checks[index+1]; + } else if (checks[index].equals("return")) { + index += 2; + } else if (checks[index].startsWith("check")) { + index += 3; + } else if (checks[index].equals("ifcheck")) { + index += 5; + } else if (checks[index].equals("nullAllowed")) { + index += 1; + } else { + System.out.println("Error: unknown keyword \"" + + checks[index] + "\""); + System.exit(0); + } + } + } + return null; + } + void emitNativeBoundsChecks(CFunc cfunc, String cname, PrintStream out, boolean isBuffer, boolean emitExceptionCheck, String offset, String remaining, String iii) { @@ -365,6 +398,9 @@ public class JniCodeEmitter { } else if (checks[index].equals("unsupported")) { // ignore index += 1; + } else if (checks[index].equals("requires")) { + // ignore + index += 2; } else if (checks[index].equals("nullAllowed")) { // ignore index += 1; @@ -776,7 +812,23 @@ public class JniCodeEmitter { out.println(); return; } - + + String requiresExtension = isRequiresFunc(cfunc); + if (requiresExtension != null) { + out.println(indent + + "if (! supportsExtension(_env, _this, have_" + requiresExtension + "ID)) {"); + out.println(indent + indent + + "_env->ThrowNew(UOEClass,"); + out.println(indent + indent + + " \"" + cfunc.getName() + "\");"); + if (isVoid) { + out.println(indent + indent + " return;"); + } else { + String retval = getErrorReturnValue(cfunc); + out.println(indent + indent + " return " + retval + ";"); + } + out.println(indent + "}"); + } if (mUseContextPointer) { out.println(indent + "android::gl::ogles_context_t *ctx = getContext(_env, _this);"); diff --git a/opengl/tools/glgen/stubs/jsr239/GLCHeader.cpp b/opengl/tools/glgen/stubs/jsr239/GLCHeader.cpp index b3d1c6cb1..c2464b056 100644 --- a/opengl/tools/glgen/stubs/jsr239/GLCHeader.cpp +++ b/opengl/tools/glgen/stubs/jsr239/GLCHeader.cpp @@ -23,6 +23,23 @@ #include #include +// Work around differences between the generated name and the actual name. + +#define glBlendEquation glBlendEquationOES +#define glBlendEquationSeparate glBlendEquationSeparateOES +#define glBlendFuncSeparate glBlendFuncSeparateOES +#define glGetTexGenfv glGetTexGenfvOES +#define glGetTexGeniv glGetTexGenivOES +#define glGetTexGenxv glGetTexGenxvOES +#define glTexGenf glTexGenfOES +#define glTexGenfv glTexGenfvOES +#define glTexGeni glTexGeniOES +#define glTexGeniv glTexGenivOES +#define glTexGenx glTexGenxOES +#define glTexGenxv glTexGenxvOES + + + /* special calls implemented in Android's GLES wrapper used to more * efficiently bound-check passed arrays */ extern "C" { @@ -58,6 +75,11 @@ static jmethodID allowIndirectBuffersID; static jfieldID positionID; static jfieldID limitID; static jfieldID elementSizeShiftID; +static jfieldID haveCheckedExtensionsID; +static jfieldID have_OES_blend_equation_separateID; +static jfieldID have_OES_blend_subtractID; +static jfieldID have_OES_framebuffer_objectID; +static jfieldID have_OES_texture_cube_mapID; /* Cache method IDs each time the class is loaded. */ @@ -72,6 +94,11 @@ nativeClassInitBuffer(JNIEnv *_env) jclass g11impClassLocal = _env->FindClass("com/google/android/gles_jni/GLImpl"); G11ImplClass = (jclass) _env->NewGlobalRef(g11impClassLocal); + haveCheckedExtensionsID = _env->GetFieldID(G11ImplClass, "haveCheckedExtensions", "Z"); + have_OES_blend_equation_separateID = _env->GetFieldID(G11ImplClass, "have_OES_blend_equation_separate", "Z"); + have_OES_blend_subtractID = _env->GetFieldID(G11ImplClass, "have_OES_blend_subtract", "Z"); + have_OES_framebuffer_objectID = _env->GetFieldID(G11ImplClass, "have_OES_framebuffer_object", "Z"); + have_OES_texture_cube_mapID = _env->GetFieldID(G11ImplClass, "have_OES_texture_cube_map", "Z"); getBasePointerID = _env->GetStaticMethodID(nioAccessClass, "getBasePointer", "(Ljava/nio/Buffer;)J"); @@ -193,5 +220,63 @@ getNumCompressedTextureFormats() { return numCompressedTextureFormats; } +// Check if the extension at the head of pExtensions is pExtension. Note that pExtensions is +// terminated by either 0 or space, while pExtension is terminated by 0. + +static bool +extensionEqual(const GLubyte* pExtensions, const GLubyte* pExtension) { + while (true) { + char a = *pExtensions++; + char b = *pExtension++; + bool aEnd = a == '\0' || a == ' '; + bool bEnd = b == '\0'; + if ( aEnd || bEnd) { + return aEnd == bEnd; + } + if ( a != b ) { + return false; + } + } +} + +static const GLubyte* +nextExtension(const GLubyte* pExtensions) { + while (true) { + char a = *pExtensions++; + if ( a == '\0') { + return pExtensions-1; + } else if ( a == ' ') { + return pExtensions; + } + } +} + +static bool +checkForExtension(const GLubyte* pExtensions, const GLubyte* pExtension) { + for (;*pExtensions != '\0'; pExtensions = nextExtension(pExtensions)) { + if (extensionEqual(pExtensions, pExtension)) { + return true; + } + } + return false; +} + +static bool +supportsExtension(JNIEnv *_env, jobject impl, jfieldID fieldId) { + if (!_env->GetBooleanField(impl, haveCheckedExtensionsID)) { + _env->SetBooleanField(impl, haveCheckedExtensionsID, true); + const GLubyte* sExtensions = glGetString(GL_EXTENSIONS); + _env->SetBooleanField(impl, have_OES_blend_equation_separateID, + checkForExtension(sExtensions, (const GLubyte*) "GL_OES_blend_equation_separate")); + _env->SetBooleanField(impl, have_OES_blend_subtractID, + checkForExtension(sExtensions, (const GLubyte*) "GL_OES_blend_subtract")); + _env->SetBooleanField(impl, have_OES_framebuffer_objectID, + checkForExtension(sExtensions, (const GLubyte*) "GL_OES_framebuffer_object")); + _env->SetBooleanField(impl, have_OES_texture_cube_mapID, + checkForExtension(sExtensions, (const GLubyte*) "GL_OES_texture_cube_map")); + } + return _env->GetBooleanField(impl, fieldId); +} + // -------------------------------------------------------------------------- diff --git a/opengl/tools/glgen/stubs/jsr239/GLImplHeader.java-impl b/opengl/tools/glgen/stubs/jsr239/GLImplHeader.java-impl index 76fea3f6a..372710625 100644 --- a/opengl/tools/glgen/stubs/jsr239/GLImplHeader.java-impl +++ b/opengl/tools/glgen/stubs/jsr239/GLImplHeader.java-impl @@ -47,6 +47,12 @@ public class GLImpl implements GL10, GL10Ext, GL11, GL11Ext, GL11ExtensionPack { Buffer _pointSizePointerOES = null; Buffer _matrixIndexPointerOES = null; Buffer _weightPointerOES = null; + + private boolean haveCheckedExtensions; + private boolean have_OES_blend_equation_separate; + private boolean have_OES_blend_subtract; + private boolean have_OES_framebuffer_object; + private boolean have_OES_texture_cube_map; public GLImpl() { }