Пример #1
0
static GLboolean
Parse_OutputReg(struct parse_state *parseState, GLint *outputRegNum)
{
   GLubyte token[100];

   /* Match "o[" */
   if (!Parse_String(parseState, "o["))
      RETURN_ERROR1("Expected o[");

   /* Get output reg name */
   if (!Parse_Token(parseState, token))
      RETURN_ERROR;

   /* try to match an output register name */
   if (_mesa_strcmp((char *) token, "COLR") == 0 ||
       _mesa_strcmp((char *) token, "COLH") == 0) {
      /* note that we don't distinguish between COLR and COLH */
      *outputRegNum = FRAG_RESULT_COLOR;
      parseState->outputsWritten |= (1 << FRAG_RESULT_COLOR);
   }
   else if (_mesa_strcmp((char *) token, "DEPR") == 0) {
      *outputRegNum = FRAG_RESULT_DEPTH;
      parseState->outputsWritten |= (1 << FRAG_RESULT_DEPTH);
   }
   else {
      RETURN_ERROR1("Invalid output register name");
   }

   /* Match ']' */
   if (!Parse_String(parseState, "]"))
      RETURN_ERROR1("Expected ]");

   return GL_TRUE;
}
Пример #2
0
/**
 * Called in response to #extension directives to enable/disable
 * the named extension.
 */
static GLboolean
pp_ext_set(pp_ext *self, const char *name, GLboolean enable)
{
   if (_mesa_strcmp (name, "GL_ARB_draw_buffers") == 0)
      self->ARB_draw_buffers = enable;
   else if (_mesa_strcmp (name, "GL_ARB_texture_rectangle") == 0)
      self->ARB_texture_rectangle = enable;
   else
      return GL_FALSE;
   return GL_TRUE;
}
Пример #3
0
/**
 * Parse f[name]  - fragment input register
 */
static GLboolean
Parse_FragReg(struct parse_state *parseState, GLint *tempRegNum)
{
   GLubyte token[100];
   GLint j;

   /* Match 'f[' */
   if (!Parse_String(parseState, "f["))
      RETURN_ERROR1("Expected f[");

   /* get <name> and look for match */
   if (!Parse_Token(parseState, token)) {
      RETURN_ERROR;
   }
   for (j = 0; InputRegisters[j]; j++) {
      if (_mesa_strcmp((const char *) token, InputRegisters[j]) == 0) {
         *tempRegNum = j;
         parseState->inputsRead |= (1 << j);
         break;
      }
   }
   if (!InputRegisters[j]) {
      /* unknown input register label */
      RETURN_ERROR2("Invalid register name", token);
   }

   /* Match '[' */
   if (!Parse_String(parseState, "]"))
      RETURN_ERROR1("Expected ]");

   return GL_TRUE;
}
Пример #4
0
/**
 * Lookup a parameter value by name in the given parameter list.
 * \return pointer to the float[4] values.
 */
GLfloat *
_mesa_lookup_parameter_value(struct program_parameter_list *paramList,
                             GLsizei nameLen, const char *name)
{
   GLuint i;

   if (!paramList)
      return NULL;

   if (nameLen == -1) {
      /* name is null-terminated */
      for (i = 0; i < paramList->NumParameters; i++) {
         if (_mesa_strcmp(paramList->Parameters[i].Name, name) == 0)
            return paramList->Parameters[i].Values;
      }
   }
   else {
      /* name is not null-terminated, use nameLen */
      for (i = 0; i < paramList->NumParameters; i++) {
         if (_mesa_strncmp(paramList->Parameters[i].Name, name, nameLen) == 0
             && _mesa_strlen(paramList->Parameters[i].Name) == (size_t)nameLen)
            return paramList->Parameters[i].Values;
      }
   }
   return NULL;
}
Пример #5
0
/**
 * Lookup a parameter index by name in the given parameter list.
 * \return index of parameter in the list.
 */
GLint
_mesa_lookup_parameter_index(struct program_parameter_list *paramList,
                             GLsizei nameLen, const char *name)
{
   GLint i;

   if (!paramList)
      return -1;

   if (nameLen == -1) {
      /* name is null-terminated */
      for (i = 0; i < (GLint) paramList->NumParameters; i++) {
         if (_mesa_strcmp(paramList->Parameters[i].Name, name) == 0)
            return i;
      }
   }
   else {
      /* name is not null-terminated, use nameLen */
      for (i = 0; i < (GLint) paramList->NumParameters; i++) {
         if (_mesa_strncmp(paramList->Parameters[i].Name, name, nameLen) == 0
             && _mesa_strlen(paramList->Parameters[i].Name) == (size_t)nameLen)
            return i;
      }
   }
   return -1;
}
Пример #6
0
GLAPI OSMESAproc GLAPIENTRY
OSMesaGetProcAddress( const char *funcName )
{
   int i;
   for (i = 0; functions[i].Name; i++) {
      if (_mesa_strcmp(functions[i].Name, funcName) == 0)
         return functions[i].Function;
   }
   return _glapi_get_proc_address(funcName);
}
Пример #7
0
static pp_symbol *
pp_symbols_find (pp_symbols *self, const char *name)
{
   GLuint i;

   for (i = 0; i < self->count; i++)
      if (_mesa_strcmp (name, slang_string_cstr (&self->symbols[i].name)) == 0)
         return &self->symbols[i];
   return NULL;
}
Пример #8
0
/**
 * Called in response to #pragma.  For example, "#pragma debug(on)" would
 * call this function as pp_pragma("debug", "on").
 * \return GL_TRUE if pragma is valid, GL_FALSE if invalid
 */
