diff options
Diffstat (limited to 'src/mesa')
| -rw-r--r-- | src/mesa/main/nvfragparse.c | 136 | ||||
| -rw-r--r-- | src/mesa/main/nvprogram.c | 28 | ||||
| -rw-r--r-- | src/mesa/main/nvprogram.h | 6 | 
3 files changed, 102 insertions, 68 deletions
| diff --git a/src/mesa/main/nvfragparse.c b/src/mesa/main/nvfragparse.c index 5df1a9b6dc..597f4e6d2c 100644 --- a/src/mesa/main/nvfragparse.c +++ b/src/mesa/main/nvfragparse.c @@ -1,4 +1,4 @@ -/* $Id: nvfragparse.c,v 1.8 2003/02/23 05:25:16 brianp Exp $ */ +/* $Id: nvfragparse.c,v 1.9 2003/02/25 19:30:27 brianp Exp $ */  /*   * Mesa 3-D graphics library @@ -135,15 +135,17 @@ static const struct instruction_pattern Instructions[] = {     { "UP4B",  FP_OPCODE_UP4B,  INPUT_1S, OUTPUT_V,            _C | _S },     { "UP4UB", FP_OPCODE_UP4UB, INPUT_1S, OUTPUT_V,            _C | _S },     { "X2D", FP_OPCODE_X2D, INPUT_3V, OUTPUT_V, _R | _H |      _C | _S }, -   { NULL, -1, 0, 0, 0 } +   { NULL, (enum fp_opcode) -1, 0, 0, 0 }  };  struct parse_state { -   const char *pos;                   /* current position */ +   const GLubyte *pos;                /* current position */     struct fragment_program *program;  /* current program */     GLuint numInst;                    /* number of instructions parsed */ +   GLuint inputsRead;                 /* bitmask of input registers used */ +   GLuint outputsWritten;             /* 2 = depth register */  }; @@ -152,13 +154,13 @@ struct parse_state {   * Search a list of instruction structures for a match.   */  static struct instruction_pattern -MatchInstruction(const char *token) +MatchInstruction(const GLubyte *token)  {     const struct instruction_pattern *inst;     struct instruction_pattern result;     for (inst = Instructions; inst->name; inst++) { -      if (_mesa_strncmp(token, inst->name, 3) == 0) { +      if (_mesa_strncmp((const char *) token, inst->name, 3) == 0) {           /* matched! */           int i = 3;           result = *inst; @@ -197,19 +199,19 @@ MatchInstruction(const char *token)  /**********************************************************************/ -static GLboolean IsLetter(char b) +static GLboolean IsLetter(GLubyte b)  {     return (b >= 'a' && b <= 'z') || (b >= 'A' && b <= 'Z') || (b == '_');  } -static GLboolean IsDigit(char b) +static GLboolean IsDigit(GLubyte b)  {     return b >= '0' && b <= '9';  } -static GLboolean IsWhitespace(char b) +static GLboolean IsWhitespace(GLubyte b)  {     return b == ' ' || b == '\t' || b == '\n' || b == '\r';  } @@ -221,7 +223,7 @@ static GLboolean IsWhitespace(char b)   * \return <= 0 we found an error, else, return number of characters parsed.   */  static GLint -GetToken(const char *str, char *token) +GetToken(const GLubyte *str, GLubyte *token)  {     GLint i = 0, j = 0; @@ -279,7 +281,7 @@ GetToken(const char *str, char *token)   * Get next token from input stream and increment stream pointer past token.   */  static GLboolean -Parse_Token(struct parse_state *parseState, char *token) +Parse_Token(struct parse_state *parseState, GLubyte *token)  {     GLint i;     i = GetToken(parseState->pos, token); @@ -296,7 +298,7 @@ Parse_Token(struct parse_state *parseState, char *token)   * Get next token from input stream but don't increment stream pointer.   */  static GLboolean -Peek_Token(struct parse_state *parseState, char *token) +Peek_Token(struct parse_state *parseState, GLubyte *token)  {     GLint i, len;     i = GetToken(parseState->pos, token); @@ -304,7 +306,7 @@ Peek_Token(struct parse_state *parseState, char *token)        parseState->pos += (-i);        return GL_FALSE;     } -   len = _mesa_strlen(token); +   len = _mesa_strlen((const char *) token);     parseState->pos += (i - len);     return GL_TRUE;  } @@ -314,10 +316,10 @@ Peek_Token(struct parse_state *parseState, char *token)   * String equality test   */  static GLboolean -StrEq(const char *a, const char *b) +StrEq(const GLubyte *a, const char *b)  {     GLint i; -   for (i = 0; a[i] && b[i] && a[i] == (char) b[i]; i++) +   for (i = 0; a[i] && b[i] && a[i] == (GLubyte) b[i]; i++)        ;     if (a[i] == 0 && b[i] == 0)        return GL_TRUE; @@ -329,13 +331,18 @@ StrEq(const char *a, const char *b)  /**********************************************************************/ -static const char *InputRegisters[] = { +static const char *InputRegisters[MAX_NV_FRAGMENT_PROGRAM_INPUTS + 1] = {     "WPOS", "COL0", "COL1", "FOGC",     "TEX0", "TEX1", "TEX2", "TEX3", "TEX4", "TEX5", "TEX6", "TEX7", NULL  }; -static const char *OutputRegisters[] = { -   "COLR", "COLH", "TEX0", "TEX1", "TEX2", "TEX3", "DEPR", NULL +static const char *OutputRegisters[MAX_NV_FRAGMENT_PROGRAM_OUTPUTS + 1] = { +   "COLR", "COLH", +   /* These are only allows for register combiners */ +   /* +   "TEX0", "TEX1", "TEX2", "TEX3", +   */ +   "DEPR", NULL  }; @@ -433,7 +440,7 @@ DummyRegisterNumber(GLuint r)  static GLboolean  Parse_String(struct parse_state *parseState, const char *pattern)  { -   const char *m; +   const GLubyte *m;     GLint i;     /* skip whitespace and comments */ @@ -452,7 +459,7 @@ Parse_String(struct parse_state *parseState, const char *pattern)     /* Try to match the pattern */     m = parseState->pos;     for (i = 0; pattern[i]; i++) { -      if (*m != pattern[i]) +      if (*m != (GLubyte) pattern[i])           return GL_FALSE;        m += 1;     } @@ -463,7 +470,7 @@ Parse_String(struct parse_state *parseState, const char *pattern)  static GLboolean -Parse_Identifier(struct parse_state *parseState, char *ident) +Parse_Identifier(struct parse_state *parseState, GLubyte *ident)  {     if (!Parse_Token(parseState, ident))        RETURN_ERROR; @@ -483,20 +490,20 @@ Parse_ScalarConstant(struct parse_state *parseState, GLfloat *number)  {     char *end = NULL; -   *number = (GLfloat) _mesa_strtod(parseState->pos, &end); +   *number = (GLfloat) _mesa_strtod((const char *) parseState->pos, &end); -   if (end && end > parseState->pos) { +   if (end && end > (char *) parseState->pos) {        /* got a number */ -      parseState->pos = end; +      parseState->pos = (GLubyte *) end;        return GL_TRUE;     }     else {        /* should be an identifier */ -      char ident[100]; +      GLubyte ident[100];        if (!Parse_Identifier(parseState, ident))           RETURN_ERROR1("Expected an identifier");        if (!_mesa_lookup_symbol(&(parseState->program->SymbolTable), -                               ident, number)) { +                               (const char *) ident, number)) {           RETURN_ERROR1("Undefined symbol");        }        return GL_TRUE; @@ -515,7 +522,7 @@ Parse_ScalarConstant(struct parse_state *parseState, GLfloat *number)  static GLboolean  Parse_VectorConstant(struct parse_state *parseState, GLfloat *vec)  { -   char token[100]; +   GLubyte token[100];     if (!Parse_String(parseState, "{"))        RETURN_ERROR1("Expected {"); @@ -579,7 +586,7 @@ Parse_VectorConstant(struct parse_state *parseState, GLfloat *vec)  static GLuint  Parse_VectorOrScalarConstant(struct parse_state *parseState, GLfloat *vec)  { -   char token[100]; +   GLubyte token[100];     if (!Peek_Token(parseState, token))        RETURN_ERROR;     if (token[0] == '{') { @@ -603,7 +610,7 @@ static GLboolean  Parse_TextureImageId(struct parse_state *parseState,                       GLuint *texUnit, GLuint *texTargetIndex)  { -   char imageSrc[100]; +   GLubyte imageSrc[100];     GLint unit;     if (!Parse_Token(parseState, imageSrc)) @@ -614,7 +621,7 @@ Parse_TextureImageId(struct parse_state *parseState,         imageSrc[2] != 'X') {        RETURN_ERROR1("Expected TEX# source");     } -   unit = _mesa_atoi(imageSrc + 3); +   unit = _mesa_atoi((const char *) imageSrc + 3);     if ((unit < 0 || unit > MAX_TEXTURE_IMAGE_UNITS) ||         (unit == 0 && (imageSrc[3] != '0' || imageSrc[4] != 0))) {        RETURN_ERROR1("Invalied TEX# source index"); @@ -655,7 +662,7 @@ Parse_TextureImageId(struct parse_state *parseState,   * the swizzle indexes.   */  static GLboolean -Parse_SwizzleSuffix(const char *token, GLuint swizzle[4]) +Parse_SwizzleSuffix(const GLubyte *token, GLuint swizzle[4])  {     if (token[1] == 0) {        /* single letter swizzle (scalar) */ @@ -696,7 +703,7 @@ static GLboolean  Parse_CondCodeMask(struct parse_state *parseState,                     struct fp_dst_register *dstReg)  { -   char token[100]; +   GLubyte token[100];     if (!Parse_Token(parseState, token))        RETURN_ERROR; @@ -743,7 +750,7 @@ Parse_CondCodeMask(struct parse_state *parseState,  static GLboolean  Parse_TempReg(struct parse_state *parseState, GLint *tempRegNum)  { -   char token[100]; +   GLubyte token[100];     /* Should be 'R##' or 'H##' */     if (!Parse_Token(parseState, token)) @@ -752,7 +759,7 @@ Parse_TempReg(struct parse_state *parseState, GLint *tempRegNum)        RETURN_ERROR1("Expected R## or H##");     if (IsDigit(token[1])) { -      GLint reg = _mesa_atoi((token + 1)); +      GLint reg = _mesa_atoi((const char *) (token + 1));        if (token[0] == 'H')           reg += 32;        if (reg >= MAX_NV_FRAGMENT_PROGRAM_TEMPS) @@ -770,16 +777,16 @@ Parse_TempReg(struct parse_state *parseState, GLint *tempRegNum)  static GLboolean  Parse_DummyReg(struct parse_state *parseState, GLint *regNum)  { -   char token[100]; +   GLubyte token[100];     /* Should be 'RC' or 'HC' */     if (!Parse_Token(parseState, token))        RETURN_ERROR; -   if (_mesa_strcmp(token, "RC")) { +   if (_mesa_strcmp((const char *) token, "RC")) {         *regNum = FP_DUMMY_REG_START;     } -   else if (_mesa_strcmp(token, "HC")) { +   else if (_mesa_strcmp((const char *) token, "HC")) {         *regNum = FP_DUMMY_REG_START + 1;     }     else { @@ -796,7 +803,7 @@ Parse_DummyReg(struct parse_state *parseState, GLint *regNum)  static GLboolean  Parse_ProgramParamReg(struct parse_state *parseState, GLint *regNum)  { -   char token[100]; +   GLubyte token[100];     if (!Parse_String(parseState, "p"))        RETURN_ERROR1("Expected p"); @@ -809,7 +816,7 @@ Parse_ProgramParamReg(struct parse_state *parseState, GLint *regNum)     if (IsDigit(token[0])) {        /* a numbered program parameter register */ -      GLint reg = _mesa_atoi(token); +      GLint reg = _mesa_atoi((const char *) token);        if (reg >= MAX_NV_FRAGMENT_PROGRAM_PARAMS)           RETURN_ERROR1("Bad constant program number");        *regNum = FP_PROG_REG_START + reg; @@ -831,7 +838,7 @@ Parse_ProgramParamReg(struct parse_state *parseState, GLint *regNum)  static GLboolean  Parse_AttribReg(struct parse_state *parseState, GLint *tempRegNum)  { -   char token[100]; +   GLubyte token[100];     GLint j;     /* Match 'f' */ @@ -849,6 +856,7 @@ Parse_AttribReg(struct parse_state *parseState, GLint *tempRegNum)     for (j = 0; InputRegisters[j]; j++) {        if (StrEq(token, InputRegisters[j])) {           *tempRegNum = FP_INPUT_REG_START + j; +         parseState->inputsRead |= (1 << j);           break;        }     } @@ -868,7 +876,7 @@ Parse_AttribReg(struct parse_state *parseState, GLint *tempRegNum)  static GLboolean  Parse_OutputReg(struct parse_state *parseState, GLint *outputRegNum)  { -   char token[100]; +   GLubyte token[100];     GLint j;     /* Match "o[" */ @@ -883,6 +891,7 @@ Parse_OutputReg(struct parse_state *parseState, GLint *outputRegNum)     for (j = 0; OutputRegisters[j]; j++) {        if (StrEq(token, OutputRegisters[j])) {           *outputRegNum = FP_OUTPUT_REG_START + j; +         parseState->outputsWritten |= (1 << j);           break;        }     } @@ -901,14 +910,14 @@ static GLboolean  Parse_MaskedDstReg(struct parse_state *parseState,                     struct fp_dst_register *dstReg)  { -   char token[100]; +   GLubyte token[100];     /* Dst reg can be R<n>, H<n>, o[n], RC or HC */     if (!Peek_Token(parseState, token))        RETURN_ERROR; -   if (_mesa_strcmp(token, "RC") == 0 || -       _mesa_strcmp(token, "HC") == 0) { +   if (_mesa_strcmp((const char *) token, "RC") == 0 || +       _mesa_strcmp((const char *) token, "HC") == 0) {        /* a write-only register */        if (!Parse_DummyReg(parseState, &dstReg->Register))           RETURN_ERROR; @@ -1007,7 +1016,7 @@ static GLboolean  Parse_SwizzleSrcReg(struct parse_state *parseState,                      struct fp_src_register *srcReg)  { -   char token[100]; +   GLubyte token[100];     /* XXX need to parse absolute value and another negation ***/     srcReg->NegateBase = GL_FALSE; @@ -1072,7 +1081,7 @@ static GLboolean  Parse_ScalarSrcReg(struct parse_state *parseState,                     struct fp_src_register *srcReg)  { -   char token[100]; +   GLubyte token[100];     /* check for '-' */     if (!Peek_Token(parseState, token)) @@ -1133,7 +1142,7 @@ static GLboolean  Parse_InstructionSequence(struct parse_state *parseState,                            struct fp_instruction program[])  { -   char token[100]; +   GLubyte token[100];     while (1) {        struct fp_instruction *inst = program + parseState->numInst; @@ -1155,7 +1164,7 @@ Parse_InstructionSequence(struct parse_state *parseState,        /* special instructions */        if (StrEq(token, "DEFINE")) { -         char id[100]; +         GLubyte id[100];           GLfloat value[7];  /* yes, 7 to be safe */           if (!Parse_Identifier(parseState, id))              RETURN_ERROR; @@ -1167,10 +1176,11 @@ Parse_InstructionSequence(struct parse_state *parseState,              RETURN_ERROR1("Expected ;");           printf("Parsed DEFINE %s = %f %f %f %f\n", id, value[0], value[1],                  value[2], value[3]); -         _mesa_add_symbol(&(parseState->program->SymbolTable), id, Definition, value); +         _mesa_add_symbol(&(parseState->program->SymbolTable), +                          (const char *) id, Definition, value);        }        else if (StrEq(token, "DECLARE")) { -         char id[100]; +         GLubyte id[100];           GLfloat value[7] = {0, 0, 0, 0, 0, 0, 0};  /* yes, to be safe */           if (!Parse_Identifier(parseState, id))              RETURN_ERROR; @@ -1188,7 +1198,8 @@ Parse_InstructionSequence(struct parse_state *parseState,           }           if (!Parse_String(parseState, ";"))              RETURN_ERROR1("Expected ;"); -         _mesa_add_symbol(&(parseState->program->SymbolTable), id, Declaration, value); +         _mesa_add_symbol(&(parseState->program->SymbolTable), +                          (const char *) id, Declaration, value);        }        else {           /* arithmetic instruction */ @@ -1331,13 +1342,17 @@ _mesa_parse_nv_fragment_program(GLcontext *ctx, GLenum dstTarget,     /* Get ready to parse */     parseState.program = program;     parseState.numInst = 0; -   program->InputsRead = 0; -   program->OutputsWritten = 0;     /* check the program header */     if (_mesa_strncmp((const char *) programString, "!!FP1.0", 7) == 0) {        target = GL_FRAGMENT_PROGRAM_NV; -      parseState.pos = (char *) programString + 7; +      parseState.pos = programString + 7; +   } +   else if (_mesa_strncmp((const char *) programString, "!!FCP1.0", 8) == 0) { +      /* fragment / register combiner program - not supported */ +      _mesa_set_program_error(ctx, 0, "Invalid fragment program header"); +      _mesa_error(ctx, GL_INVALID_OPERATION, "glLoadProgramNV(bad header)"); +      return;     }     else {        /* invalid header */ @@ -1357,6 +1372,13 @@ _mesa_parse_nv_fragment_program(GLcontext *ctx, GLenum dstTarget,     if (Parse_InstructionSequence(&parseState, instBuffer)) {        /* success! */ +      if (parseState.outputsWritten == 0) { +         /* must write at least one output! */ +         _mesa_error(ctx, GL_INVALID_OPERATION, +                     "Invalid fragment program - no outputs written."); +         return; +      } +        /* copy the compiled instructions */        assert(parseState.numInst <= MAX_NV_FRAGMENT_PROGRAM_INSTRUCTIONS);        newInst = (struct fp_instruction *) @@ -1378,6 +1400,8 @@ _mesa_parse_nv_fragment_program(GLcontext *ctx, GLenum dstTarget,           FREE(program->Instructions);        }        program->Instructions = newInst; +      program->InputsRead = parseState.inputsRead; +      program->OutputsWritten = parseState.outputsWritten;        /* allocate registers for declared program parameters */        _mesa_assign_program_registers(&(program->SymbolTable)); @@ -1395,11 +1419,11 @@ _mesa_parse_nv_fragment_program(GLcontext *ctx, GLenum dstTarget,  #ifdef DEBUG        {           GLint line, column; -         const char *lineStr; -         lineStr = _mesa_find_line_column((const char *) programString, +         const GLubyte *lineStr; +         lineStr = _mesa_find_line_column(programString,                                            parseState.pos, &line, &column);           _mesa_debug(ctx, "Parse error on line %d, column %d:%s\n", -                     line, column, lineStr); +                     line, column, (char *) lineStr);           _mesa_free((void *) lineStr);        }  #endif diff --git a/src/mesa/main/nvprogram.c b/src/mesa/main/nvprogram.c index 207d705a18..99634ce60c 100644 --- a/src/mesa/main/nvprogram.c +++ b/src/mesa/main/nvprogram.c @@ -1,4 +1,4 @@ -/* $Id: nvprogram.c,v 1.4 2003/02/23 05:23:53 brianp Exp $ */ +/* $Id: nvprogram.c,v 1.5 2003/02/25 19:30:28 brianp Exp $ */  /*   * Mesa 3-D graphics library @@ -104,7 +104,7 @@ _mesa_lookup_program_register(const struct symbol_table *symbolTable,     const struct symbol *s;     for (s = symbolTable->Head; s; s = s->Next) {        if (_mesa_strcmp(s->Name, (const char *) name) == 0 && -          _mesa_strlen(s->Name) == len) { +          _mesa_strlen(s->Name) == (size_t) len) {           return s->Register;        }     } @@ -141,19 +141,29 @@ _mesa_set_program_error(GLcontext *ctx, GLint pos, const char *string)  } -const char * -_mesa_find_line_column(const char *string, const char *pos, +/** + * Find the line number and column for 'pos' within 'string'. + * Return a copy of the line which contains 'pos'.  Free the line with + * _mesa_free(). + * \param string  the program string + * \param pos     the position within the string + * \param line    returns the line number corresponding to 'pos'. + * \param col     returns the column number corresponding to 'pos'. + * \return copy of the line containing 'pos'. + */ +const GLubyte * +_mesa_find_line_column(const GLubyte *string, const GLubyte *pos,                         GLint *line, GLint *col)  { -   const char *lineStart = string; -   const char *p = string; -   char *s; +   const GLubyte *lineStart = string; +   const GLubyte *p = string; +   GLubyte *s;     int len;     *line = 1;     while (p != pos) { -      if (*p == '\n') { +      if (*p == (GLubyte) '\n') {           (*line)++;           lineStart = p + 1;        } @@ -166,7 +176,7 @@ _mesa_find_line_column(const char *string, const char *pos,     while (*p != 0 && *p != '\n')        p++;     len = p - lineStart; -   s = (char *) _mesa_malloc(len + 1); +   s = (GLubyte *) _mesa_malloc(len + 1);     _mesa_memcpy(s, lineStart, len);     s[len] = 0; diff --git a/src/mesa/main/nvprogram.h b/src/mesa/main/nvprogram.h index c58b0edf5d..b41dc95097 100644 --- a/src/mesa/main/nvprogram.h +++ b/src/mesa/main/nvprogram.h @@ -1,4 +1,4 @@ -/* $Id: nvprogram.h,v 1.3 2003/02/23 05:23:54 brianp Exp $ */ +/* $Id: nvprogram.h,v 1.4 2003/02/25 19:30:29 brianp Exp $ */  /*   * Mesa 3-D graphics library @@ -55,8 +55,8 @@ _mesa_assign_program_registers(struct symbol_table *symbolTable);  extern void  _mesa_set_program_error(GLcontext *ctx, GLint pos, const char *string); -extern const char * -_mesa_find_line_column(const char *string, const char *pos, +extern const GLubyte * +_mesa_find_line_column(const GLubyte *string, const GLubyte *pos,                         GLint *line, GLint *col);  extern void | 
