[Mesa-dev] [PATCH 15/21] nir: Add a function for comparing cursors

Connor Abbott cwabbott0 at gmail.com
Thu Feb 25 06:45:59 UTC 2016


On Sat, Feb 13, 2016 at 9:14 PM, Jason Ekstrand <jason at jlekstrand.net> wrote:
> ---
>  src/compiler/nir/nir.c | 63 ++++++++++++++++++++++++++++++++++++++++++++++++++
>  src/compiler/nir/nir.h |  2 ++
>  2 files changed, 65 insertions(+)
>
> diff --git a/src/compiler/nir/nir.c b/src/compiler/nir/nir.c
> index cd78475..468065a 100644
> --- a/src/compiler/nir/nir.c
> +++ b/src/compiler/nir/nir.c
> @@ -716,6 +716,69 @@ nir_cf_node_get_function(nir_cf_node *node)
>     return nir_cf_node_as_function(node);
>  }
>
> +/* Reduces a cursor by trying to convert everything to after and trying to
> + * go up to block granularity when possible.
> + */
> +static nir_cursor
> +reduce_cursor(nir_cursor cursor)
> +{
> +   switch (cursor.option) {
> +   case nir_cursor_before_block:
> +      if (exec_list_is_empty(&cursor.block->instr_list)) {
> +         /* Empty block.  After is as good as before. */
> +         cursor.option = nir_cursor_after_block;
> +      } else {
> +         /* Try to switch to after the previous block if there is one.
> +          * (This isn't likely, but it can happen.)
> +          */
> +         nir_cf_node *prev_node = nir_cf_node_prev(&cursor.block->cf_node);
> +         if (prev_node && prev_node->type == nir_cf_node_block) {

How can the current node and the previous node both be blocks? It's an
invariant of the control-flow modification code that no two blocks
ever wind up next to each other.

> +            cursor.block = nir_cf_node_as_block(prev_node);
> +            cursor.option = nir_cursor_after_block;
> +         }
> +      }
> +      return cursor;
> +
> +   case nir_cursor_after_block:
> +      return cursor;
> +
> +   case nir_cursor_before_instr: {
> +      nir_instr *prev_instr = nir_instr_prev(cursor.instr);
> +      if (prev_instr) {
> +         /* Before this instruction is after the previous */
> +         cursor.instr = prev_instr;
> +         cursor.option = nir_cursor_after_instr;
> +      } else {
> +         /* No previous instruction.  Switch to before block */
> +         cursor.block = cursor.instr->block;
> +         cursor.option = nir_cursor_before_block;
> +      }
> +      return reduce_cursor(cursor);
> +   }
> +
> +   case nir_cursor_after_instr:
> +      if (nir_instr_next(cursor.instr) == NULL) {
> +         /* This is the last instruction, switch to after block */
> +         cursor.option = nir_cursor_after_block;
> +         cursor.block = cursor.instr->block;
> +      }
> +      return cursor;
> +
> +   default:
> +      unreachable("Inavlid cursor option");
> +   }
> +}
> +
> +bool
> +nir_cursors_equal(nir_cursor a, nir_cursor b)
> +{
> +   /* Reduced cursors should be unique */
> +   a = reduce_cursor(a);
> +   b = reduce_cursor(b);
> +
> +   return a.block == b.block && a.option == b.option;
> +}
> +
>  static bool
>  add_use_cb(nir_src *src, void *state)
>  {
> diff --git a/src/compiler/nir/nir.h b/src/compiler/nir/nir.h
> index 4c6c22f..c856b83 100644
> --- a/src/compiler/nir/nir.h
> +++ b/src/compiler/nir/nir.h
> @@ -1803,6 +1803,8 @@ typedef struct {
>     };
>  } nir_cursor;
>
> +bool nir_cursors_equal(nir_cursor a, nir_cursor b);
> +
>  static inline nir_cursor
>  nir_before_block(nir_block *block)
>  {
> --
> 2.5.0.400.gff86faf
>
> _______________________________________________
> mesa-dev mailing list
> mesa-dev at lists.freedesktop.org
> https://lists.freedesktop.org/mailman/listinfo/mesa-dev


More information about the mesa-dev mailing list