OSX上的OpenGL段错误,但在Raspberry Pi

时间:2017-03-25 06:47:52

标签: c macos opengl

我已经开始开发一个可以在Raspberry Pi和OS X上运行的OpenGL(ES)应用程序。我基于rasbian附带的“三角形”示例的起点。此示例显示带有映射纹理的旋转立方体。它使用特定的broadcom函数来初始化上下文。对于OSX,我使用了适当的GLUT功能。我已经将os函数拆分为osx vs pi,并且pi版本工作正常。当我运行osx版本时,我总是在redraw_scene()中的glDrawArrays()调用上得到段错误。通常,原因是顶点数据不正确。但是如上所述,相同的代码(与设置和绘图相关)适用于Pi。这是代码的修剪版本,用于演示错误。对于常规的OpenGL与ES,我可能需要做些不同的事情吗?

#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <GLUT/glut.h>

typedef struct {
   uint32_t screen_width;
   uint32_t screen_height;
   GLuint tex[6];
   GLfloat rot_angle_x_inc;
   GLfloat rot_angle_y_inc;
   GLfloat rot_angle_z_inc;
   GLfloat rot_angle_x;
   GLfloat rot_angle_y;
   GLfloat rot_angle_z;
   GLfloat distance;
   GLfloat distance_inc;
   char *tex_buf1;
   char *tex_buf2;
   char *tex_buf3;
} CUBE_STATE_T;

static CUBE_STATE_T _state, *state=&_state;

#define IMAGE_SIZE 128

const GLbyte quadx[6*4*3] = {
    -10, -10,  10, 10, -10,  10, -10,  10,  10, 10,  10,  10, -10, -10, -10, -10,  10, -10, 10, -10, -10, 10,  10, -10,
    -10, -10,  10, -10,  10,  10, -10, -10, -10, -10,  10, -10, 10, -10, -10, 10,  10, -10, 10, -10,  10, 10,  10,  10,
    -10,  10,  10, 10,  10,  10, -10,  10, -10, 10,  10, -10, -10, -10,  10, -10, -10, -10, 10, -10,  10, 10, -10, -10
};

const GLfloat texCoords[6 * 4 * 2] = {
    0.f,  0.f, 0.f,  1.f, 1.f,  0.f, 1.f,  1.f, 0.f,  0.f, 0.f,  1.f, 1.f,  0.f, 1.f,  1.f,
    0.f,  0.f, 0.f,  1.f, 1.f,  0.f, 1.f,  1.f, 0.f,  0.f, 0.f,  1.f, 1.f,  0.f, 1.f,  1.f,
    0.f,  0.f, 0.f,  1.f, 1.f,  0.f, 1.f,  1.f, 0.f,  0.f, 0.f,  1.f, 1.f,  0.f, 1.f,  1.f
};

void reshapeView(int width, int height);
void drawView();
void update_model();
void redraw_scene();

char * junk() {
    // dont load real images just make some random junk
    int image_sz = IMAGE_SIZE*IMAGE_SIZE*3;
    char * texture = (char*)malloc(image_sz);
    for (int x=0;x<image_sz;x++) {
        texture[x] = (char)x;
    }
    return texture;
}

void create() {
    char * myargv [1];
    int myargc = 1;
    myargv[0] = strdup("view");
    glutInit(&myargc, myargv);

    glutInitDisplayMode(GLUT_DOUBLE | GLUT_DEPTH | GLUT_RGBA);
    glutInitWindowPosition(0, 0);
    glutCreateWindow("window");
    glutFullScreen();

    state->tex_buf1 = junk();
    state->tex_buf2 = junk();
    state->tex_buf3 = junk();

    glGenTextures(6, &state->tex[0]);

    glBindTexture(GL_TEXTURE_2D, state->tex[0]);
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, IMAGE_SIZE, IMAGE_SIZE, 0,
                 GL_RGB, GL_UNSIGNED_BYTE, state->tex_buf1);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, (GLfloat)GL_NEAREST);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, (GLfloat)GL_NEAREST);

    glBindTexture(GL_TEXTURE_2D, state->tex[1]);
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, IMAGE_SIZE, IMAGE_SIZE, 0,
                 GL_RGB, GL_UNSIGNED_BYTE, state->tex_buf1);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, (GLfloat)GL_NEAREST);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, (GLfloat)GL_NEAREST);

    glBindTexture(GL_TEXTURE_2D, state->tex[2]);
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, IMAGE_SIZE, IMAGE_SIZE, 0,
                 GL_RGB, GL_UNSIGNED_BYTE, state->tex_buf2);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, (GLfloat)GL_NEAREST);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, (GLfloat)GL_NEAREST);

    glBindTexture(GL_TEXTURE_2D, state->tex[3]);
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, IMAGE_SIZE, IMAGE_SIZE, 0,
                 GL_RGB, GL_UNSIGNED_BYTE, state->tex_buf2);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, (GLfloat)GL_NEAREST);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, (GLfloat)GL_NEAREST);

    glBindTexture(GL_TEXTURE_2D, state->tex[4]);
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, IMAGE_SIZE, IMAGE_SIZE, 0,
                 GL_RGB, GL_UNSIGNED_BYTE, state->tex_buf3);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, (GLfloat)GL_NEAREST);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, (GLfloat)GL_NEAREST);

    glBindTexture(GL_TEXTURE_2D, state->tex[5]);
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, IMAGE_SIZE, IMAGE_SIZE, 0,
                 GL_RGB, GL_UNSIGNED_BYTE, state->tex_buf3);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, (GLfloat)GL_NEAREST);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, (GLfloat)GL_NEAREST);

    glTexCoordPointer(2, GL_FLOAT, 0, texCoords);
    glEnableClientState(GL_TEXTURE_COORD_ARRAY);

    glEnable(GL_TEXTURE_2D);

    glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
    glEnable(GL_CULL_FACE);
    glMatrixMode(GL_MODELVIEW);

    glutReshapeFunc(reshapeView);
    glutDisplayFunc(drawView);
    glutIdleFunc(drawView);
}

