/[gzz]/gzz/gfx/libutil/nvcode.py
ViewVC logotype

Diff of /gzz/gfx/libutil/nvcode.py

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.6 by jvk, Sat Nov 23 17:43:37 2002 UTC revision 1.7 by jvk, Sun Nov 24 10:01:40 2002 UTC
# Line 38  def combinerscale(x): Line 38  def combinerscale(x):
38    
39  def matchop(str,i):  def matchop(str,i):
40      def opchar(str, i):      def opchar(str, i):
41          return i < len(str) and str[i] in [ "*", "/", "+", "-", ".", "|" ]          return i < len(str) and str[i] in [ "*", "/", "+", "-", ".", "|", "%" ]
42      if opchar(str, i): return i + 1      if opchar(str, i): return i + 1
43      return 0      return 0
44    
# Line 144  def parseregs(tree): Line 144  def parseregs(tree):
144                      tree[i:i+1] = [("reg", regmap[node[1]], "RGB")]                      tree[i:i+1] = [("reg", regmap[node[1]], "RGB")]
145          i += 1          i += 1
146    
 def removeparen(tree):  
     # Remove extra parentheses  
     if len(tree) == 1 and tree[0][0] == "sub":  
         tree[:] = tree[0][1]  
     return tree  
       
147  def parsekey(tree):  def parsekey(tree):
148      # Return list of node types      # Return list of node types
149      return map(lambda x: x[0], tree)      return tuple(map(lambda x: x[0], tree))
       
150            
151  def findregs(tree, type = "reg"):  def findregs(tree, type = "reg"):
152      def func(x, type=type): return x[0] == type      def func(x, type=type): return x[0] == type
# Line 189  def parseinput(tree, final = 0): Line 182  def parseinput(tree, final = 0):
182              ("-", .5): "HALF_BIAS_NORMAL_NV",              ("-", .5): "HALF_BIAS_NORMAL_NV",
183              }              }
184    
185      key = tuple(parsekey(tree))      for i in range(0,len(tree)):
186                if tree[i][0] == "sub":
187      if inputmap.has_key(key):              key = parsekey(tree[i][1])
188          reg = (findregs(tree) + [("reg", "ZERO", "ALPHA")])[0]              if inputmap.has_key(key):
189          tree[:] = [("in", reg[1], inputmap[key], reg[2])]                  reg = (findregs(tree[i][1]) + [("reg", "ZERO", "ALPHA")])[0]
190      else:                  tree[i] = ("in", reg[1], inputmap[key], reg[2])
         for i in range(0,len(tree)):  
             if tree[i][0] == "sub":  
                 parseinput(tree[i][1], final)  
                 if len(tree[i][1]) == 1:  
                     tree[i] = tree[i][1][0]  
191              else:              else:
192                  # Search for substring matches, too, for single-node keys                  parseinput(tree[i][1], final)
193                  key = (tree[i][0],)          elif tree[i][0] == "reg":
194                  if inputmap.has_key(key):              # Convert identity-mapped regs
195                      reg = ("reg", "ZERO", "ALPHA")              tree[i] = ("in", tree[i][1], inputmap["reg",], tree[i][2])
                     if key == ("reg",): reg = tree[i]  
                     tree[i] = ("in", reg[1], inputmap[key], reg[2])  
196    
197        return tree
198    
199  def parseGeneralCombiner(outreg, tree):  def parseGeneralCombiner(outreg, tree):
200      out = {      out = {
# Line 227  def parseGeneralCombiner(outreg, tree): Line 214  def parseGeneralCombiner(outreg, tree):
214          ("-", 0): "NONE",          ("-", 0): "NONE",
215          }          }
216            
217      key = tuple(parsekey(tree))      key = parsekey(tree)
218      if outputscale.has_key(key):      if outputscale.has_key(key):
219          out["scale"] = outputscale[key]          out["scale"] = outputscale[key]
220          tree[:] = tree[:-2]          tree = tree[0][1]
         removeparen(tree)  
221    
222      key = tuple(parsekey(tree)[-2:])      key = parsekey(tree[-2:])
223      if outputbias.has_key(key):      if outputbias.has_key(key):
224          out["bias"] = outputbias[key]          out["bias"] = outputbias[key]
225          tree[:] = tree[:-2]          tree = tree[:-2]
226    
     removeparen(tree)  
227      parseinput(tree)      parseinput(tree)
228    
229      funcmap = {      funcmap = {
230          ("in", ".", "in"): ("AB", "TRUE"),          ("in", ".", "in"): ("AB", "TRUE"),
         ("in",):           ("A",  "FALSE"),  
231          ("in", "*", "in"): ("AB", "FALSE"),          ("in", "*", "in"): ("AB", "FALSE"),
232            ("in",):           ("A",  "FALSE"),
233            ("-", "in"):       ("A",  "FALSE", 1),
234    
235          ("in", "+", "in"):                       ("AC",   "FALSE"),          ("in", "+", "in"):                       ("AC",   "FALSE"),
236          ("in", "+", "in", "*", "in"):            ("ACD",  "FALSE"),          ("in", "+", "in", "*", "in"):            ("ACD",  "FALSE"),
237          ("in", "*", "in", "+", "in"):            ("ABC",  "FALSE"),          ("in", "*", "in", "+", "in"):            ("ABC",  "FALSE"),
238          ("in", "*", "in", "+", "in", "*", "in"): ("ABCD", "FALSE"),          ("in", "*", "in", "+", "in", "*", "in"): ("ABCD", "FALSE"),
239            ("-", "in", "+", "in"):                  ("AC",   "FALSE", 1),
240            ("-", "in", "+", "in", "*", "in"):       ("ACD",  "FALSE", 1),
241            ("in", "-", "in"):                       ("AC",   "FALSE", 2),
242            ("in", "*", "in", "-", "in"):            ("ABC",  "FALSE", 1),
243            ("-", "in", "-", "in"):                  ("AC",   "FALSE", 3),
244          ("in", "|", "in"):                       ("AC",   "TRUE"),          ("in", "|", "in"):                       ("AC",   "TRUE"),
245          ("in", "|", "in", "*", "in"):            ("ACD",  "TRUE"),          ("in", "|", "in", "*", "in"):            ("ACD",  "TRUE"),
246          ("in", "*", "in", "|", "in"):            ("ABC",  "TRUE"),          ("in", "*", "in", "|", "in"):            ("ABC",  "TRUE"),
247          ("in", "*", "in", "|", "in", "*", "in"): ("ABCD", "TRUE"),          ("in", "*", "in", "|", "in", "*", "in"): ("ABCD", "TRUE"),
248          }          }
249    
250      key = tuple(parsekey(tree))      key = parsekey(tree)
251      if funcmap.has_key(key):      if funcmap.has_key(key):
252          func = funcmap[key]          func = funcmap[key]
253          regs = findregs(tree, "in")          regs = findregs(tree, "in")
254            neg = len(func) > 2 and func[2]
255    
256          if "C" in func[0]:          if "C" in func[0]:
257              regset = "ABCD"              regset = "ABCD"
# Line 275  def parseGeneralCombiner(outreg, tree): Line 267  def parseGeneralCombiner(outreg, tree):
267    
268          for reg in regset:          for reg in regset:
269              if reg not in func[0]:              if reg not in func[0]:
270                  out[reg] = "ZERO UNSIGNED_IDENTITY_NV ALPHA"                  if neg & 1: out[reg] = "ZERO EXPAND_NORMAL_NV ALPHA"
271                    else: out[reg] = "ZERO UNSIGNED_INVERT_NV ALPHA"
272                    neg >>= 1
273      else:      else:
274          print "ERROR: General combiner function", key, "not recognized"          print "ERROR: General combiner function", key, "not recognized"
275          return None          return None
# Line 346  def outputGeneralCombiner(stage): Line 339  def outputGeneralCombiner(stage):
339    
340    
341  def parseFinalCombiner(outreg, tree):  def parseFinalCombiner(outreg, tree):
342      parseinput(tree, final = 1)      tree = parseinput([("sub",tree)], final = 1)
343        if tree[0][0] == "sub": tree = tree[0][1]
344    
345      key = tuple(parsekey(tree))      key = parsekey(tree)
346    
347      if outreg == "EF":      if outreg == "EF":
348          if key != ("in", "*", "in"):          if key != ("in", "*", "in"):
349              print "ERROR: EF must be a product, got", key              print "ERROR: EF must be a product, got", key
350              return ""              return ""
351          return ("FinalCombinerInput VARIABLE_E_NV " +          return ("FinalCombinerInputNV VARIABLE_E_NV " +
352                  " ".join(tree[0][1:]) + "\n" +                  " ".join(tree[0][1:]) + "\n" +
353                  "FinalCombinerInput VARIABLE_F_NV " +                  "FinalCombinerInputNV VARIABLE_F_NV " +
354                  " ".join(tree[2][1:]) + "\n")                  " ".join(tree[2][1:]) + "\n")
355      elif outreg == "ALPHA":      elif outreg == "ALPHA":
356          if key != ("in",):          if key != ("in",):
357              print "ERROR: alpha must be an input mapped register, got", key              print "ERROR: alpha must be an input mapped register, got", key
358              return ""              return ""
359          return ("FinalCombinerInput VARIABLE_G_NV " +          return ("FinalCombinerInputNV VARIABLE_G_NV " +
360                  " ".join(tree[0][1:]) + "\n")                  " ".join(tree[0][1:]) + "\n")
361      else:      else:
362          funcmap = {          funcmap = {
# Line 387  def parseFinalCombiner(outreg, tree): Line 381  def parseFinalCombiner(outreg, tree):
381                                 regs[0], regs[i])                                 regs[0], regs[i])
382                          return ""                          return ""
383                  else:                  else:
384                      code += ("FinalCombinerInput VARIABLE_%s_NV %s\n"                      code += ("FinalCombinerInputNV VARIABLE_%s_NV %s\n"
385                               % (func[i], " ".join(regs[i][1:])))                               % (func[i], " ".join(regs[i][1:])))
386    
387              for reg in "ABCD":              for reg in "ABCD":
388                  if reg not in func:                  if reg not in func:
389                      code += ("FinalCombinerInput VARIABLE_%s_NV "                      code += ("FinalCombinerInputNV VARIABLE_%s_NV "
390                               "ZERO UNSIGNED_IDENTITY_NV ALPHA\n" % reg)                               "ZERO UNSIGNED_IDENTITY_NV ALPHA\n" % reg)
391    
392              return code              return code
# Line 419  REG = REGNAME Line 413  REG = REGNAME
413      | REGNAME . RGB_COMP      | REGNAME . RGB_COMP
414    
415  IN = REG  IN = REG
416       | (REG)
417     | (1 - REG)     | (1 - REG)
418     | (+REG)     | (+REG)
419     | (-REG)     | (-REG)
# Line 426  IN = REG Line 421  IN = REG
421     | (1 - 2 * REG)     | (1 - 2 * REG)
422     | (REG - .5)     | (REG - .5)
423     | (.5 - REG)     | (.5 - REG)
424     | 0 | .5 | 1 | (-1) | (-.5) | (-0) | (+0) | (+.5) | (+1)     | (0) | (.5) | (1) | (-1) | (-.5) | (-0) | (+0) | (+.5) | (+1)
    | (IN)  
425    
426  EXP = IN . IN  EXP = IN . IN
427      | IN      | IN
# Line 441  EXP = IN . IN Line 435  EXP = IN . IN
435      | IN * IN '|' IN      | IN * IN '|' IN
436      | IN * IN '|' IN * IN      | IN * IN '|' IN * IN
437    
438  PAREN_EXP = EXP  BIASED_EXP = EXP
439            | (EXP)             | EXP - .5
440               | EXP - 0
 BIASED_EXP = PAREN_EXP  
            | PAREN_EXP - .5  
            | PAREN_EXP - 0  
441    
442  OUT = BIASED_EXP  OUT = BIASED_EXP
443      | (BIASED_EXP) / 2      | (BIASED_EXP) / 2
# Line 455  OUT = BIASED_EXP Line 446  OUT = BIASED_EXP
446      | (BIASED_EXP) * 2      | (BIASED_EXP) * 2
447      | (BIASED_EXP) * 4      | (BIASED_EXP) * 4
448                        
   
449  FINAL_IN = REG  FINAL_IN = REG
450           | (1 - REG)            | (1 - REG)
451           | 0 | 1            | (0) | (1)
452           | (FINAL_IN)  
453    FINAL_IN1 = FINAL_IN
454              | 1 - REG
455              | 0 | 1
456    
457  FINAL_OUT = FINAL_IN * FINAL_IN + FINAL_IN * FINAL_IN + FINAL_IN  FINAL_OUT = FINAL_IN * FINAL_IN + FINAL_IN * FINAL_IN + FINAL_IN
458            | FINAL_IN * FINAL_IN + FINAL_IN * FINAL_IN            | FINAL_IN * FINAL_IN + FINAL_IN * FINAL_IN
459            | FINAL_IN * FINAL_IN + FINAL_IN            | FINAL_IN * FINAL_IN + FINAL_IN
460            | FINAL_IN + FINAL_IN            | FINAL_IN + FINAL_IN
461            | FINAL_IN * FINAL_IN            | FINAL_IN * FINAL_IN
462            | FINAL_IN            | FINAL_IN1
463    
464  FUNC = REG '=' OUT  FUNC = REG '=' OUT
465       | RGB_COMP '=' FINAL_OUT       | RGB_COMP '=' FINAL_OUT
466       | ALPHA_COMP '=' FINAL_IN       | ALPHA_COMP '=' FINAL_IN1
467       | EF '=' FINAL_IN * FINAL_IN       | EF '=' FINAL_IN * FINAL_IN
468       | CONST0 '=' vector       | CONST0 '=' vector
469       | CONST1 '=' vector       | CONST1 '=' vector
# Line 479  FUNC = REG '=' OUT Line 472  FUNC = REG '=' OUT
472  # The syntax is given by FUNC above.  # The syntax is given by FUNC above.
473  # Code from lines not containing a '=' is passed through.  # Code from lines not containing a '=' is passed through.
474  #  #
475  #   str     The code lines separated by '\n' or ';'. '#'-comments are removed.  #   str     The code lines separated by '\n' or ';'. '#'-comments are ignored
476  #   returns The generated code  #   returns The generated code
477  #  #
478  # NUM_GENERAL_COMBINERS_NV and PER_STAGE_CONSTANTS_NV are automatically set.  # NUM_GENERAL_COMBINERS_NV and PER_STAGE_CONSTANTS_NV are automatically set.
479  #  #
480  # Semantics:  # Semantics:
481  #   - A new combiner stage is started for all combiner code lines except for  #   - A new combiner stage is started (unless empty) for all lines except for
482  #     those adjacent "REG = OUT" assignments that can fit in the current stage.  #     those adjacent "REG = OUT" assignments that can fit in the current stage.
483  #   - Per stage constants are enabled unless all constant assignments are  #   - Per stage constants are enabled unless all constant assignments are
484  #     either before or after all general combiner register assignments  #     either before or after all general combiner register assignments
# Line 502  FUNC = REG '=' OUT Line 495  FUNC = REG '=' OUT
495  #   color = EF * FOG + (1-EF) * SPARE1  #   color = EF * FOG + (1-EF) * SPARE1
496  #  #
497  def parseCombiner(str):  def parseCombiner(str):
498      def removeComment(line):      def splitLine(line):
499          pos = line.find("#")          pos = line.find("#")
500          if pos >= 0: return line[:pos]          if pos >= 0:
501          return line              if line[:pos].strip():
502                            return line[:pos].split(";") + [ line[pos:] ]
503      lines = ";".join(map(removeComment,str.splitlines())).split(";")              return [ line ]
504            return line.split(";")
505          
506        lines = reduce(lambda x,y: x+y, map(splitLine, str.splitlines()))
507        
508      code = ""      code = ""
509            
510      stage = {      stage = {
# Line 519  def parseCombiner(str): Line 514  def parseCombiner(str):
514          }          }
515    
516      for line in lines:      for line in lines:
517          line = line.strip()          if line.lstrip().startswith("#"):
518          if not line: continue              code += line + "\n"
519                continue
520                
521          pos = line.find("=")          pos = line.find("=")
522          if pos == -1:          if pos == -1:
523                code += outputGeneralCombiner(stage)
524              code += line + "\n"              code += line + "\n"
525              continue              continue
526    
# Line 562  def parseCombiner(str): Line 559  def parseCombiner(str):
559                      out = parseGeneralCombiner(outreg, right)                      out = parseGeneralCombiner(outreg, right)
560                      if not out: return ""                      if not out: return ""
561    
562                        if outcomp == "BLUE":
563                            print "ERROR: cannot write only BLUE in", line
564                            return ""
565    
566                      if not addStageComp(stage[outcomp], out):                      if not addStageComp(stage[outcomp], out):
567                          code += outputGeneralCombiner(stage)                          code += outputGeneralCombiner(stage)
568                          stage[outcomp] = out                          stage[outcomp] = out

Legend:
Removed from v.1.6  
changed lines
  Added in v.1.7

savannah-hackers-public@gnu.org
ViewVC Help
Powered by ViewVC 1.1.26