static GLboolean
pp_pragma(struct gl_sl_pragmas *pragmas, const char *pragma, const char *param)
{
#if 0
   printf("#pragma %s %s\n", pragma, param);
#endif
   if (_mesa_strcmp(pragma, "optimize") == 0) {
      if (!param)
         return GL_FALSE; /* missing required param */
      if (_mesa_strcmp(param, "on") == 0) {
         pragmas->Optimize = GL_TRUE;
      }
      else if (_mesa_strcmp(param, "off") == 0) {
         pragmas->Optimize = GL_FALSE;
      }
      else {
         return GL_FALSE; /* invalid param */
      }
   }
   else if (_mesa_strcmp(pragma, "debug") == 0) {
      if (!param)
         return GL_FALSE; /* missing required param */
      if (_mesa_strcmp(param, "on") == 0) {
         pragmas->Debug = GL_TRUE;
      }
      else if (_mesa_strcmp(param, "off") == 0) {
         pragmas->Debug = GL_FALSE;
      }
      else {
         return GL_FALSE; /* invalid param */
      }
   }
   /* all other pragmas are silently ignored */
   return GL_TRUE;
}
/**
 * Test if the named extension is enabled in this context.
 */
GLboolean
_mesa_extension_is_enabled( GLcontext *ctx, const char *name )
{
   const GLboolean *base = (const GLboolean *) &ctx->Extensions;
   GLuint i;

   for (i = 0 ; i < Elements(default_extensions) ; i++) {
      if (_mesa_strcmp(default_extensions[i].name, name) == 0) {
         if (!default_extensions[i].flag_offset)
            return GL_TRUE;
         return *(base + default_extensions[i].flag_offset);
      }
   }
   return GL_FALSE;
}
Пример #10
0
/**
 * Mark the named uniform as 'used'.
 */
void
_mesa_use_uniform(struct gl_program_parameter_list *paramList,
                  const char *name)
{
   GLuint i;
   for (i = 0; i < paramList->NumParameters; i++) {
      struct gl_program_parameter *p = paramList->Parameters + i;
      if ((p->Type == PROGRAM_UNIFORM || p->Type == PROGRAM_SAMPLER) &&
          _mesa_strcmp(p->Name, name) == 0) {
         p->Used = GL_TRUE;
         /* Note that large uniforms may occupy several slots so we're
          * not done searching yet.
          */
      }
   }
}
Пример #11
0
/**
 * Parse v[#] or v[<name>]
 */
static GLboolean
Parse_AttribReg(struct parse_state *parseState, GLint *tempRegNum)
{
   GLubyte token[100];
   GLint j;

   /* Match 'v' */
   if (!Parse_String(parseState, "v"))
      RETURN_ERROR;

   /* Match '[' */
   if (!Parse_String(parseState, "["))
      RETURN_ERROR;

   /* match number or named register */
   if (!Parse_Token(parseState, token))
      RETURN_ERROR;

   if (parseState->isStateProgram && token[0] != '0')
      RETURN_ERROR1("Only v[0] accessible in vertex state programs");

   if (IsDigit(token[0])) {
      GLint reg = _mesa_atoi((char *) token);
      if (reg >= MAX_NV_VERTEX_PROGRAM_INPUTS)
         RETURN_ERROR1("Bad vertex attribute register name");
      *tempRegNum = reg;
   }
   else {
      for (j = 0; InputRegisters[j]; j++) {
         if (_mesa_strcmp((const char *) token, InputRegisters[j]) == 0) {
            *tempRegNum = j;
            break;
         }
      }
      if (!InputRegisters[j]) {
         /* unknown input register label */
         RETURN_ERROR2("Bad register name", token);
      }
   }

   /* Match '[' */
   if (!Parse_String(parseState, "]"))
      RETURN_ERROR;

   return GL_TRUE;
}
Пример #12
0
/**
 * Add a new named constant to the parameter list.
 * This will be used when the program contains something like this:
 *    PARAM myVals = { 0, 1, 2, 3 };
 *
 * \param paramList  the parameter list
 * \param name  the name for the constant
 * \param values  four float values
 * \return index/position of the new parameter in the parameter list
 */