void reshapeView(int width, int height) {
    state->screen_width = width;
    state->screen_height = height;

    glHint( GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST );
    glViewport(0, 0, (GLsizei)state->screen_width, (GLsizei)state->screen_height);
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();

    float nearp = 1.0f;
    float farp = 500.0f;
    float hht = nearp * (float)tan(45.0 / 2.0 / 180.0 * 3.141592654);
    float hwd = hht * (float)state->screen_width / (float)state->screen_height;

    glFrustum(-hwd, hwd, -hht, hht, nearp, farp);

    glEnableClientState( GL_VERTEX_ARRAY );
    glVertexPointer( 3, GL_BYTE, 0, quadx );

    glMatrixMode(GL_MODELVIEW);
    glLoadIdentity();
    glTranslatef(0.f, 0.f, -50.f);

    state->rot_angle_x = 45.f;
    state->rot_angle_y = 30.f;
    state->rot_angle_z = 0.f;
    state->rot_angle_x_inc = 0.5f;
    state->rot_angle_y_inc = 0.5f;
    state->rot_angle_z_inc = 0.f;
    state->distance = 40.f;
}

void drawView() {
    update_model();
    redraw_scene();
    glutSwapBuffers();
}

void update_model() {
    glLoadIdentity();
    glTranslatef(0.f, 0.f, -state->distance);

    glRotatef(state->rot_angle_x, 1.0f, 0.f, 0.f);
    glRotatef(state->rot_angle_y, 0.f, 1.0f, 0.f);
    glRotatef(state->rot_angle_z, 0.f, 0.f, 1.0f);
}

void redraw_scene() {
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

    glBindTexture(GL_TEXTURE_2D, state->tex[0]);
    glRotatef(270.f, 0.f, 0.f, 1.f ); // front face normal along z axis
    // ZOMG segfaults here!!! 
    glDrawArrays( GL_TRIANGLE_STRIP, 0, 4);

    glBindTexture(GL_TEXTURE_2D, state->tex[1]);
    glRotatef(90.f, 0.f, 0.f, 1.f ); // back face normal along z axis
    glDrawArrays( GL_TRIANGLE_STRIP, 4, 4);

    glBindTexture(GL_TEXTURE_2D, state->tex[2]);
    glRotatef(90.f, 1.f, 0.f, 0.f ); // left face normal along x axis
    glDrawArrays( GL_TRIANGLE_STRIP, 8, 4);

    glBindTexture(GL_TEXTURE_2D, state->tex[3]);
    glRotatef(90.f, 1.f, 0.f, 0.f ); // right face normal along x axis
    glDrawArrays( GL_TRIANGLE_STRIP, 12, 4);

    glBindTexture(GL_TEXTURE_2D, state->tex[4]);
    glRotatef(270.f, 0.f, 1.f, 0.f ); // top face normal along y axis
    glDrawArrays( GL_TRIANGLE_STRIP, 16, 4);

    glBindTexture(GL_TEXTURE_2D, state->tex[5]);
    glRotatef(90.f, 0.f, 1.f, 0.f ); // bottom face normal along y axis
    glDrawArrays( GL_TRIANGLE_STRIP, 20, 4);
}

int main() {
    create();
    glutMainLoop();
    return 0;
}

CMake文件......

cmake_minimum_required(VERSION 3.5)
project(jni)

set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -framework OpenGL -framework GLUT -Wno-deprecated -std=c++11")

set(SOURCE_FILES
    demo.cpp
)

add_executable(demo.bin ${SOURCE_FILES})

1 个答案:

答案 0 :(得分:0)

您应该在segfault之前检查glGetError()的返回值,以确定出现了什么问题。段错误可能是由于驱动程序或显卡不支持某些类型的OpenGL操作引起的。