mesa/progs/perf/vertexrate.c

277 lines
7.0 KiB
C

/*
* Copyright (C) 2009 VMware, Inc. All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included
* in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* VMWARE BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
* AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
/**
* Measure simple vertex processing rate via:
* - immediate mode
* - vertex arrays
* - VBO vertex arrays
* - glDrawElements
* - VBO glDrawElements
* - glDrawRangeElements
* - VBO glDrawRangeElements
*
* Brian Paul
* 16 Sep 2009
*/
#include <assert.h>
#include <string.h>
#include "glmain.h"
#include "common.h"
#define MAX_VERTS (100 * 100)
/** glVertex2/3/4 size */
#define VERT_SIZE 4
int WinWidth = 500, WinHeight = 500;
static GLuint VertexBO, ElementBO;
static unsigned NumVerts = MAX_VERTS;
static unsigned VertBytes = VERT_SIZE * sizeof(float);
static float *VertexData = NULL;
static unsigned NumElements = MAX_VERTS;
static GLuint *Elements = NULL;
/**
* Load VertexData buffer with a 2-D grid of points in the range [-1,1]^2.
*/
static void
InitializeVertexData(void)
{
unsigned i;
float x = -1.0, y = -1.0;
float dx = 2.0 / 100;
float dy = 2.0 / 100;
VertexData = (float *) malloc(NumVerts * VertBytes);
for (i = 0; i < NumVerts; i++) {
VertexData[i * VERT_SIZE + 0] = x;
VertexData[i * VERT_SIZE + 1] = y;
VertexData[i * VERT_SIZE + 2] = 0.0;
VertexData[i * VERT_SIZE + 3] = 1.0;
x += dx;
if (x > 1.0) {
x = -1.0;
y += dy;
}
}
Elements = (GLuint *) malloc(NumVerts * sizeof(GLuint));
for (i = 0; i < NumVerts; i++) {
Elements[i] = NumVerts - i - 1;
}
}
/** Called from test harness/main */
void
PerfInit(void)
{
InitializeVertexData();
/* setup VertexBO */
glGenBuffersARB(1, &VertexBO);
glBindBufferARB(GL_ARRAY_BUFFER_ARB, VertexBO);
glBufferDataARB(GL_ARRAY_BUFFER_ARB,
NumVerts * VertBytes, VertexData, GL_STATIC_DRAW_ARB);
glEnableClientState(GL_VERTEX_ARRAY);
/* setup ElementBO */
glGenBuffersARB(1, &ElementBO);
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, ElementBO);
glBufferDataARB(GL_ELEMENT_ARRAY_BUFFER_ARB,
NumElements * sizeof(GLuint), Elements, GL_STATIC_DRAW_ARB);
}
static void
DrawImmediate(unsigned count)
{
unsigned i;
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER, 0);
glBindBufferARB(GL_ARRAY_BUFFER, 0);
for (i = 0; i < count; i++) {
unsigned j;
glBegin(GL_POINTS);
for (j = 0; j < NumVerts; j++) {
#if VERT_SIZE == 4
glVertex4fv(VertexData + j * 4);
#elif VERT_SIZE == 3
glVertex3fv(VertexData + j * 3);
#elif VERT_SIZE == 2
glVertex2fv(VertexData + j * 2);
#else
abort();
#endif
}
glEnd();
}
glFinish();
PerfSwapBuffers();
}
static void
DrawArraysMem(unsigned count)
{
unsigned i;
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER, 0);
glBindBufferARB(GL_ARRAY_BUFFER, 0);
glVertexPointer(VERT_SIZE, GL_FLOAT, VertBytes, VertexData);
for (i = 0; i < count; i++) {
glDrawArrays(GL_POINTS, 0, NumVerts);
}
glFinish();
PerfSwapBuffers();
}
static void
DrawArraysVBO(unsigned count)
{
unsigned i;
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER, 0);
glBindBufferARB(GL_ARRAY_BUFFER, VertexBO);
glVertexPointer(VERT_SIZE, GL_FLOAT, VertBytes, (void *) 0);
for (i = 0; i < count; i++) {
glDrawArrays(GL_POINTS, 0, NumVerts);
}
glFinish();
PerfSwapBuffers();
}
static void
DrawElementsMem(unsigned count)
{
unsigned i;
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER, 0);
glBindBufferARB(GL_ARRAY_BUFFER, 0);
glVertexPointer(VERT_SIZE, GL_FLOAT, VertBytes, VertexData);
for (i = 0; i < count; i++) {
glDrawElements(GL_POINTS, NumVerts, GL_UNSIGNED_INT, Elements);
}
glFinish();
PerfSwapBuffers();
}
static void
DrawElementsBO(unsigned count)
{
unsigned i;
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER, ElementBO);
glBindBufferARB(GL_ARRAY_BUFFER, VertexBO);
glVertexPointer(VERT_SIZE, GL_FLOAT, VertBytes, (void *) 0);
for (i = 0; i < count; i++) {
glDrawElements(GL_POINTS, NumVerts, GL_UNSIGNED_INT, (void *) 0);
}
glFinish();
PerfSwapBuffers();
}
static void
DrawRangeElementsMem(unsigned count)
{
unsigned i;
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER, 0);
glBindBufferARB(GL_ARRAY_BUFFER, 0);
glVertexPointer(VERT_SIZE, GL_FLOAT, VertBytes, VertexData);
for (i = 0; i < count; i++) {
glDrawRangeElements(GL_POINTS, 0, NumVerts - 1,
NumVerts, GL_UNSIGNED_INT, Elements);
}
glFinish();
PerfSwapBuffers();
}
static void
DrawRangeElementsBO(unsigned count)
{
unsigned i;
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER, ElementBO);
glBindBufferARB(GL_ARRAY_BUFFER, VertexBO);
glVertexPointer(VERT_SIZE, GL_FLOAT, VertBytes, (void *) 0);
for (i = 0; i < count; i++) {
glDrawRangeElements(GL_POINTS, 0, NumVerts - 1,
NumVerts, GL_UNSIGNED_INT, (void *) 0);
}
glFinish();
PerfSwapBuffers();
}
void
PerfNextRound(void)
{
}
/** Called from test harness/main */
void
PerfDraw(void)
{
double rate;
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
perf_printf("Vertex rate (%d x Vertex%df)\n", NumVerts, VERT_SIZE);
rate = PerfMeasureRate(DrawImmediate);
rate *= NumVerts;
perf_printf(" Immediate mode: %s verts/sec\n", PerfHumanFloat(rate));
rate = PerfMeasureRate(DrawArraysMem);
rate *= NumVerts;
perf_printf(" glDrawArrays: %s verts/sec\n", PerfHumanFloat(rate));
rate = PerfMeasureRate(DrawArraysVBO);
rate *= NumVerts;
perf_printf(" VBO glDrawArrays: %s verts/sec\n", PerfHumanFloat(rate));
rate = PerfMeasureRate(DrawElementsMem);
rate *= NumVerts;
perf_printf(" glDrawElements: %s verts/sec\n", PerfHumanFloat(rate));
rate = PerfMeasureRate(DrawElementsBO);
rate *= NumVerts;
perf_printf(" VBO glDrawElements: %s verts/sec\n", PerfHumanFloat(rate));
rate = PerfMeasureRate(DrawRangeElementsMem);
rate *= NumVerts;
perf_printf(" glDrawRangeElements: %s verts/sec\n", PerfHumanFloat(rate));
rate = PerfMeasureRate(DrawRangeElementsBO);
rate *= NumVerts;
perf_printf(" VBO glDrawRangeElements: %s verts/sec\n", PerfHumanFloat(rate));
exit(0);
}