Skip to content

Instantly share code, notes, and snippets.

@julienr
Last active February 8, 2018 16:08
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save julienr/7f0014da2d54227c269a to your computer and use it in GitHub Desktop.
Save julienr/7f0014da2d54227c269a to your computer and use it in GitHub Desktop.
OSmesa on ubuntu 14.04

Download

mesa-11.0.0-rc1.tar.gz glu-9.0.0.tar.gz

Build osmesa with gallium

http://www.paraview.org/Wiki/ParaView/ParaView_And_Mesa_3D#Installing_OSMesa_Gallium_llvmpipe_state-tracker

autoreconf -fi

CC=clang CXX=clang ./configure CXXFLAGS="-fPIC -O2 -g -DDEFAULT_SOFTWARE_DEPTH_BITS=31" CFLAGS="-fPIC -O2 -g -DDEFAULT_SOFTWARE_DEPTH_BITS=31" LDFLAGS="-lm -lstdc++" --disable-xvmc --disable-glx --disable-dri --with-dri-drivers="" --with-gallium-drivers="swrast" --enable-texture-float --enable-shared-glapi --disable-egl --with-egl-platforms="" --enable-gallium-osmesa --enable-gallium-llvm=yes --prefix=/opt/osmesa_llvmpipe

make -j6 make install

Build GLU (optional)

CC=clang CXX=clang ./configure PKG_CONFIG_PATH=/opt/osmesa_llvmpipe/lib/pkgconfig CXXFLAGS="-fPIC -O2" CFLAGS="-fPIC -O2" LDFLAGS="-lm -lstdc++" --enable-osmesa --prefix=/opt/osmesa_llvmpipe

make -j6 make install

TODO

Write a vispy backend for OSMesa : vispy/vispy#78

https://github.com/vispy/vispy/blob/master/vispy/app/backends/_template.py