GLint
_mesa_add_named_constant(struct gl_program_parameter_list *paramList,
                         const char *name, const GLfloat values[4],
                         GLuint size)
{
   /* first check if this is a duplicate constant */
   GLint pos;
   for (pos = 0; pos < paramList->NumParameters; pos++) {
      const GLfloat *pvals = paramList->ParameterValues[pos];
      if (pvals[0] == values[0] &&
          pvals[1] == values[1] &&
          pvals[2] == values[2] &&
          pvals[3] == values[3] &&
          _mesa_strcmp(paramList->Parameters[pos].Name, name) == 0) {
         /* Same name and value is already in the param list - reuse it */
         return pos;
      }
   }
   /* not found, add new parameter */
   return _mesa_add_parameter(paramList, PROGRAM_CONSTANT, name,
                              size, GL_NONE, values, NULL, 0x0);
}
Пример #13
0
static GLboolean
Parse_OutputReg(struct parse_state *parseState, GLint *outputRegNum)
{
   GLubyte token[100];
   GLint start, j;

   /* Match 'o' */
   if (!Parse_String(parseState, "o"))
      RETURN_ERROR;

   /* Match '[' */
   if (!Parse_String(parseState, "["))
      RETURN_ERROR;

   /* Get output reg name */
   if (!Parse_Token(parseState, token))
      RETURN_ERROR;

   if (parseState->isPositionInvariant)
      start = 1; /* skip HPOS register name */
   else
      start = 0;

   /* try to match an output register name */
   for (j = start; OutputRegisters[j]; j++) {
      if (_mesa_strcmp((const char *) token, OutputRegisters[j]) == 0) {
         *outputRegNum = j;
         break;
      }
   }
   if (!OutputRegisters[j])
      RETURN_ERROR1("Unrecognized output register name");

   /* Match ']' */
   if (!Parse_String(parseState, "]"))
      RETURN_ERROR1("Expected ]");

   return GL_TRUE;
}
Пример #14
0
void
slang_print_function(const slang_function *f, GLboolean body)
{
   GLuint i;

#if 0
   if (_mesa_strcmp((char *) f->header.a_name, "main") != 0)
     return;
#endif

   printf("FUNCTION %s ( scope=%p\n",
          (char *) f->header.a_name, (void *) f->parameters);

   for (i = 0; i < f->param_count; i++) {
      print_variable(f->parameters->variables[i], 3);
   }

   printf(") param scope = %p\n", (void *) f->parameters);

   if (body && f->body)
      slang_print_tree(f->body, 0);
}
/**
 * Either enable or disable the named extension.
 */
