panfrost/midgard: Use unsigned blend patch offset
[mesa.git] / src / gallium / auxiliary / tgsi / tgsi_text.c
index 1b4f59404609ec2dd36913b8b5145e80518927bf..9779f212cb13cf693e6e74485de18c10539cec43 100644 (file)
@@ -208,14 +208,17 @@ static boolean parse_int( const char **pcur, int *val )
    return FALSE;
 }
 
-static boolean parse_identifier( const char **pcur, char *ret )
+static boolean parse_identifier( const char **pcur, char *ret, size_t len )
 {
    const char *cur = *pcur;
-   int i = 0;
+   size_t i = 0;
    if (is_alpha_underscore( cur )) {
       ret[i++] = *cur++;
-      while (is_alpha_underscore( cur ) || is_digit( cur ))
+      while (is_alpha_underscore( cur ) || is_digit( cur )) {
+         if (i == len - 1)
+            return FALSE;
          ret[i++] = *cur++;
+      }
       ret[i++] = '\0';
       *pcur = cur;
       return TRUE;
@@ -863,7 +866,7 @@ parse_optional_swizzle(
 
    eat_opt_white( &cur );
    if (*cur == '.') {
-      uint i;
+      int i;
 
       cur++;
       eat_opt_white( &cur );
@@ -996,24 +999,34 @@ parse_texoffset_operand(
 static boolean
 match_inst(const char **pcur,
            unsigned *saturate,
+           unsigned *precise,
            const struct tgsi_opcode_info *info)
 {
    const char *cur = *pcur;
+   const char *mnemonic = tgsi_get_opcode_name(info->opcode);
 
    /* simple case: the whole string matches the instruction name */
-   if (str_match_nocase_whole(&cur, info->mnemonic)) {
+   if (str_match_nocase_whole(&cur, mnemonic)) {
       *pcur = cur;
       *saturate = 0;
+      *precise = 0;
       return TRUE;
    }
 
-   if (str_match_no_case(&cur, info->mnemonic)) {
+   if (str_match_no_case(&cur, mnemonic)) {
       /* the instruction has a suffix, figure it out */
-      if (str_match_nocase_whole(&cur, "_SAT")) {
+      if (str_match_no_case(&cur, "_SAT")) {
          *pcur = cur;
          *saturate = 1;
-         return TRUE;
       }
+
+      if (str_match_no_case(&cur, "_PRECISE")) {
+         *pcur = cur;
+         *precise = 1;
+      }
+
+      if (!is_digit_alpha_underscore(cur))
+         return TRUE;
    }
 
    return FALSE;
@@ -1024,8 +1037,9 @@ parse_instruction(
    struct translate_ctx *ctx,
    boolean has_label )
 {
-   uint i;
+   int i;
    uint saturate = 0;
+   uint precise = 0;
    const struct tgsi_opcode_info *info;
    struct tgsi_full_instruction inst;
    const char *cur;
@@ -1033,43 +1047,6 @@ parse_instruction(
 
    inst = tgsi_default_full_instruction();
 
-   /* Parse predicate.
-    */
-   eat_opt_white( &ctx->cur );
-   if (*ctx->cur == '(') {
-      uint file;
-      int index;
-      uint swizzle[4];
-      boolean parsed_swizzle;
-
-      inst.Instruction.Predicate = 1;
-
-      ctx->cur++;
-      if (*ctx->cur == '!') {
-         ctx->cur++;
-         inst.Predicate.Negate = 1;
-      }
-
-      if (!parse_register_1d( ctx, &file, &index ))
-         return FALSE;
-
-      if (parse_optional_swizzle( ctx, swizzle, &parsed_swizzle, 4 )) {
-         if (parsed_swizzle) {
-            inst.Predicate.SwizzleX = swizzle[0];
-            inst.Predicate.SwizzleY = swizzle[1];
-            inst.Predicate.SwizzleZ = swizzle[2];
-            inst.Predicate.SwizzleW = swizzle[3];
-         }
-      }
-
-      if (*ctx->cur != ')') {
-         report_error( ctx, "Expected `)'" );
-         return FALSE;
-      }
-
-      ctx->cur++;
-   }
-
    /* Parse instruction name.
     */
    eat_opt_white( &ctx->cur );
@@ -1077,7 +1054,7 @@ parse_instruction(
       cur = ctx->cur;
 
       info = tgsi_get_opcode_info( i );
-      if (match_inst(&cur, &saturate, info)) {
+      if (match_inst(&cur, &saturate, &precise, info)) {
          if (info->num_dst + info->num_src + info->is_tex == 0) {
             ctx->cur = cur;
             break;
@@ -1098,6 +1075,7 @@ parse_instruction(
 
    inst.Instruction.Opcode = i;
    inst.Instruction.Saturate = saturate;
+   inst.Instruction.Precise = precise;
    inst.Instruction.NumDstRegs = info->num_dst;
    inst.Instruction.NumSrcRegs = info->num_src;
 
@@ -1160,7 +1138,7 @@ parse_instruction(
 
    cur = ctx->cur;
    eat_opt_white( &cur );
-   for (i = 0; inst.Instruction.Texture && *cur == ','; i++) {
+   for (i = 0; inst.Instruction.Texture && *cur == ',' && i < TGSI_FULL_MAX_TEX_OFFSETS; i++) {
          cur++;
          eat_opt_white( &cur );
          ctx->cur = cur;
@@ -1608,10 +1586,6 @@ static boolean parse_declaration( struct translate_ctx *ctx )
             break;
          }
       }
-      if (i == TGSI_INTERPOLATE_COUNT) {
-         report_error( ctx, "Expected semantic or interpolate attribute" );
-         return FALSE;
-      }
    }
 
    cur = ctx->cur;
@@ -1631,6 +1605,20 @@ static boolean parse_declaration( struct translate_ctx *ctx )
       }
    }
 
+   cur = ctx->cur;
+   eat_opt_white( &cur );
+   if (*cur == ',' && !is_vs_input) {
+      cur++;
+      eat_opt_white( &cur );
+      if (str_match_nocase_whole( &cur, tgsi_invariant_name )) {
+         decl.Declaration.Invariant = 1;
+         ctx->cur = cur;
+      } else {
+         report_error( ctx, "Expected semantic, interpolate attribute, or invariant ");
+         return FALSE;
+      }
+   }
+
    advance = tgsi_build_full_declaration(
       &decl,
       ctx->tokens_cur,
@@ -1648,7 +1636,7 @@ static boolean parse_immediate( struct translate_ctx *ctx )
 {
    struct tgsi_full_immediate imm;
    uint advance;
-   int type;
+   uint type;
 
    if (*ctx->cur == '[') {
       uint uindex;
@@ -1787,7 +1775,7 @@ static boolean parse_property( struct translate_ctx *ctx )
       report_error( ctx, "Syntax error" );
       return FALSE;
    }
-   if (!parse_identifier( &ctx->cur, id )) {
+   if (!parse_identifier( &ctx->cur, id, sizeof(id) )) {
       report_error( ctx, "Syntax error" );
       return FALSE;
    }