2012-03-26 3 views
1

나는 간단한 VBO를 실행하려고합니다. 하지만VBO + glBufferData 크기가 너무 크면 충돌이 발생합니다.

glBufferData(GL_ARRAY_BUFFER, sizeof(Vertex)*vertexcount, vertices, GL_STATIC_DRAW); 

를 호출 할 때 그냥 충돌하지만, vertexcount가 1531 이상 그리고 경우에만 예, "정점"배열에 저장, 또는 오히려 더 후 1531 개 요소에 대한 할당 충분한 공간이있다. 이것은 내 꼭지점 구조체입니다.

typedef struct{ 
    float x, y, z; 
    float nx, ny, nz; 
    float u, v; 
}Vertex, vertex; 

그래서 32 바이트 여야합니다. 32 바이트 * 1531 = 48992 바이트 = 48kb.

그러나 48kb는 정상 VBO에 비해 너무 높지 않습니다. 나는 무슨 일이 일어나는지 이해하지 못한다.

편집 :

윈도우 XP 32 비트 서비스 팩 3

엔비디아 지포스 9800GT

Edit2가 1천24메가바이트 : 내 전체 코드의 짧은 버전 : (흥미로운 부분은 하단에)

#include <windows.h> 
#include <glew.h> 
#include <wglew.h> 
#include <gl3.h> 
#include <gl/glu.h> 
#define BUFFER_OFFSET(i) ((char *)NULL + (i)) 

typedef struct{ 
    float x, y, z; 
float nx, ny, nz; 
float u, v; 
}Vertex, vertex; 

typedef struct{ 
    int first, second, third; 
}VertexIndex, vertexindex, vindex, Vindex; 

typedef struct{ 
    unsigned int vao; 
    unsigned int vertexcount, indexcount; 
}Mesh, mesh; 

typedef struct{ 
    HWND hwnd; 
    HDC hdc; 
    HGLRC hrc; 
}GLWindow, Window, window; 

void WindowShenanigans(Window *w, HINSTANCE *hinstance, WNDPROC WindowProc) 
{ 
    HWND tmp_hwnd; 
    WNDCLASS wndclass; 

    ZeroMemory(&wndclass, sizeof(WNDCLASS)); 
    wndclass.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC | CS_GLOBALCLASS; 
    wndclass.cbClsExtra = 0;  
    wndclass.cbWndExtra = 0; 
    wndclass.lpszMenuName = 0; 
    wndclass.hIcon = 0; 
    wndclass.hInstance = *hinstance; 
    wndclass.lpszClassName = "glclass"; 
    wndclass.hbrBackground = (HBRUSH)(COLOR_APPWORKSPACE); 
    wndclass.hCursor = LoadCursor(0, IDC_ARROW); 
    wndclass.lpfnWndProc = WindowProc; 

    if(RegisterClass(&wndclass) == 0) 
    { 
     return; 
    } 

    ShowCursor(TRUE); 

    tmp_hwnd = CreateWindowA ("glclass", 
          "bla", 
          WS_BORDER | WS_CAPTION | WS_SYSMENU, 
          0, 0, 
          600, 
          800, 
          HWND_DESKTOP, 
          NULL, 
          hinstance, 
          NULL); 

    w->hwnd = tmp_hwnd; 

    unsigned int PixelFormat; 
    PIXELFORMATDESCRIPTOR pfd; 

    pfd.nSize = sizeof(PIXELFORMATDESCRIPTOR); 
    pfd.nVersion = 1; 
    pfd.dwFlags = PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER; 
    pfd.iPixelType = PFD_TYPE_RGBA; 
    pfd.cColorBits = 32; 
    pfd.cDepthBits = 16; 
    pfd.cStencilBits = 32; 
    pfd.iLayerType = PFD_MAIN_PLANE; 

    w->hdc = GetDC(w->hwnd); 

    PixelFormat = ChoosePixelFormat(w->hdc, &pfd); 
    SetPixelFormat(w->hdc, PixelFormat, &pfd); 

    int attrib[] = 
    { 
      WGL_CONTEXT_MAJOR_VERSION_ARB, 3, 
      WGL_CONTEXT_MINOR_VERSION_ARB, 2, 
      WGL_CONTEXT_FLAGS_ARB, WGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB, 
      0 
    }; //OpenGL Context 

    HGLRC tmphrc = wglCreateContext(w->hdc); 

    wglMakeCurrent (w->hdc, tmphrc); 

    PFNWGLCREATEBUFFERREGIONARBPROC wglCreateContextAttribsARB =  (PFNWGLCREATEBUFFERREGIONARBPROC)wglGetProcAddress("wglCreateContextAttribsARB"); 
    w->hrc = (HGLRC)wglCreateContextAttribsARB(w->hdc, 0, (UINT)attrib) ; 

    ShowWindow(w->hwnd, SW_SHOW); 
    UpdateWindow(w->hwnd); 
} 