OSMESA_PATH=/opt/osmesa_llvmpipe
LDFLAGS+=`PKG_CONFIG_PATH=$(OSMESA_PATH)/lib/pkgconfig/ pkg-config --libs osmesa`
CFLAGS+=`PKG_CONFIG_PATH=$(OSMESA_PATH)/lib/pkgconfig/ pkg-config --cflags osmesa`
all:
clang -o osmesa_test osmesa_test.cc $(LDFLAGS) $(CFLAGS) -lGLU
run:
LD_LIBRARY_PATH=$(OSMESA_PATH)/lib ./osmesa_test
// From http://cs.anu.edu.au/~Hugh.Fisher/mesa3d/memcube.source
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <GL/gl.h>
#include <GL/glu.h>
#include <GL/osmesa.h>
#define Near 0.1
#define Far 20.0
static int winWidth = 800;
static int winHeight = 600;
static int WireFrame = GL_TRUE;
static float Spin = 30;
static float CubeColor[4] = { 0, 1, 0, 1 };
static GLfloat Verts[8][3] = {
{ -0.5, 0.5, -0.5 }, /* 0 left top rear */
{ 0.5, 0.5, -0.5 }, /* 1 right top rear */
{ 0.5, -0.5, -0.5 }, /* 2 right bottom rear */
{ -0.5, -0.5, -0.5 }, /* 3 left bottom rear */
{ -0.5, 0.5, 0.5 }, /* 4 left top front */
{ 0.5, 0.5, 0.5 }, /* 5 right top front */
{ 0.5, -0.5, 0.5 }, /* 6 right bottom front */
{ -0.5, -0.5, 0.5 } /* 7 left bottom front */
};
static int Faces[6][4] = {
{ 4, 5, 6, 7 }, /* front */
{ 5, 1, 2, 6 }, /* right */
{ 0, 4, 7, 3 }, /* left */
{ 4, 0, 1, 5 }, /* top */
{ 7, 6, 2, 3 }, /* bottom */
{ 1, 0, 3, 2 } /* rear */
};
static GLfloat Normals[6][3] = {
{ 0, 0, 1 },
{ -1, 0, 0 },
{ 1, 0, 0 },
{ 0, 1, 0 },
{ 0, -1, 0 },
{ 0, 0, -1 }
};
static void Fail (const char * message)
{
fprintf(stderr, "%s", message);
exit(-1);
}
void CheckGL ()
{
int err;
err = glGetError();
if (err != GL_NO_ERROR)
Fail((char *)gluErrorString(err));
}
/**** Actual scene rendering ****/
static void drawCube()
{
int face, vert;
glBegin(GL_QUADS);
for (face = 0; face < 6; face++) {
for (vert = 0; vert < 4; vert ++) {
glVertex3fv(Verts[Faces[face][vert]]);
glNormal3fv(Normals[face]);
}
}
glEnd();
}
static void configWireStyle ()
{
glDisable(GL_LIGHTING);
glColor4fv(CubeColor);
glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
}
static void configLighting ()
{
static GLfloat ambient[4] = { 0.05, 0.05, 0.05, 1.0 };
static GLfloat white[4] = { 1, 1, 1, 1 };
static GLfloat black[4] = { 0, 0, 0, 1 };
static GLfloat position[4] = { 0, 1, 1, 0 };
glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
glEnable(GL_LIGHTING);
glEnable(GL_LIGHT0);
glLightfv(GL_LIGHT0, GL_AMBIENT, ambient);
glLightfv(GL_LIGHT0, GL_DIFFUSE, white);
glLightfv(GL_LIGHT0, GL_SPECULAR, white);
glLightfv(GL_LIGHT0, GL_POSITION, position);
glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, CubeColor);
glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, black);
glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, black);
}
static void setProjection ()
{
float aspect;
aspect = (float)winWidth / (float)winHeight;
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(60.0, aspect, Near, Far);
glMatrixMode(GL_MODELVIEW);
}
static void setViewpoint ()
{
glLoadIdentity();
gluLookAt(0, 0, 1,
0, 0, 0,
0, 1, 0);
}
static void drawScene ()
{
glPushMatrix();
glTranslatef(0.0, 0.0, -2.0);
glRotatef(Spin, 0.0, 1.0, 0.0);
if (WireFrame)
configWireStyle();
else
configLighting();
drawCube();
glPopMatrix();
}
static void redisplay ()
{
glClearColor(0, 0, 0, 0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glEnable(GL_DEPTH_TEST);
setProjection();
setViewpoint();
drawScene();
CheckGL();
}
// Assumes buffer is RGBA
void writeToBMP(const char* fname, int width, int height, const char* buffer) {
int filesize = 54 + 3*width*height;
unsigned char bmpfileheader[14] = {'B','M', 0,0,0,0, 0,0, 0,0, 54,0,0,0};
unsigned char bmpinfoheader[40] = {40,0,0,0, 0,0,0,0, 0,0,0,0, 1,0, 24,0};
unsigned char bmppad[3] = {0,0,0};
bmpfileheader[ 2] = (unsigned char)(filesize );
bmpfileheader[ 3] = (unsigned char)(filesize>> 8);
bmpfileheader[ 4] = (unsigned char)(filesize>>16);
bmpfileheader[ 5] = (unsigned char)(filesize>>24);
bmpinfoheader[ 4] = (unsigned char)( width );
bmpinfoheader[ 5] = (unsigned char)( width>> 8);
bmpinfoheader[ 6] = (unsigned char)( width>>16);
bmpinfoheader[ 7] = (unsigned char)( width>>24);
bmpinfoheader[ 8] = (unsigned char)( height );
bmpinfoheader[ 9] = (unsigned char)( height>> 8);
bmpinfoheader[10] = (unsigned char)( height>>16);
bmpinfoheader[11] = (unsigned char)( height>>24);
FILE* f = fopen(fname,"wb");
fwrite(bmpfileheader,1,14,f);
fwrite(bmpinfoheader,1,40,f);
for(int i=0; i<height; i++)
{
fwrite(buffer+(width*(height-i-1)*3),3,width,f);
fwrite(bmppad,1,(4-(width*3)%4)%4,f);
}
fclose(f);
}
// This returns a newly allocated buffer
char* BufferRGBAToRGB(int width, int height, const char* rgba_img) {
char* rgb_img = (char*)calloc(width * height, 4);
for (int i = 0; i < height; ++i) {
for (int j = 0; j < width; ++j) {
rgb_img[(i * width + j)*3 + 0] = rgba_img[(i * width + j)*4 + 0];
rgb_img[(i * width + j)*3 + 1] = rgba_img[(i * width + j)*4 + 1];
rgb_img[(i * width + j)*3 + 2] = rgba_img[(i * width + j)*4 + 2];
}
}
return rgb_img;
}
int main (int argc, char * argv[])
{
OSMesaContext ctx;
void * buffer;
// Seems like osmesa 10.4 only supports RGBA
ctx = OSMesaCreateContext(OSMESA_RGBA, NULL);
buffer = calloc(winWidth * winHeight, 4);
if (buffer == NULL)
Fail("Cannot allocate memory frame buffer");
if (! OSMesaMakeCurrent(ctx, buffer, GL_UNSIGNED_BYTE, winWidth, winHeight))
Fail("OSMesaMakeCurrent");
printf("GL_VERSION %d\n", GL_VERSION);
printf("GL_RENDERER %d\n", GL_RENDERER);
printf("GL vendor : %s version : %s\n", glGetString(GL_VENDOR),
glGetString(GL_VERSION));
printf("GL renderer : %s\n", glGetString(GL_RENDERER));
redisplay();
glFinish();
const char* rgb_buffer = BufferRGBAToRGB(winWidth, winHeight, (char*)buffer);
writeToBMP("cube.bmp", winWidth, winHeight, (char*)rgb_buffer);
//writeToPPM("cube.ppm", GL_RGB, winWidth, winHeight, buffer);
printf("Created cube.bmp\n");
exit(0);
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment