Minor tweaks to help out at a driver level.
[mesa.git] / src / mesa / main / nvvertexec.c
index 73d5440c79aa85f54abfe1ac90681bef6bf9071f..fd1519e9a87681f3520658612069500acdc1d649 100644 (file)
@@ -1,8 +1,8 @@
 /*
  * Mesa 3-D graphics library
- * Version:  5.1
+ * Version:  6.0
  *
- * Copyright (C) 1999-2003  Brian Paul   All Rights Reserved.
+ * Copyright (C) 1999-2004  Brian Paul   All Rights Reserved.
  *
  * Permission is hereby granted, free of charge, to any person obtaining a
  * copy of this software and associated documentation files (the "Software"),
@@ -35,6 +35,7 @@
 #include "mtypes.h"
 #include "nvvertexec.h"
 #include "nvvertprog.h"
+#include "program.h"
 #include "math/m_matrix.h"
 
 
@@ -63,6 +64,20 @@ _mesa_init_vp_registers(GLcontext *ctx)
    }
 
    /* The program parameters aren't touched */
+   /* XXX: This should be moved to glBegin() time, but its safe (and slow!) 
+    * here - Karl
+    */
+   if (ctx->VertexProgram.Current->Parameters) {
+      /* Grab the state */                       
+      _mesa_load_state_parameters(ctx, ctx->VertexProgram.Current->Parameters);
+
+      /* And copy it into the program state */
+      for (i=0; i<ctx->VertexProgram.Current->Parameters->NumParameters; i++) {
+         MEMCPY(ctx->VertexProgram.Parameters[i], 
+                &ctx->VertexProgram.Current->Parameters->Parameters[i].Values,
+                4*sizeof(GLfloat));                            
+      }                                  
+   }
 }
 
 
@@ -219,7 +234,8 @@ get_register_pointer( const struct vp_src_register *source,
 {
    if (source->RelAddr) {
       const GLint reg = source->Index + state->AddressReg[0];
-      ASSERT(source->File == PROGRAM_ENV_PARAM);
+      ASSERT( (source->File == PROGRAM_ENV_PARAM) || 
+        (source->File == PROGRAM_STATE_VAR) );
       if (reg < 0 || reg > MAX_NV_VERTEX_PROGRAM_PARAMS)
          return zeroVec;
       else
@@ -233,13 +249,11 @@ get_register_pointer( const struct vp_src_register *source,
             return state->Inputs[source->Index];
          case PROGRAM_LOCAL_PARAM:
             /* XXX fix */
-            return state->Temporaries[source->Index];
+            return state->Temporaries[source->Index]; 
          case PROGRAM_ENV_PARAM:
             return state->Parameters[source->Index];
          case PROGRAM_STATE_VAR:
-            /* XXX fix */
-            return NULL;
-            break;
+            return state->Parameters[source->Index];
          default:
             _mesa_problem(NULL,
                           "Bad source register file in fetch_vector4(vp)");
@@ -356,7 +370,19 @@ _mesa_exec_vertex_program(GLcontext *ctx, const struct vertex_program *program)
 
    ctx->_CurrentProgram = GL_VERTEX_PROGRAM_ARB; /* or NV, doesn't matter */
 
-   for (inst = program->Instructions; inst->Opcode != VP_OPCODE_END; inst++) {
+   /* If the program is position invariant, multiply the input
+    * position and the MVP matrix and stick it into the output pos slot
+    */
+   if (ctx->VertexProgram.Current->IsPositionInvariant) {
+      TRANSFORM_POINT( ctx->VertexProgram.Outputs[0], 
+                       ctx->_ModelProjectMatrix.m, 
+                       ctx->VertexProgram.Inputs[0]);
+
+      /* XXX: This could go elsewhere */
+      ctx->VertexProgram.Current->OutputsWritten |= 0x1;
+   }
+
+   for (inst = program->Instructions; /*inst->Opcode != VP_OPCODE_END*/; inst++) {
 
       if (ctx->VertexProgram.CallbackEnabled &&
           ctx->VertexProgram.Callback) {
@@ -689,7 +715,7 @@ _mesa_exec_vertex_program(GLcontext *ctx, const struct vertex_program *program)
             {
                GLfloat t[4];
                fetch_vector1( &inst->SrcReg[0], state, t );
-               t[0] = t[1] = t[2] = t[3] = _mesa_pow(2.0, t[0]);
+               t[0] = t[1] = t[2] = t[3] = (GLfloat)_mesa_pow(2.0, t[0]);
                store_vector4( &inst->DstReg, state, t );
             }
             break;
@@ -706,7 +732,7 @@ _mesa_exec_vertex_program(GLcontext *ctx, const struct vertex_program *program)
                GLfloat t[4], u[4];
                fetch_vector1( &inst->SrcReg[0], state, t );
                fetch_vector1( &inst->SrcReg[1], state, u );
-               t[0] = t[1] = t[2] = t[3] = _mesa_pow(t[0], u[0]);
+               t[0] = t[1] = t[2] = t[3] = (GLfloat)_mesa_pow(t[0], u[0]);
                store_vector4( &inst->DstReg, state, t );
             }
             break;