LRESULT CALLBACK WindowProc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) 
{ 
    switch(msg) 
    { 
     case WM_DESTROY: 
     { 
      PostQuitMessage(0); 
      return 0; 
     } 
     case WM_CLOSE: 
     { 
      PostQuitMessage(0); 
      return 0; 
     } 
     case WM_CREATE: 
     { 
     } 
     break; 
     case WM_SIZE: 
     { 
     } 
     break; 

     case WM_PAINT: 
     { 
     } 
     break; 
    } 
    return DefWindowProc(hwnd, msg, wparam, lparam); 
} 

BOOL ProcessMessage(MSG *msg) 
{ 
    if(GetMessage(msg, NULL, 0, 0) != 0) 
    { 
     TranslateMessage(msg); 
     DispatchMessage(msg); 
     return TRUE; 
    } 
    else 
    { 
     return FALSE; 
    } 
} 

/////////////////////////////////////////////////////////////////////////////////////////// 
void DataUpload(Mesh *m, Vindex *indices, Vertex *vertices) 
{ 
    unsigned int vbo, index_vbo; 

    glGenVertexArrays(1, &m->vao); 
    glBindVertexArray(m->vao); 

    glGenBuffers(1, &index_vbo); 
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, index_vbo); 
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(unsigned int)*3500, indices, GL_STATIC_DRAW); 

    glGenBuffers(1, &vbo); 
    glBindBuffer(GL_ARRAY_BUFFER, vbo); 
    // MessageBox(HWND_DESKTOP, "3..2..1..", "", MB_OK); 
    glBufferData(GL_ARRAY_BUFFER, sizeof(Vertex)*3500, vertices, GL_STATIC_DRAW); 
    // MessageBox(HWND_DESKTOP, "YEA", "", MB_OK); 

    glEnableVertexAttribArray(0); 
    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), BUFFER_OFFSET(0)); 
    glEnableVertexAttribArray(1); 
    glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), BUFFER_OFFSET(sizeof(float)*3)); 
    glEnableVertexAttribArray(2); 
    glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, sizeof(Vertex), BUFFER_OFFSET(sizeof(float)*6)); 
    glBindVertexArray(0); 
} 

void MeshGenerate(Mesh *m, float x, float y, float z) 
{ 
     int i; 
     Vertex *vertices; 
     Vindex *indices; 
     m->vertexcount = 3500; 
     m->indexcount = 3500; 
     vertices = malloc(3500*sizeof(vertex)); 
     indices = malloc(3500*sizeof(vindex)); 

     for(i = 0; i<3500; i++) 
     { 
      vertices[i].x = 1.0f; 
      vertices[i].y = 1.0f; 
      vertices[i].z = 1.0f; 
      vertices[i].nx = 1.0f; 
      vertices[i].ny = 1.0f; 
      vertices[i].nz = 1.0f; 
      vertices[i].u = 1.0f; 
      vertices[i].v = 1.0f; 
     } 
     for(i = 0; i<3500; i++) 
     { 
      indices[i].first = 1; 
      indices[i].second = 1; 
      indices[i].third = 1; 
     } 
     DataUpload(m, vertices, indices); 
     return; 
} 

int WINAPI WinMain(HINSTANCE hinstance, HINSTANCE hprevinstance, LPSTR lpcmdline, int nshowcmd) 
{ 
    MSG msg; 
    BOOL isActive = 1; 
    window w; 
    WindowShenanigans(&w, &hinstance, WindowProc); 

    glewInit(); 

    Mesh m; 
    MeshGenerate(&m, 1.0f, 1.0f, 1.0f); 

    while(isActive == 1) 
    { 
     SwapBuffers(w.hdc); 
     isActive = ProcessMessage(&msg); 
    } 

    return msg.wParam; 
} 
//////////////////////////////////////////////////////////////////////////////// 
+0

가되어야 하는가? – vmpstr

+2

[SSCCE] (http://sscce.org/)를 게시하십시오. – genpfault

+0

동일한 메모리를 mallocing하는 것이 도움이되는지 확인하십시오. –

답변

2
ogl.c: In function `MeshGenerate': 

ogl.c : 200 : 경고 : DataUpload' from incompatible pointer type ogl.c:200: warning: passing arg 3 of의 2 번 인수 : 경고 : 호환되지 않는 포인터 유형의 DataUpload '

제대로 작동하지 않는 샘플을 얻을 수 없습니다. 그러나 이것은 분명히 중요한 문제입니다.

DataUpload(m, vertices, indices); 

그것은 그냥 좋은 오래된 segfault의

DataUpload(m, indices, vertices); 
+0

예, 나는 <_ <. 이제 잘 작동합니다. – user1290204

관련 문제