static void
set_extension( GLcontext *ctx, const char *name, GLboolean state )
{
   GLboolean *base = (GLboolean *) &ctx->Extensions;
   GLuint i;

   if (ctx->Extensions.String) {
      /* The string was already queried - can't change it now! */
      _mesa_problem(ctx, "Trying to enable/disable extension after glGetString(GL_EXTENSIONS): %s", name);
      return;
   }

   for (i = 0 ; i < Elements(default_extensions) ; i++) {
      if (_mesa_strcmp(default_extensions[i].name, name) == 0) {
         if (default_extensions[i].flag_offset) {
            GLboolean *enabled = base + default_extensions[i].flag_offset;
            *enabled = state;
         }
         return;
      }
   }
   _mesa_problem(ctx, "Trying to enable unknown extension: %s", name);
}
Пример #16
0
void
_mesa_GetProgramRegisterfvMESA(GLenum target,
                               GLsizei len, const GLubyte *registerName,
                               GLfloat *v)
{
   char reg[1000];
   GET_CURRENT_CONTEXT(ctx);

   /* We _should_ be inside glBegin/glEnd */
#if 0
   if (ctx->Driver.CurrentExecPrimitive == PRIM_OUTSIDE_BEGIN_END) {
      _mesa_error(ctx, GL_INVALID_OPERATION, "glGetProgramRegisterfvMESA");
      return;
   }
#endif

   /* make null-terminated copy of registerName */
   len = MIN2((unsigned int) len, sizeof(reg) - 1);
   _mesa_memcpy(reg, registerName, len);
   reg[len] = 0;

   switch (target) {
      case GL_VERTEX_PROGRAM_NV:
         if (!ctx->Extensions.ARB_vertex_program &&
             !ctx->Extensions.NV_vertex_program) {
            _mesa_error(ctx, GL_INVALID_ENUM,
                        "glGetProgramRegisterfvMESA(target)");
            return;
         }
         if (!ctx->VertexProgram.Enabled) {
            _mesa_error(ctx, GL_INVALID_OPERATION,
                        "glGetProgramRegisterfvMESA");
            return;
         }
         /* GL_NV_vertex_program */
         if (reg[0] == 'R') {
            /* Temp register */
            GLint i = _mesa_atoi(reg + 1);
            if (i >= (GLint)ctx->Const.MaxVertexProgramTemps) {
               _mesa_error(ctx, GL_INVALID_VALUE,
                           "glGetProgramRegisterfvMESA(registerName)");
               return;
            }
            COPY_4V(v, ctx->VertexProgram.Temporaries[i]);
         }
         else if (reg[0] == 'v' && reg[1] == '[') {
            /* Vertex Input attribute */
            GLuint i;
            for (i = 0; i < ctx->Const.MaxVertexProgramAttribs; i++) {
               const char *name = _mesa_nv_vertex_input_register_name(i);
               char number[10];
               sprintf(number, "%d", i);
               if (_mesa_strncmp(reg + 2, name, 4) == 0 ||
                   _mesa_strncmp(reg + 2, number, _mesa_strlen(number)) == 0) {
                  COPY_4V(v, ctx->VertexProgram.Inputs[i]);
                  return;
               }
            }
            _mesa_error(ctx, GL_INVALID_VALUE,
                        "glGetProgramRegisterfvMESA(registerName)");
            return;
         }
         else if (reg[0] == 'o' && reg[1] == '[') {
            /* Vertex output attribute */
         }
         /* GL_ARB_vertex_program */
         else if (_mesa_strncmp(reg, "vertex.", 7) == 0) {

         }
         else {
            _mesa_error(ctx, GL_INVALID_VALUE,
                        "glGetProgramRegisterfvMESA(registerName)");
            return;
         }
         break;
      case GL_FRAGMENT_PROGRAM_ARB:
         if (!ctx->Extensions.ARB_fragment_program) {
            _mesa_error(ctx, GL_INVALID_ENUM,
                        "glGetProgramRegisterfvMESA(target)");
            return;
         }
         if (!ctx->FragmentProgram.Enabled) {
            _mesa_error(ctx, GL_INVALID_OPERATION,
                        "glGetProgramRegisterfvMESA");
            return;
         }
         /* XXX to do */
         break;
      case GL_FRAGMENT_PROGRAM_NV:
         if (!ctx->Extensions.NV_fragment_program) {
            _mesa_error(ctx, GL_INVALID_ENUM,
                        "glGetProgramRegisterfvMESA(target)");
            return;
         }
         if (!ctx->FragmentProgram.Enabled) {
            _mesa_error(ctx, GL_INVALID_OPERATION,
                        "glGetProgramRegisterfvMESA");
            return;
         }
         if (reg[0] == 'R') {
            /* Temp register */
            GLint i = _mesa_atoi(reg + 1);
            if (i >= (GLint)ctx->Const.MaxFragmentProgramTemps) {
               _mesa_error(ctx, GL_INVALID_VALUE,
                           "glGetProgramRegisterfvMESA(registerName)");
               return;
            }
            COPY_4V(v, ctx->FragmentProgram.Machine.Temporaries[i]);
         }
         else if (reg[0] == 'f' && reg[1] == '[') {
            /* Fragment input attribute */
            GLuint i;
            for (i = 0; i < ctx->Const.MaxFragmentProgramAttribs; i++) {
               const char *name = _mesa_nv_fragment_input_register_name(i);
               if (_mesa_strncmp(reg + 2, name, 4) == 0) {
                  COPY_4V(v, ctx->FragmentProgram.Machine.Inputs[i]);
                  return;
               }
            }
            _mesa_error(ctx, GL_INVALID_VALUE,
                        "glGetProgramRegisterfvMESA(registerName)");
            return;
         }
         else if (_mesa_strcmp(reg, "o[COLR]") == 0) {
            /* Fragment output color */
            COPY_4V(v, ctx->FragmentProgram.Machine.Outputs[FRAG_OUTPUT_COLR]);
         }
         else if (_mesa_strcmp(reg, "o[COLH]") == 0) {
            /* Fragment output color */
            COPY_4V(v, ctx->FragmentProgram.Machine.Outputs[FRAG_OUTPUT_COLH]);
         }
         else if (_mesa_strcmp(reg, "o[DEPR]") == 0) {
            /* Fragment output depth */
            COPY_4V(v, ctx->FragmentProgram.Machine.Outputs[FRAG_OUTPUT_DEPR]);
         }
         else {
            /* try user-defined identifiers */
            const GLfloat *value = _mesa_lookup_parameter_value(
                       ctx->FragmentProgram.Current->Parameters, -1, reg);
            if (value) {
               COPY_4V(v, value);
            }
            else {
               _mesa_error(ctx, GL_INVALID_VALUE,
                           "glGetProgramRegisterfvMESA(registerName)");
               return;
            }
         }
         break;
      default:
         _mesa_error(ctx, GL_INVALID_ENUM,
                     "glGetProgramRegisterfvMESA(target)");
         return;
   }

}
Пример #17
0
static GLboolean
Parse_ParamReg(struct parse_state *parseState, struct vp_src_register *srcReg)
{
   GLubyte token[100];

   if (!Parse_String(parseState, "c"))
      RETURN_ERROR;

   if (!Parse_String(parseState, "["))
      RETURN_ERROR;

   if (!Peek_Token(parseState, token))
      RETURN_ERROR;

   if (IsDigit(token[0])) {
      /* a numbered program parameter register */
      GLint reg;
      (void) Parse_Token(parseState, token);
      reg = _mesa_atoi((char *) token);
      if (reg >= MAX_NV_VERTEX_PROGRAM_PARAMS)
         RETURN_ERROR1("Bad program parameter number");
      srcReg->File = PROGRAM_ENV_PARAM;
      srcReg->Index = reg;
   }
   else if (_mesa_strcmp((const char *) token, "A0") == 0) {
      /* address register "A0.x" */
      if (!Parse_AddrReg(parseState))
         RETURN_ERROR;

      srcReg->RelAddr = GL_TRUE;
      srcReg->File = PROGRAM_ENV_PARAM;
      /* Look for +/-N offset */
      if (!Peek_Token(parseState, token))
         RETURN_ERROR;

      if (token[0] == '-' || token[0] == '+') {
         const GLubyte sign = token[0];
         (void) Parse_Token(parseState, token); /* consume +/- */

         /* an integer should be next */
         if (!Parse_Token(parseState, token))
            RETURN_ERROR;

         if (IsDigit(token[0])) {
            const GLint k = _mesa_atoi((char *) token);
            if (sign == '-') {
               if (k > 64)
                  RETURN_ERROR1("Bad address offset");
               srcReg->Index = -k;
            }
            else {
               if (k > 63)
                  RETURN_ERROR1("Bad address offset");
               srcReg->Index = k;
            }
         }
         else {
            RETURN_ERROR;
         }
      }
      else {
         /* probably got a ']', catch it below */
      }
   }
   else {
      RETURN_ERROR;
   }

   /* Match closing ']' */
   if (!Parse_String(parseState, "]"))
      RETURN_ERROR;

   return GL_TRUE;
}
Пример #18
0
static GLboolean
preprocess_source (slang_string *output, const char *source,
                   grammar pid, grammar eid,
                   slang_info_log *elog,
                   const struct gl_extensions *extensions,
                   struct gl_sl_pragmas *pragmas)
{
   static const char *predefined[] = {
      "__FILE__",
      "__LINE__",
      "__VERSION__",
#if FEATURE_es2_glsl
      "GL_ES",
      "GL_FRAGMENT_PRECISION_HIGH",
#endif
      NULL
   };
   byte *prod;
   GLuint size, i;
   pp_state state;

