Skip to content

Commit

Permalink
Preshader input registers are separate from the actual shader constan…
Browse files Browse the repository at this point in the history
…t file!

So make the effort to manage yet-another set of arrays for these registers...
  • Loading branch information
icculus committed Jun 1, 2011
1 parent f63af56 commit 69df21a
Show file tree
Hide file tree
Showing 4 changed files with 153 additions and 7 deletions.
19 changes: 19 additions & 0 deletions mojoshader.h
Expand Up @@ -3002,6 +3002,25 @@ void MOJOSHADER_glSetVertexAttribute(MOJOSHADER_usage usage,
int normalized, unsigned int stride,
const void *ptr);




/* These below functions are temporary and will be removed from the API once
the real Effects API is written. Do not use! */
void MOJOSHADER_glSetVertexPreshaderUniformF(unsigned int idx, const float *data,
unsigned int vec4n);
void MOJOSHADER_glGetVertexPreshaderUniformF(unsigned int idx, float *data,
unsigned int vec4n);
void MOJOSHADER_glSetPixelPreshaderUniformF(unsigned int idx, const float *data,
unsigned int vec4n);
void MOJOSHADER_glGetPixelPreshaderUniformF(unsigned int idx, float *data,
unsigned int vec4n);
/* These above functions are temporary and will be removed from the API once
the real Effects API is written. Do not use! */




/*
* Inform MojoShader that it should commit any pending state to the GL. This
* must be called after you bind a program and update any inputs, right
Expand Down
18 changes: 14 additions & 4 deletions mojoshader_effects.c
Expand Up @@ -14,7 +14,7 @@

#if SUPPORT_PRESHADERS
void MOJOSHADER_runPreshader(const MOJOSHADER_preshader *preshader,
float *regs)
const float *inregs, float *outregs)
{
// this is fairly straightforward, as there aren't any branching
// opcodes in the preshader instruction set (at the moment, at least).
Expand Down Expand Up @@ -61,14 +61,24 @@ void MOJOSHADER_runPreshader(const MOJOSHADER_preshader *preshader,
} // case

case MOJOSHADER_PRESHADEROPERAND_INPUT:
if (isscalar)
src[opiter][0] = inregs[index];
else
{
int cpy;
for (cpy = 0; cpy < elems; cpy++)
src[opiter][cpy] = inregs[index+cpy];
} // else
break;

case MOJOSHADER_PRESHADEROPERAND_OUTPUT:
if (isscalar)
src[opiter][0] = regs[index];
src[opiter][0] = outregs[index];
else
{
int cpy;
for (cpy = 0; cpy < elems; cpy++)
src[opiter][cpy] = regs[index+cpy];
src[opiter][cpy] = outregs[index+cpy];
} // else
break;

Expand Down Expand Up @@ -161,7 +171,7 @@ void MOJOSHADER_runPreshader(const MOJOSHADER_preshader *preshader,
{
assert(operand->type == MOJOSHADER_PRESHADEROPERAND_OUTPUT);
for (i = 0; i < elems; i++)
regs[operand->index + i] = (float) dst[i];
outregs[operand->index + i] = (float) dst[i];
} // else
} // for
} // MOJOSHADER_runPreshader
Expand Down
2 changes: 1 addition & 1 deletion mojoshader_internal.h
Expand Up @@ -78,7 +78,7 @@
#endif

#if SUPPORT_PRESHADERS
void MOJOSHADER_runPreshader(const MOJOSHADER_preshader *, float *);
void MOJOSHADER_runPreshader(const MOJOSHADER_preshader*, const float*, float*);
#else
#define MOJOSHADER_runPreshader(a, b)
#endif
Expand Down
121 changes: 119 additions & 2 deletions mojoshader_opengl.c
Expand Up @@ -7,6 +7,9 @@
* This file written by Ryan C. Gordon.
*/

// !!! FIXME: preshaders shouldn't be handled in here at all. This should
// !!! FIXME: be in the Effects API, once that's actually written.

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
Expand Down Expand Up @@ -85,6 +88,12 @@ struct MOJOSHADER_glProgram
GLint *ps_uniforms_int4;
size_t ps_uniforms_bool_count;
GLint *ps_uniforms_bool;

size_t vs_preshader_reg_count;
GLfloat *vs_preshader_regs;
size_t ps_preshader_reg_count;
GLfloat *ps_preshader_regs;

