TNL module needs to implement ctx->Driver.ProgramStringNotify() function
so that calls to glProgramStringARB() to specify a new program causes the
TNL-attached data to get recomputed.
diff --git a/src/mesa/drivers/common/driverfuncs.c b/src/mesa/drivers/common/driverfuncs.c
index 8503135..9fe4ee3 100644
--- a/src/mesa/drivers/common/driverfuncs.c
+++ b/src/mesa/drivers/common/driverfuncs.c
@@ -45,6 +45,7 @@
 #endif
 
 #include "driverfuncs.h"
+#include "tnl/tnl.h"
 #include "swrast/swrast.h"
 
 
@@ -222,6 +223,7 @@
    driver->NeedFlush = 0;
    driver->SaveNeedFlush = 0;
 
+   driver->ProgramStringNotify = _tnl_program_string;
    driver->FlushVertices = NULL;
    driver->SaveFlushVertices = NULL;
    driver->NotifySaveBegin = NULL;
diff --git a/src/mesa/tnl/t_vb_arbprogram.c b/src/mesa/tnl/t_vb_arbprogram.c
index 08b9ffc..8b16835 100644
--- a/src/mesa/tnl/t_vb_arbprogram.c
+++ b/src/mesa/tnl/t_vb_arbprogram.c
@@ -43,6 +43,7 @@
 #include "t_pipeline.h"
 #include "t_vb_arbprogram.h"
 
+
 #define DISASSEM 0
 
 /*--------------------------------------------------------------------------- */
@@ -1459,3 +1460,20 @@
    validate_vertex_program,	/* validate */
    run_arb_vertex_program	/* run */
 };
+
+
+/**
+ * Called via ctx->Driver.ProgramStringNotify() after a new vertex program
+ * string has been parsed.
+ */
+void
+_tnl_program_string(GLcontext *ctx, GLenum target, struct program *program)
+{
+   if (target == GL_VERTEX_PROGRAM_ARB) {
+      /* free any existing tnl data hanging off the program */
+      struct vertex_program *vprog = (struct vertex_program *) program;
+      if (vprog->TnlData) {
+         free_tnl_data(vprog);
+      }
+   }
+}
diff --git a/src/mesa/tnl/tnl.h b/src/mesa/tnl/tnl.h
index d04310f..428fe12 100644
--- a/src/mesa/tnl/tnl.h
+++ b/src/mesa/tnl/tnl.h
@@ -83,5 +83,7 @@
 extern void
 _tnl_allow_pixel_fog( GLcontext *ctx, GLboolean value );
 
+extern void
+_tnl_program_string(GLcontext *ctx, GLenum target, struct program *program);
 
 #endif