   if (!grammar_fast_check (pid, (const byte *) (source), &prod, &size, 65536)) {
      grammar_error_to_log (elog);
      return GL_FALSE;
   }

   pp_state_init (&state, elog, extensions);
   pp_pragmas_init (pragmas);

   /* add the predefined symbols to the symbol table */
   for (i = 0; predefined[i]; i++) {
      pp_symbol *symbol = NULL;
      symbol = pp_symbols_push(&state.symbols);
      assert(symbol);
      slang_string_pushs(&symbol->name,
                         predefined[i], _mesa_strlen(predefined[i]));
   }

   i = 0;
   while (i < size) {
      if (prod[i] != ESCAPE_TOKEN) {
         if (state.cond.top->effective) {
            slang_string input;
            expand_state es;

            /* Eat only one line of source code to expand it.
             * FIXME: This approach has one drawback. If a macro with parameters spans across
             *        multiple lines, the preprocessor will raise an error. */
            slang_string_init (&input);
            while (prod[i] != '\0' && prod[i] != '\n')
               slang_string_pushc (&input, prod[i++]);
            if (prod[i] != '\0')
               slang_string_pushc (&input, prod[i++]);

            /* Increment line number. */
            state.line++;

            es.output = output;
            es.input = slang_string_cstr (&input);
            es.state = &state;
            if (!expand (&es, &state.symbols))
               goto error;

            slang_string_free (&input);
         }
         else {
            /* Condition stack is disabled - keep track on line numbers and output only newlines. */
            if (prod[i] == '\n') {
               state.line++;
               /*pp_annotate (output, "%c", prod[i]);*/
            }
            else {
               /*pp_annotate (output, "%c", prod[i]);*/
            }
            i++;
         }
      }
      else {
         const char *id;
         GLuint idlen;
         GLubyte token;

         i++;
         token = prod[i++];
         switch (token) {

         case TOKEN_END:
            /* End of source string.
               * Check if all #ifs have been terminated by matching #endifs.
               * On condition stack there should be only the global condition context. */
            if (state.cond.top->endif_required) {
               slang_info_log_error (elog, "end of source without matching #endif.");
               return GL_FALSE;
            }
            break;

         case TOKEN_DEFINE:
            {
               pp_symbol *symbol = NULL;

               /* Parse macro name. */
               id = (const char *) (&prod[i]);
               idlen = _mesa_strlen (id);
               if (state.cond.top->effective) {
                  pp_annotate (output, "// #define %s(", id);

                  /* If the symbol is already defined, override it. */
                  symbol = pp_symbols_find (&state.symbols, id);
                  if (symbol == NULL) {
                     symbol = pp_symbols_push (&state.symbols);
                     if (symbol == NULL)
                        goto error;
                     slang_string_pushs (&symbol->name, id, idlen);
                  }
                  else {
                     pp_symbol_reset (symbol);
                  }
               }
               i += idlen + 1;

               /* Parse optional macro parameters. */
               while (prod[i++] != PARAM_END) {
                  pp_symbol *param;

                  id = (const char *) (&prod[i]);
                  idlen = _mesa_strlen (id);
                  if (state.cond.top->effective) {
                     pp_annotate (output, "%s, ", id);
                     param = pp_symbols_push (&symbol->parameters);
                     if (param == NULL)
                        goto error;
                     slang_string_pushs (&param->name, id, idlen);
                  }
                  i += idlen + 1;
               }

               /* Parse macro replacement. */
               id = (const char *) (&prod[i]);
               idlen = _mesa_strlen (id);
               if (state.cond.top->effective) {
                  slang_string replacement;
                  expand_state es;

                  pp_annotate (output, ") %s", id);

                  slang_string_init(&replacement);
                  slang_string_pushs(&replacement, id, idlen);

                  /* Expand macro replacement. */
                  es.output = &symbol->replacement;
                  es.input = slang_string_cstr(&replacement);
                  es.state = &state;
                  if (!expand(&es, &state.symbols)) {
                     slang_string_free(&replacement);
                     goto error;
                  }
                  slang_string_free(&replacement);
               }
               i += idlen + 1;
            }
            break;

         case TOKEN_UNDEF:
            id = (const char *) (&prod[i]);
            i += _mesa_strlen (id) + 1;
            if (state.cond.top->effective) {
               pp_symbol *symbol;

               pp_annotate (output, "// #undef %s", id);
               /* Try to find symbol with given name and remove it. */
               symbol = pp_symbols_find (&state.symbols, id);
               if (symbol != NULL)
                  if (!pp_symbols_erase (&state.symbols, symbol))
                     goto error;
            }
            break;

         case TOKEN_IF:
            {
               GLint result;

               /* Parse #if expression end execute it. */
               pp_annotate (output, "// #if ");
               if (!parse_if (output, prod, &i, &result, &state, eid))
                  goto error;

               /* Push new condition on the stack. */
               if (!pp_cond_stack_push (&state.cond, state.elog))
                  goto error;
               state.cond.top->current = result ? GL_TRUE : GL_FALSE;
               state.cond.top->else_allowed = GL_TRUE;
               state.cond.top->endif_required = GL_TRUE;
               pp_cond_stack_reevaluate (&state.cond);
            }
            break;

         case TOKEN_ELSE:
            /* Check if #else is alloved here. */
            if (!state.cond.top->else_allowed) {
               slang_info_log_error (elog, "#else without matching #if.");
               goto error;
            }

            /* Negate current condition and reevaluate it. */
            state.cond.top->current = !state.cond.top->current;
            state.cond.top->else_allowed = GL_FALSE;
            pp_cond_stack_reevaluate (&state.cond);
            if (state.cond.top->effective)
               pp_annotate (output, "// #else");
            break;

         case TOKEN_ELIF:
            /* Check if #elif is alloved here. */
            if (!state.cond.top->else_allowed) {
               slang_info_log_error (elog, "#elif without matching #if.");
               goto error;
            }

            /* Negate current condition and reevaluate it. */
            state.cond.top->current = !state.cond.top->current;
            pp_cond_stack_reevaluate (&state.cond);

            if (state.cond.top->effective)
               pp_annotate (output, "// #elif ");

            {
               GLint result;

               /* Parse #elif expression end execute it. */
               if (!parse_if (output, prod, &i, &result, &state, eid))
                  goto error;

               /* Update current condition and reevaluate it. */
               state.cond.top->current = result ? GL_TRUE : GL_FALSE;
               pp_cond_stack_reevaluate (&state.cond);
            }
            break;

         case TOKEN_ENDIF:
            /* Check if #endif is alloved here. */
            if (!state.cond.top->endif_required) {
               slang_info_log_error (elog, "#endif without matching #if.");
               goto error;
            }

            /* Pop the condition off the stack. */
            state.cond.top++;
            if (state.cond.top->effective)
               pp_annotate (output, "// #endif");
            break;

         case TOKEN_EXTENSION:
            /* Parse the extension name. */
            id = (const char *) (&prod[i]);
            i += _mesa_strlen (id) + 1;
            if (state.cond.top->effective)
               pp_annotate (output, "// #extension %s: ", id);

            /* Parse and apply extension behavior. */
            if (state.cond.top->effective) {
               switch (prod[i++]) {

               case BEHAVIOR_REQUIRE:
                  pp_annotate (output, "require");
                  if (!pp_ext_set (&state.ext, id, GL_TRUE)) {
                     if (_mesa_strcmp (id, "all") == 0) {
                        slang_info_log_error (elog, "require: bad behavior for #extension all.");
                        goto error;
                     }
                     else {
                        slang_info_log_error (elog, "%s: required extension is not supported.", id);
                        goto error;
                     }
                  }
                  break;

               case BEHAVIOR_ENABLE:
                  pp_annotate (output, "enable");
                  if (!pp_ext_set (&state.ext, id, GL_TRUE)) {
                     if (_mesa_strcmp (id, "all") == 0) {
                        slang_info_log_error (elog, "enable: bad behavior for #extension all.");
                        goto error;
                     }
                     else {
                        slang_info_log_warning (elog, "%s: enabled extension is not supported.", id);
                     }
                  }
                  break;

               case BEHAVIOR_WARN:
                  pp_annotate (output, "warn");
                  if (!pp_ext_set (&state.ext, id, GL_TRUE)) {
                     if (_mesa_strcmp (id, "all") != 0) {
                        slang_info_log_warning (elog, "%s: enabled extension is not supported.", id);
                     }
                  }
                  break;

               case BEHAVIOR_DISABLE:
                  pp_annotate (output, "disable");
                  if (!pp_ext_set (&state.ext, id, GL_FALSE)) {
                     if (_mesa_strcmp (id, "all") == 0) {
                        pp_ext_disable_all (&state.ext);
                     }
                     else {
                        slang_info_log_warning (elog, "%s: disabled extension is not supported.", id);
                     }
                  }
                  break;

               default:
                  assert (0);
               }
            }
            break;

         case TOKEN_PRAGMA:
            {
               GLint have_param;
               const char *pragma, *param;

               pragma = (const char *) (&prod[i]);
               i += _mesa_strlen(pragma) + 1;
               have_param = (prod[i++] == PRAGMA_PARAM);
               if (have_param) {
                  param = (const char *) (&prod[i]);
                  i += _mesa_strlen(param) + 1;
               }
               else {
                  param = NULL;
               }
               pp_pragma(pragmas, pragma, param);
            }
            break;

         case TOKEN_LINE:
            id = (const char *) (&prod[i]);
            i += _mesa_strlen (id) + 1;

            if (state.cond.top->effective) {
               slang_string buffer;
               GLuint count;
               GLint results[2];
               expand_state es;

               slang_string_init (&buffer);
               state.line++;
               es.output = &buffer;
               es.input = id;
               es.state = &state;
               if (!expand (&es, &state.symbols))
                  goto error;

               pp_annotate (output, "// #line ");
               count = execute_expressions (output, eid,
                                             (const byte *) (slang_string_cstr (&buffer)),
                                             results, state.elog);
               slang_string_free (&buffer);
               if (count == 0)
                  goto error;

               state.line = results[0] - 1;
               if (count == 2)
                  state.file = results[1];
            }
            break;
         }
      }
   }