uint32 refcount;
// GLSL uses these...location of uniform arrays.
GLint vs_float4_loc;
Expand Down Expand Up @@ -1279,6 +1288,8 @@ static void program_unref(MOJOSHADER_glProgram *program)
ctx->profileDeleteProgram(program->handle);
shader_unref(program->vertex);
shader_unref(program->fragment);
Free(program->vs_preshader_regs);
Free(program->ps_preshader_regs);
Free(program->vs_uniforms_float4);
Free(program->vs_uniforms_int4);
Free(program->vs_uniforms_bool);
Expand Down Expand Up @@ -1395,6 +1406,38 @@ static int lookup_uniforms(MOJOSHADER_glProgram *program,

#undef MAKE_ARRAY

if (pd->preshader)
{
unsigned int largest = 0;
const MOJOSHADER_symbol *sym = pd->preshader->symbols;
for (i = 0; i < pd->preshader->symbol_count; i++, sym++)
{
const unsigned int val = sym->register_index + sym->register_count;
if (val > largest)
largest = val;
} // for

if (largest > 0)
{
const size_t len = largest * sizeof (GLfloat);
GLfloat *buf = (GLfloat *) Malloc(len);
if (buf == NULL)
return 0;
memset(buf, '\0', len);

if (shader_type == MOJOSHADER_TYPE_VERTEX)
{
program->vs_preshader_reg_count = largest;
program->vs_preshader_regs = buf;
} // if
else if (shader_type == MOJOSHADER_TYPE_PIXEL)
{
program->ps_preshader_reg_count = largest;
program->ps_preshader_regs = buf;
} // else if
} // if
} // if

return 1;
} // lookup_uniforms

Expand Down Expand Up @@ -1884,6 +1927,78 @@ void MOJOSHADER_glSetVertexAttribute(MOJOSHADER_usage usage,
} // MOJOSHADER_glSetVertexAttribute


void MOJOSHADER_glSetVertexPreshaderUniformF(unsigned int idx,
const float *data,
unsigned int vec4n)
{
MOJOSHADER_glProgram *program = ctx->bound_program;
if (program == NULL)
return; // nothing to do.

const uint maxregs = program->vs_preshader_reg_count;
if (idx < maxregs)
{
assert(sizeof (GLfloat) == sizeof (float));
const uint cpy = (minuint(maxregs - idx, vec4n) * sizeof (*data)) * 4;
memcpy(program->vs_preshader_regs + (idx * 4), data, cpy);
program->generation = ctx->generation-1;
} // if
} // MOJOSHADER_glSetVertexPreshaderUniformF


void MOJOSHADER_glGetVertexPreshaderUniformF(unsigned int idx, float *data,
unsigned int vec4n)
{
MOJOSHADER_glProgram *program = ctx->bound_program;
if (program == NULL)
return; // nothing to do.

const uint maxregs = program->vs_preshader_reg_count;
if (idx < maxregs)
{
assert(sizeof (GLfloat) == sizeof (float));
const uint cpy = (minuint(maxregs - idx, vec4n) * sizeof (*data)) * 4;
memcpy(data, program->vs_preshader_regs + (idx * 4), cpy);
} // if
} // MOJOSHADER_glGetVertexPreshaderUniformF


void MOJOSHADER_glSetPixelPreshaderUniformF(unsigned int idx,
const float *data,
unsigned int vec4n)
{
MOJOSHADER_glProgram *program = ctx->bound_program;
if (program == NULL)
return; // nothing to do.

const uint maxregs = program->ps_preshader_reg_count;
if (idx < maxregs)
{
assert(sizeof (GLfloat) == sizeof (float));
const uint cpy = (minuint(maxregs - idx, vec4n) * sizeof (*data)) * 4;
memcpy(program->ps_preshader_regs + (idx * 4), data, cpy);
program->generation = ctx->generation-1;
} // if
} // MOJOSHADER_glSetPixelPreshaderUniformF


void MOJOSHADER_glGetPixelPreshaderUniformF(unsigned int idx, float *data,
unsigned int vec4n)
{
MOJOSHADER_glProgram *program = ctx->bound_program;
if (program == NULL)
return; // nothing to do.

const uint maxregs = program->ps_preshader_reg_count;
if (idx < maxregs)
{
assert(sizeof (GLfloat) == sizeof (float));
const uint cpy = (minuint(maxregs - idx, vec4n) * sizeof (*data)) * 4;
memcpy(data, program->ps_preshader_regs + (idx * 4), cpy);
} // if
} // MOJOSHADER_glGetPixelPreshaderUniformF


void MOJOSHADER_glProgramReady(void)
{
MOJOSHADER_glProgram *program = ctx->bound_program;
Expand Down Expand Up @@ -1915,7 +2030,8 @@ void MOJOSHADER_glProgramReady(void)
preshader = program->vertex->parseData->preshader;
if (preshader)
{
MOJOSHADER_runPreshader(preshader, ctx->vs_reg_file_f);
MOJOSHADER_runPreshader(preshader, program->vs_preshader_regs,
ctx->vs_reg_file_f);
ran_preshader = 1;
} // if
} // if
Expand All @@ -1925,7 +2041,8 @@ void MOJOSHADER_glProgramReady(void)
preshader = program->fragment->parseData->preshader;
if (preshader)
{
MOJOSHADER_runPreshader(preshader, ctx->ps_reg_file_f);
MOJOSHADER_runPreshader(preshader, program->ps_preshader_regs,
ctx->ps_reg_file_f);
ran_preshader = 1;
} // if
} // if
Expand Down

0 comments on commit 69df21a

Please sign in to comment.