title: ARB Fragment If/Else
body: <p>I have a problem and I can't seem to wrap my head around it, so I was hoping someon here might be able to help me out.</p>
  
  <p>I'm writing a compiler for miniGLSL, and so far so good. I'm at the point where I need to output to an ARB fragment program, but the problem is, the ARB I have to target doesn't support branching. (A full list of supported instructions can be found here <a href="http://petewarden.com/notes/archives/2005/05/fragment_progra_2.html" rel="nofollow">http://petewarden.com/notes/archives/2005/05/fragment_progra_2.html</a> ).</p>
  
  <p>In order to simulate if/else, I've been making use of the CMP program as follows (assuming 0 or greater = true, otherwise, false. // represents comments as # causes bad formatting on here):</p>
  
  <pre><code>if (a &lt; b)
    a = 1 + 1;
    if (f &lt; g)
      c = 2 + 3;
  else
    if (h &lt; i)
      b = 1 + 2;
    else
      d = 2 + 3;
  </code></pre>
  
  <p>into ARB fragment:</p>
  
  <pre><code>TEMP cond1, cond2, cond3, tempvar1, tempvar2, tempvar3, tempvar4, a, b, c, d, e, f, g;
  //TOP IF
  //condition a &lt; b
  SLT a, b, cond1;
  SUB cond1, 1.0, cond1;
  
  //Assign if true
  ADD 1.0, 1.0, tempvar1;
  CMP cond1, a, tempvar1, a;
  
  //Condition f &lt; g
  SLT f, g, cond2;
  SUB cond2, 1.0, cond2;
  //if top level if was false, assign false, otherwise assign it to itself
  CMP cond1, -1.0, cond2, cond2;
  //Assignment
  ADD 2.0, 3.0, tempvar2;
  CMP cond2, c, tempvar2, c;
  
  //TOP ELSE
  //if h &lt; i
  SLT h, i, cond2;
  SUB cond2, 1.0, cond2;
  //If top level if was true, make false
  CMP cond1, cond2, -1.0, cond2;
  CMP cond2, tempvar3, b, b;
  //Else
  //if top level if was true, and previous if was false, make true
  </code></pre>
  
  <p>This is about where I get before i realize my code is going to start getting really ugly. Each level of if/else is going to introduce continually stacking compares, and additionally, the last else requires me to re-evaluate cond2, or use another register. I know I'm probably doing something wrong here, but I'm not sure what. I've tried using counters, tried adding the result of previous stages of if/else block, anding, oring, etc. but I can't find a good solution to how to convert if/else blocks into ARB fragment assembly that doesn't really on increasingly large stacks of CMP statements. Does any one have an idea how to make this simpler so my compiler can output this programmatically? I'm not worried to much about optimization at this point, I just want to get it to work.</p>
  
  <p>Thanks</p>