   /* Check for missing #endifs. */
   if (state.cond.top->endif_required) {
      slang_info_log_error (elog, "#endif expected but end of source found.");
      goto error;
   }

   grammar_alloc_free(prod);
   pp_state_free (&state);
   return GL_TRUE;

error:
   grammar_alloc_free(prod);
   pp_state_free (&state);
   return GL_FALSE;
}
Пример #19
0
int slang_string_compare (const char *str1, const char *str2)
{
	return _mesa_strcmp (str1, str2);
}
Пример #20
0
static GLboolean
Parse_MaskedDstReg(struct parse_state *parseState,
                   struct prog_dst_register *dstReg)
{
   GLubyte token[100];
   GLint idx;

   /* Dst reg can be R<n>, H<n>, o[n], RC or HC */
   if (!Peek_Token(parseState, token))
      RETURN_ERROR;

   if (_mesa_strcmp((const char *) token, "RC") == 0 ||
       _mesa_strcmp((const char *) token, "HC") == 0) {
      /* a write-only register */
      dstReg->File = PROGRAM_WRITE_ONLY;
      if (!Parse_DummyReg(parseState, &idx))
         RETURN_ERROR;
      dstReg->Index = idx;
   }
   else if (token[0] == 'R' || token[0] == 'H') {
      /* a temporary register */
      dstReg->File = PROGRAM_TEMPORARY;
      if (!Parse_TempReg(parseState, &idx))
         RETURN_ERROR;
      dstReg->Index = idx;
   }
   else if (token[0] == 'o') {
      /* an output register */
      dstReg->File = PROGRAM_OUTPUT;
      if (!Parse_OutputReg(parseState, &idx))
         RETURN_ERROR;
      dstReg->Index = idx;
   }
   else {
      RETURN_ERROR1("Invalid destination register name");
   }

