On 3 September 2011 11:38, Kenneth Graunke <span dir="ltr">&lt;<a href="mailto:kenneth@whitecape.org">kenneth@whitecape.org</a>&gt;</span> wrote:<br><div class="gmail_quote"><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex;">
<div><div></div><div class="h5">On 09/02/2011 09:06 AM, Paul Berry wrote:<br>
&gt; Previously, the old VS backend computed the URB entry size by adding<br>
&gt; the number of vertex shader outputs to the size of the URB header.<br>
&gt; This often produced a larger result than necessary, because some<br>
&gt; vertex shader outputs are stored in the header, so they were being<br>
&gt; double counted.  This patch changes the old VS backend to compute the<br>
&gt; URB entry size directly from the number of slots in the VUE map.<br>
&gt; ---<br>
&gt;  src/mesa/drivers/dri/i965/brw_vs.h      |    1 -<br>
&gt;  src/mesa/drivers/dri/i965/brw_vs_emit.c |   31 +++++++------------------------<br>
&gt;  2 files changed, 7 insertions(+), 25 deletions(-)<br>
&gt;<br>
&gt; diff --git a/src/mesa/drivers/dri/i965/brw_vs.h b/src/mesa/drivers/dri/i965/brw_vs.h<br>
&gt; index a02c06d..c31869c 100644<br>
&gt; --- a/src/mesa/drivers/dri/i965/brw_vs.h<br>
&gt; +++ b/src/mesa/drivers/dri/i965/brw_vs.h<br>
&gt; @@ -65,7 +65,6 @@ struct brw_vs_compile {<br>
&gt;<br>
&gt;     struct brw_vue_map vue_map;<br>
&gt;     GLuint first_output;<br>
&gt; -   GLuint nr_outputs;<br>
&gt;     GLuint last_scratch;<br>
&gt;<br>
&gt;     GLuint first_tmp;<br>
&gt; diff --git a/src/mesa/drivers/dri/i965/brw_vs_emit.c b/src/mesa/drivers/dri/i965/brw_vs_emit.c<br>
&gt; index e7667c8..7c430ce 100644<br>
&gt; --- a/src/mesa/drivers/dri/i965/brw_vs_emit.c<br>
&gt; +++ b/src/mesa/drivers/dri/i965/brw_vs_emit.c<br>
&gt; @@ -402,36 +402,19 @@ static void brw_vs_alloc_regs( struct brw_vs_compile *c )<br>
&gt;     /* The VS VUEs are shared by VF (outputting our inputs) and VS, so size<br>
&gt;      * them to fit the biggest thing they need to.<br>
&gt;      */<br>
&gt; -   attributes_in_vue = MAX2(c-&gt;nr_outputs, c-&gt;nr_inputs);<br>
&gt; +   attributes_in_vue = MAX2(c-&gt;vue_map.num_slots, c-&gt;nr_inputs);<br>
&gt;<br>
&gt; -   /* See emit_vertex_write() for where the VUE&#39;s overhead on top of the<br>
&gt; -    * attributes comes from.<br>
&gt; -    */<br>
&gt; -   if (intel-&gt;gen &gt;= 7) {<br>
&gt; -      int header_regs = 2;<br>
&gt; -      if (c-&gt;key.nr_userclip)<br>
&gt; -      header_regs += 2;<br>
&gt; -<br>
&gt; -      /* Each attribute is 16 bytes (1 vec4), so dividing by 4 gives us the<br>
&gt; -       * number of 64-byte (512-bit) units.<br>
&gt; -       */<br>
&gt; -      c-&gt;prog_data.urb_entry_size = (attributes_in_vue + header_regs + 3) / 4;<br>
&gt; -   } else if (intel-&gt;gen == 6) {<br>
&gt; -      int header_regs = 2;<br>
&gt; -      if (c-&gt;key.nr_userclip)<br>
&gt; -      header_regs += 2;<br>
&gt; -<br>
&gt; -      /* Each attribute is 16 bytes (1 vec4), so dividing by 8 gives us the<br>
&gt; +   if (intel-&gt;gen == 6) {<br>
&gt; +      /* Each attribute is 32 bytes (2 vec4s), so dividing by 8 gives us the<br>
&gt;         * number of 128-byte (1024-bit) units.<br>
&gt;         */<br>
&gt; -      c-&gt;prog_data.urb_entry_size = (attributes_in_vue + header_regs + 7) / 8;<br>
&gt; -   } else if (intel-&gt;gen == 5)<br>
&gt; +      c-&gt;prog_data.urb_entry_size = (attributes_in_vue + 7) / 8;<br>
&gt; +   } else {<br>
&gt;        /* Each attribute is 16 bytes (1 vec4), so dividing by 4 gives us the<br>
&gt;         * number of 64-byte (512-bit) units.<br>
&gt;         */<br>
&gt; -      c-&gt;prog_data.urb_entry_size = (attributes_in_vue + 6 + 3) / 4;<br>
&gt; -   else<br>
&gt; -      c-&gt;prog_data.urb_entry_size = (attributes_in_vue + 2 + 3) / 4;<br>
&gt; +      c-&gt;prog_data.urb_entry_size = (attributes_in_vue + 3) / 4;<br>
&gt; +   }<br>
&gt;<br>
&gt;     c-&gt;prog_data.total_grf = reg;<br>
<br>
</div></div>Totally non-obvious, but seems correct and is _much_ cleaner.<br>
<br>
While we&#39;re at it, it might be nicer to do:<br>
<br>
   if (intel-&gt;gen == 6)<br>
      c-&gt;prog_data.urb_entry_size = ALIGN(attributes_in_vue, 8) / 8;<br>
   else<br>
      c-&gt;prog_data.urb_entry_size = ALIGN(attributes_in_vue, 4) / 4;<br>
<br>
Otherwise, I get confused, thinking there are +7 or +3 registers<br>
dedicated to something or other.  Most likely because in the original<br>
code, (attributes_in_vue + 6 + 3) / 4, the +6 _is_ adding some header<br>
registers, while the +3 is purely a &quot;round up!&quot; factor.<br>
<br>
We can always do that in a follow-up patch if you prefer (or just not,<br>
because this is all going away soon enough.)<br>
</blockquote></div><br>Yeah, I like your rewrite, Ken--it&#39;s clearer, and it&#39;s a simple enough change.  I&#39;ll go ahead and update the patch.<br>