Skip to content

Commit

Permalink
Use glow instead of gl_generator for GL/GLES bindings (#321)
Browse files Browse the repository at this point in the history
Signed-off-by: sagudev <[email protected]>
  • Loading branch information
sagudev authored Jan 14, 2025
1 parent 300789d commit e78ea1b
Show file tree
Hide file tree
Showing 37 changed files with 939 additions and 944 deletions.
4 changes: 2 additions & 2 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ gl_generator = "0.14"
cfg_aliases = "0.2.1"

[features]
chains = ["fnv", "glow"]
chains = ["fnv"]
default = ["sm-raw-window-handle-06"]
sm-angle = []
sm-angle-builtin = ["mozangle"]
Expand All @@ -37,7 +37,7 @@ euclid = "0.22"
fnv = { version = "1.0", optional = true }
libc = "0.2"
log = "0.4"
glow = { version = "0.16", optional = true }
glow = "0.16"
osmesa-sys = { version = "0.1", optional = true }
rwh_05 = { package = "raw-window-handle", version = "0.5.2", features = ["std"], optional = true }
rwh_06 = { package = "raw-window-handle", version = "0.6.2", features = ["std"], optional = true }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ public class SurfmanInstrumentedTest {
private static native void testDeviceCreation();
private static native void testGenericSurfaceCreation();
private static native void testGL();
private static native void testNewlyCreatedContextsAreNotCurrent();
private static native void testNewlyCreatedContextsAreCurrent();
private static native void testSurfaceTextureBlitFramebuffer();
private static native void testSurfaceTextureRightSideUp();

Expand Down Expand Up @@ -75,8 +75,8 @@ public void gl() {
}

@Test
public void newlyCreatedContextsAreNotCurrent() {
testNewlyCreatedContextsAreNotCurrent();
public void newlyCreatedContextsAreCurrent() {
testNewlyCreatedContextsAreCurrent();
}

@Test
Expand Down
4 changes: 2 additions & 2 deletions android-example/rust/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -128,11 +128,11 @@ pub unsafe extern "system" fn Java_org_mozilla_surfmanthreadsexample_SurfmanInst
}

#[no_mangle]
pub unsafe extern "system" fn Java_org_mozilla_surfmanthreadsexample_SurfmanInstrumentedTest_testNewlyCreatedContextsAreNotCurrent(
pub unsafe extern "system" fn Java_org_mozilla_surfmanthreadsexample_SurfmanInstrumentedTest_testNewlyCreatedContextsAreCurrent(
_env: JNIEnv,
_class: JClass,
) {
tests::test_newly_created_contexts_are_not_current();
tests::test_newly_created_contexts_are_current();
}

#[no_mangle]
Expand Down
11 changes: 0 additions & 11 deletions build.rs
Original file line number Diff line number Diff line change
Expand Up @@ -50,15 +50,4 @@ fn main() {
let registry = Registry::new(Api::Egl, (1, 5), Profile::Core, Fallbacks::All, []);
registry.write_bindings(StructGenerator, &mut file).unwrap();
}

// Generate GL bindings.
if target_os == "android" || target_env == "ohos" {
let mut file = File::create(dest.join("gl_bindings.rs")).unwrap();
let registry = Registry::new(Api::Gles2, (3, 0), Profile::Core, Fallbacks::All, []);
registry.write_bindings(StructGenerator, &mut file).unwrap();
} else {
let mut file = File::create(dest.join("gl_bindings.rs")).unwrap();
let registry = Registry::new(Api::Gl, (3, 3), Profile::Core, Fallbacks::All, []);
registry.write_bindings(StructGenerator, &mut file).unwrap();
}
}
3 changes: 1 addition & 2 deletions examples/common/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,9 @@
// OpenGL convenience wrappers used in the examples.

use gl;
use gl::types::{GLchar, GLenum, GLint, GLuint};
use gl::types::{GLenum, GLint, GLuint};
use std::fs::File;
use std::io::Read;
use std::os::raw::c_void;
use std::ptr;
use surfman::GLApi;

Expand Down
9 changes: 6 additions & 3 deletions examples/offscreen.rs
Original file line number Diff line number Diff line change
Expand Up @@ -129,7 +129,10 @@ fn main() {

unsafe {
let surface_info = device.context_surface_info(&context).unwrap().unwrap();
gl::BindFramebuffer(gl::FRAMEBUFFER, surface_info.framebuffer_object);
gl::BindFramebuffer(
gl::FRAMEBUFFER,
surface_info.framebuffer_object.map_or(0, |fbo| fbo.0.get()),
);
gl::Viewport(0, 0, FRAMEBUFFER_WIDTH, FRAMEBUFFER_HEIGHT);
ck();
gl::ClearColor(0.0, 0.0, 0.0, 1.0);
Expand Down Expand Up @@ -200,7 +203,7 @@ impl TriVertexArray {
gl::FLOAT,
gl::FALSE,
12,
0 as *const GLvoid,
0 as _,
);
ck();
gl::VertexAttribPointer(
Expand All @@ -209,7 +212,7 @@ impl TriVertexArray {
gl::UNSIGNED_BYTE,
gl::TRUE,
12,
8 as *const GLvoid,
8 as _,
);
ck();
gl::EnableVertexAttribArray(tri_program.position_attribute as GLuint);
Expand Down
31 changes: 20 additions & 11 deletions examples/threads.rs
Original file line number Diff line number Diff line change
Expand Up @@ -285,12 +285,17 @@ impl App {
unsafe {
self.device.make_context_current(&self.context).unwrap();

let framebuffer_object = match self.device.context_surface_info(&self.context) {
Ok(Some(surface_info)) => surface_info.framebuffer_object,
_ => 0,
};

gl::BindFramebuffer(gl::FRAMEBUFFER, framebuffer_object);
let framebuffer_object = self
.device
.context_surface_info(&self.context)
.ok()
.flatten()
.and_then(|surface_info| surface_info.framebuffer_object);

gl::BindFramebuffer(
gl::FRAMEBUFFER,
framebuffer_object.map_or(0, |fbo| fbo.0.get()),
);
gl::Viewport(0, 0, self.window_size.width, self.window_size.height);

gl::ClearColor(0.0, 0.0, 1.0, 1.0);
Expand Down Expand Up @@ -400,7 +405,8 @@ impl App {
gl::BindTexture(
self.device.surface_gl_texture_target(),
self.device
.surface_texture_object(self.texture.as_ref().unwrap()),
.surface_texture_object(self.texture.as_ref().unwrap())
.map_or(0, |tex| tex.0.get()),
);
gl::Uniform1i(self.blit_vertex_array.blit_program.source_uniform, 0);
ck();
Expand Down Expand Up @@ -498,7 +504,10 @@ fn worker_thread(
.unwrap()
.framebuffer_object;

gl::BindFramebuffer(gl::FRAMEBUFFER, framebuffer_object);
gl::BindFramebuffer(
gl::FRAMEBUFFER,
framebuffer_object.map_or(0, |fbo| fbo.0.get()),
);
gl::Viewport(0, 0, size.width, size.height);

gl::ClearColor(0.0, 0.0, 0.0, 1.0);
Expand Down Expand Up @@ -650,7 +659,7 @@ impl BlitVertexArray {
gl::UNSIGNED_BYTE,
gl::FALSE,
2,
0 as *const GLvoid,
0 as _,
);
ck();
gl::EnableVertexAttribArray(blit_program.position_attribute as GLuint);
Expand Down Expand Up @@ -695,7 +704,7 @@ impl GridVertexArray {
gl::UNSIGNED_BYTE,
gl::FALSE,
2,
0 as *const GLvoid,
0 as _,
);
ck();
gl::EnableVertexAttribArray(grid_program.position_attribute as GLuint);
Expand Down Expand Up @@ -740,7 +749,7 @@ impl CheckVertexArray {
gl::UNSIGNED_BYTE,
gl::FALSE,
2,
0 as *const GLvoid,
0 as _,
);
ck();
gl::EnableVertexAttribArray(check_program.position_attribute as GLuint);
Expand Down
13 changes: 3 additions & 10 deletions src/chains.rs
Original file line number Diff line number Diff line change
Expand Up @@ -34,15 +34,8 @@ use std::collections::hash_map::Entry;
use std::fmt::Debug;
use std::hash::Hash;
use std::mem;
use std::num::NonZero;
use std::sync::{Arc, Mutex, MutexGuard, RwLock, RwLockReadGuard, RwLockWriteGuard};

impl crate::SurfaceInfo {
fn framebuffer(&self) -> Option<gl::NativeFramebuffer> {
NonZero::new(self.framebuffer_object).map(gl::NativeFramebuffer)
}
}

// The data stored for each swap chain.
struct SwapChainData<Device: DeviceAPI> {
// The size of the back buffer
Expand Down Expand Up @@ -201,9 +194,9 @@ impl<Device: DeviceAPI> SwapChainData<Device> {
if let PreserveBuffer::Yes(gl) = preserve_buffer {
let front_info = device.surface_info(&new_front_buffer);
unsafe {
gl.bind_framebuffer(gl::READ_FRAMEBUFFER, front_info.framebuffer());
gl.bind_framebuffer(gl::READ_FRAMEBUFFER, front_info.framebuffer_object);
debug_assert_eq!(gl.get_error(), gl::NO_ERROR);
gl.bind_framebuffer(gl::DRAW_FRAMEBUFFER, back_info.framebuffer());
gl.bind_framebuffer(gl::DRAW_FRAMEBUFFER, back_info.framebuffer_object);
debug_assert_eq!(gl.get_error(), gl::NO_ERROR);
gl.blit_framebuffer(
0,
Expand Down Expand Up @@ -398,7 +391,7 @@ impl<Device: DeviceAPI> SwapChainData<Device> {
.context_surface_info(context)
.unwrap()
.unwrap()
.framebuffer();
.framebuffer_object;
unsafe {
gl.bind_framebuffer(gl::FRAMEBUFFER, fbo);
gl.clear_color(color[0], color[1], color[2], color[3]);
Expand Down
22 changes: 5 additions & 17 deletions src/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@
#![allow(unused_imports)]

use crate::gl;
use crate::gl::types::GLuint;
use crate::info::GLVersion;
use crate::Gl;

Expand Down Expand Up @@ -79,29 +78,18 @@ pub(crate) fn current_context_uses_compatibility_profile(_gl: &Gl) -> bool {
#[cfg(not(any(target_os = "android", target_env = "ohos")))]
#[allow(dead_code)]
pub(crate) fn current_context_uses_compatibility_profile(gl: &Gl) -> bool {
use glow::HasContext;

unsafe {
// First, try `GL_CONTEXT_PROFILE_MASK`.
let mut context_profile_mask = 0;
gl.GetIntegerv(gl::CONTEXT_PROFILE_MASK, &mut context_profile_mask);
if gl.GetError() == gl::NO_ERROR
let context_profile_mask = gl.get_parameter_i32(gl::CONTEXT_PROFILE_MASK);
if gl.get_error() == gl::NO_ERROR
&& (context_profile_mask & gl::CONTEXT_COMPATIBILITY_PROFILE_BIT as i32) != 0
{
return true;
}

// Second, look for the `GL_ARB_compatibility` extension.
let mut num_extensions = 0;
gl.GetIntegerv(gl::NUM_EXTENSIONS, &mut num_extensions);
if gl.GetError() == gl::NO_ERROR {
for extension_index in 0..(num_extensions as GLuint) {
let extension = gl.GetStringi(gl::EXTENSIONS, extension_index) as *const c_char;
let extension = CStr::from_ptr(extension);
if extension.to_str() == Ok("GL_ARB_compatibility") {
return true;
}
}
}

false
gl.supported_extensions().contains("GL_ARB_compatibility")
}
}
6 changes: 3 additions & 3 deletions src/device.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,9 @@
//! The abstract interface that all devices conform to.
use super::connection::Connection as ConnectionInterface;
use crate::gl::types::{GLenum, GLuint};
use crate::{ContextAttributes, ContextID, Error, GLApi, SurfaceAccess, SurfaceInfo, SurfaceType};
use euclid::default::Size2D;
use glow::Texture;

use std::os::raw::c_void;

Expand Down Expand Up @@ -200,7 +200,7 @@ where
/// Returns the OpenGL texture target needed to read from this surface texture.
///
/// This will be `GL_TEXTURE_2D` or `GL_TEXTURE_RECTANGLE`, depending on platform.
fn surface_gl_texture_target(&self) -> GLenum;
fn surface_gl_texture_target(&self) -> u32;

/// Displays the contents of a widget surface on screen.
///
Expand Down Expand Up @@ -234,5 +234,5 @@ where
/// Returns the OpenGL texture object containing the contents of this surface.
///
/// It is only legal to read from, not write to, this texture object.
fn surface_texture_object(&self, surface_texture: &Self::SurfaceTexture) -> GLuint;
fn surface_texture_object(&self, surface_texture: &Self::SurfaceTexture) -> Option<Texture>;
}
35 changes: 17 additions & 18 deletions src/gl_utils.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,21 +2,21 @@
//
//! Various OpenGL utilities used by the different backends.
use glow::{HasContext, NativeFramebuffer};

use crate::gl;
use crate::gl::types::{GLenum, GLint, GLuint};
use crate::Gl;

#[allow(dead_code)]
pub(crate) fn create_and_bind_framebuffer(
gl: &Gl,
texture_target: GLenum,
texture_object: GLuint,
) -> GLuint {
texture_target: u32,
texture_object: Option<glow::NativeTexture>,
) -> NativeFramebuffer {
unsafe {
let mut framebuffer_object = 0;
gl.GenFramebuffers(1, &mut framebuffer_object);
gl.BindFramebuffer(gl::FRAMEBUFFER, framebuffer_object);
gl.FramebufferTexture2D(
let framebuffer_object = gl.create_framebuffer().unwrap();
gl.bind_framebuffer(gl::FRAMEBUFFER, Some(framebuffer_object));
gl.framebuffer_texture_2d(
gl::FRAMEBUFFER,
gl::COLOR_ATTACHMENT0,
texture_target,
Expand All @@ -27,25 +27,24 @@ pub(crate) fn create_and_bind_framebuffer(
}
}

pub(crate) fn unbind_framebuffer_if_necessary(gl: &Gl, framebuffer_object: GLuint) {
pub(crate) fn unbind_framebuffer_if_necessary(gl: &Gl, framebuffer_object: NativeFramebuffer) {
unsafe {
// Unbind the framebuffer if it's bound.
let (mut current_draw_framebuffer, mut current_read_framebuffer) = (0, 0);
gl.GetIntegerv(gl::DRAW_FRAMEBUFFER_BINDING, &mut current_draw_framebuffer);
gl.GetIntegerv(gl::READ_FRAMEBUFFER_BINDING, &mut current_read_framebuffer);
if current_draw_framebuffer == framebuffer_object as GLint {
gl.BindFramebuffer(gl::DRAW_FRAMEBUFFER, 0);
let current_draw_framebuffer = gl.get_parameter_framebuffer(gl::DRAW_FRAMEBUFFER_BINDING);
let current_read_framebuffer = gl.get_parameter_framebuffer(gl::READ_FRAMEBUFFER_BINDING);
if current_draw_framebuffer == Some(framebuffer_object) {
gl.bind_framebuffer(gl::DRAW_FRAMEBUFFER, None);
}
if current_read_framebuffer == framebuffer_object as GLint {
gl.BindFramebuffer(gl::READ_FRAMEBUFFER, 0);
if current_read_framebuffer == Some(framebuffer_object) {
gl.bind_framebuffer(gl::READ_FRAMEBUFFER, None);
}
}
}

#[allow(dead_code)]
pub(crate) fn destroy_framebuffer(gl: &Gl, framebuffer_object: GLuint) {
pub(crate) fn destroy_framebuffer(gl: &Gl, framebuffer_object: NativeFramebuffer) {
unbind_framebuffer_if_necessary(gl, framebuffer_object);
unsafe {
gl.DeleteFramebuffers(1, &framebuffer_object);
gl.delete_framebuffer(framebuffer_object);
}
}
Loading

0 comments on commit e78ea1b

Please sign in to comment.