   /* Parse optional write mask */
   if (Parse_String(parseState, ".")) {
      /* got a mask */
      GLint k = 0;

      if (!Parse_Token(parseState, token))  /* get xyzw writemask */
         RETURN_ERROR;

      dstReg->WriteMask = 0;

      if (token[k] == 'x') {
         dstReg->WriteMask |= WRITEMASK_X;
         k++;
      }
      if (token[k] == 'y') {
         dstReg->WriteMask |= WRITEMASK_Y;
         k++;
      }
      if (token[k] == 'z') {
         dstReg->WriteMask |= WRITEMASK_Z;
         k++;
      }
      if (token[k] == 'w') {
         dstReg->WriteMask |= WRITEMASK_W;
         k++;
      }
      if (k == 0) {
         RETURN_ERROR1("Invalid writemask character");
      }

   }
   else {
      dstReg->WriteMask = WRITEMASK_XYZW;
   }

   /* optional condition code mask */
   if (Parse_String(parseState, "(")) {
      /* ("EQ" | "GE" | "GT" | "LE" | "LT" | "NE" | "TR" | "FL".x|y|z|w) */
      /* ("EQ" | "GE" | "GT" | "LE" | "LT" | "NE" | "TR" | "FL".[xyzw]) */
      if (!Parse_CondCodeMask(parseState, dstReg))
         RETURN_ERROR;

      if (!Parse_String(parseState, ")"))  /* consume ")" */
         RETURN_ERROR1("Expected )");

      return GL_TRUE;
   }
   else {
      /* no cond code mask */
      dstReg->CondMask = COND_TR;
      dstReg->CondSwizzle = SWIZZLE_NOOP;
      return GL_TRUE;
   }
}
Пример #21
0
static GLboolean
expand (expand_state *e, pp_symbols *symbols)
{
   while (!IS_NULL(*e->input)) {
      if (IS_FIRST_ID_CHAR(*e->input)) {
         slang_string buffer;
         const char *id;

         /* Parse the identifier. */
         slang_string_init (&buffer);
         slang_string_pushc (&buffer, *e->input++);
         while (IS_NEXT_ID_CHAR(*e->input))
            slang_string_pushc (&buffer, *e->input++);
         id = slang_string_cstr (&buffer);

         /* Now check if the identifier is special in some way. The "defined" identifier is
          * actually an operator that we must handle here and expand it either to " 0 " or " 1 ".
          * The other identifiers start with "__" and we expand it to appropriate values
          * taken from the preprocessor state. */
         if (_mesa_strcmp (id, "defined") == 0) {
            if (!expand_defined (e, &buffer))
               return GL_FALSE;
         }
         else if (_mesa_strcmp (id, "__LINE__") == 0) {
            slang_string_pushc (e->output, ' ');
            slang_string_pushi (e->output, e->state->line);
            slang_string_pushc (e->output, ' ');
         }
         else if (_mesa_strcmp (id, "__FILE__") == 0) {
            slang_string_pushc (e->output, ' ');
            slang_string_pushi (e->output, e->state->file);
            slang_string_pushc (e->output, ' ');
         }
         else if (_mesa_strcmp (id, "__VERSION__") == 0) {
            slang_string_pushc (e->output, ' ');
            slang_string_pushi (e->output, e->state->version);
            slang_string_pushc (e->output, ' ');
         }
#if FEATURE_es2_glsl
         else if (_mesa_strcmp (id, "GL_ES") == 0 ||
                  _mesa_strcmp (id, "GL_FRAGMENT_PRECISION_HIGH") == 0) {
            slang_string_pushc (e->output, ' ');
            slang_string_pushi (e->output, '1');
            slang_string_pushc (e->output, ' ');
         }
#endif
         else {
            pp_symbol *symbol;

            /* The list of symbols from <symbols> take precedence over the list from <state>.
             * Note that in some cases this is the same list so avoid double look-up. */
            symbol = pp_symbols_find (symbols, id);
            if (symbol == NULL && symbols != &e->state->symbols)
               symbol = pp_symbols_find (&e->state->symbols, id);

            /* If the symbol was found, recursively expand its definition. */
            if (symbol != NULL) {
               if (!expand_symbol (e, symbol)) {
                  slang_string_free (&buffer);
                  return GL_FALSE;
               }
            }
            else {
               slang_string_push (e->output, &buffer);
            }
         }
         slang_string_free (&buffer);
      }
      else if (IS_WHITE(*e->input)) {
         slang_string_pushc (e->output, *e->input++);
      }
      else {
         while (!IS_WHITE(*e->input) && !IS_NULL(*e->input) && !IS_FIRST_ID_CHAR(*e->input))
            slang_string_pushc (e->output, *e->input++);
      }
   }
   return GL_TRUE;
}
Пример #22
0
Файл: enums.c Проект: aosm/X11
static int compar_name( const enum_elt *a, const enum_elt *b )
{
   return _mesa_strcmp(a->c, b->c);
}