Replace add_newer_entrypoints (src/mesa/main/context.c) with
device-specific code.  A new Python script
(src/mesa/glapi/extension_helper.py) generates a list of all
entry-points for all known extensions.  Each driver the selects only
the extensions that it needs and enables the via either
driInitExtensions or driInitSingleExtension.

This code has been compile-tested on a drivers, but has only been
run-tested on mga and i915 (on i830 hardware).

These changes were discussed at length on the mesa3d-dev mailing list.

http://marc.theaimsgroup.com/?t=111947074700001&r=1&w=2
diff --git a/src/mesa/glapi/extension_helper.py b/src/mesa/glapi/extension_helper.py
new file mode 100644
index 0000000..21f5b56
--- /dev/null
+++ b/src/mesa/glapi/extension_helper.py
@@ -0,0 +1,289 @@
+#!/usr/bin/env python
+
+# (C) Copyright IBM Corporation 2005
+# 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"),
+# to deal in the Software without restriction, including without limitation
+# on the rights to use, copy, modify, merge, publish, distribute, sub
+# license, and/or sell copies of the Software, and to permit persons to whom
+# the Software is furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice (including the next
+# paragraph) shall be included in all copies or substantial portions of the
+# Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.  IN NO EVENT SHALL
+# IBM AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
+# IN THE SOFTWARE.
+#
+# Authors:
+#    Ian Romanick <idr@us.ibm.com>
+
+import gl_XML
+import license
+import sys, getopt, string
+
+vtxfmt = [
+    "ArrayElement", \
+    "Color3f", \
+    "Color3fv", \
+    "Color4f", \
+    "Color4fv", \
+    "EdgeFlag", \
+    "EdgeFlagv", \
+    "EvalCoord1f", \
+    "EvalCoord1fv", \
+    "EvalCoord2f", \
+    "EvalCoord2fv", \
+    "EvalPoint1", \
+    "EvalPoint2", \
+    "FogCoordfEXT", \
+    "FogCoordfvEXT", \
+    "Indexf", \
+    "Indexfv", \
+    "Materialfv", \
+    "MultiTexCoord1fARB", \
+    "MultiTexCoord1fvARB", \
+    "MultiTexCoord2fARB", \
+    "MultiTexCoord2fvARB", \
+    "MultiTexCoord3fARB", \
+    "MultiTexCoord3fvARB", \
+    "MultiTexCoord4fARB", \
+    "MultiTexCoord4fvARB", \
+    "Normal3f", \
+    "Normal3fv", \
+    "SecondaryColor3fEXT", \
+    "SecondaryColor3fvEXT", \
+    "TexCoord1f", \
+    "TexCoord1fv", \
+    "TexCoord2f", \
+    "TexCoord2fv", \
+    "TexCoord3f", \
+    "TexCoord3fv", \
+    "TexCoord4f", \
+    "TexCoord4fv", \
+    "Vertex2f", \
+    "Vertex2fv", \
+    "Vertex3f", \
+    "Vertex3fv", \
+    "Vertex4f", \
+    "Vertex4fv", \
+    "CallList", \
+    "CallLists", \
+    "Begin", \
+    "End", \
+    "VertexAttrib1fNV", \
+    "VertexAttrib1fvNV", \
+    "VertexAttrib2fNV", \
+    "VertexAttrib2fvNV", \
+    "VertexAttrib3fNV", \
+    "VertexAttrib3fvNV", \
+    "VertexAttrib4fNV", \
+    "VertexAttrib4fvNV", \
+    "VertexAttrib1fARB", \
+    "VertexAttrib1fvARB", \
+    "VertexAttrib2fARB", \
+    "VertexAttrib2fvARB", \
+    "VertexAttrib3fARB", \
+    "VertexAttrib3fvARB", \
+    "VertexAttrib4fARB", \
+    "VertexAttrib4fvARB", \
+    "Rectf", \
+    "DrawArrays", \
+    "DrawElements", \
+    "DrawRangeElements", \
+    "EvalMesh1", \
+    "EvalMesh2", \
+]
+
+def condition_for_function(f, abi, all_not_in_ABI):
+	"""Create a C-preprocessor condition for the function.
+	
+	There are two modes of operation.  If all_not_in_ABI is set, a
+	condition is only created is all of the entry-point names for f are
+	not in the selected ABI.  If all_not_in_ABI is not set, a condition
+	is created if any entryp-point name is not in the selected ABI.
+	"""
+
+	condition = []
+	for n in f.entry_points:
+		[category, num] = api.get_category_for_name( n )
+		if category not in abi:
+			condition.append( 'defined(need_%s)' % (gl_XML.real_category_name( category )) )
+		elif all_not_in_ABI:
+			return []
+
+	return condition
+
+
+class PrintGlExtensionGlue(gl_XML.gl_print_base):
+	def __init__(self):
+		gl_XML.gl_print_base.__init__(self)
+
+		self.name = "extension_helper.py (from Mesa)"
+		self.license = license.bsd_license_template % ("(C) Copyright IBM Corporation 2005", "IBM")
+		return
+
+
+	def printRealHeader(self):
+		print '#include "utils.h"'
+		print ''
+		return
+
+
+	def printBody(self, api):
+		abi = [ "1.0", "1.1", "1.2", "GL_ARB_multitexture" ]
+
+		category_list = {}
+
+		print '#ifndef NULL'
+		print '# define NULL 0'
+		print '#endif'
+		print ''
+
+		for f in api.functionIterateAll():
+			condition = condition_for_function(f, abi, 0)
+			if len(condition):
+				print '#if %s' % (string.join(condition, " || "))
+				print 'static const char %s_names[] = ' % (f.name)
+
+				parameter_signature = ''
+				for p in f.parameterIterator():
+					# FIXME: This is a *really* ugly hack. :(
+
+					tn = p.type_expr.get_base_type_node()
+					if p.is_pointer():
+						parameter_signature += 'p'
+					elif tn.integer:
+						parameter_signature += 'i'
+					elif tn.size == 4:
+						parameter_signature += 'f'
+					else:
+						parameter_signature += 'd'
+
+				print '    "%s\\0" /* Parameter signature */' % (parameter_signature)
+
+				for n in f.entry_points:
+					print '    "gl%s\\0"' % (n)
+
+					[category, num] = api.get_category_for_name( n )
+					if category not in abi:
+						c = gl_XML.real_category_name(category)
+						if not category_list.has_key(c):
+							category_list[ c ] = []
+
+						category_list[ c ].append( [f.name, f.offset] )
+
+				print '    "";'
+				print '#endif'
+				print ''
+
+		keys = category_list.keys()
+		keys.sort()
+
+		for category in keys:
+			print '#if defined(need_%s)' % (category)
+			print 'static const struct dri_extension_function %s_functions[] = {' % (category)
+			for [function, offset] in category_list[ category ]:
+				print '    { %s_names, %d },' % (function, offset)
+			print '    { NULL, 0 }'
+			print '};'
+			print '#endif'
+			print ''
+		
+		return
+
+
+class PrintInitDispatch(gl_XML.gl_print_base):
+	def __init__(self):
+		gl_XML.gl_print_base.__init__(self)
+
+		self.name = "extension_helper.py (from Mesa)"
+		self.license = license.bsd_license_template % ("(C) Copyright IBM Corporation 2005", "IBM")
+		return
+
+
+	def do_function_body(self, api, abi, vtxfmt_only):
+		last_condition_string = None
+		for f in api.functionIterateByOffset():
+			if (f.name in vtxfmt) and not vtxfmt_only:
+				continue
+
+			if (f.name not in vtxfmt) and vtxfmt_only:
+				continue
+
+			condition = condition_for_function(f, abi, 1)
+			condition_string = string.join(condition, " || ")
+
+			if condition_string != last_condition_string:
+				if last_condition_string:
+					print '#endif /* %s */' % (last_condition_string)
+
+				if condition_string:
+					print '#if %s' % (condition_string)
+				
+			if vtxfmt_only:
+				print '   disp->%s = vfmt->%s;' % (f.name, f.name)
+			else:
+				print '   disp->%s = _mesa_%s;' % (f.name, f.name)
+
+			last_condition_string = condition_string
+
+		if last_condition_string:
+			print '#endif /* %s */' % (last_condition_string)
+		
+
+
+	def printBody(self, api):
+		abi = [ "1.0", "1.1", "1.2", "GL_ARB_multitexture" ]
+		
+		print 'void driver_init_exec_table(struct _glapi_table *disp)'
+		print '{'
+		self.do_function_body(api, abi, 0)
+		print '}'
+		print ''
+		print 'void driver_install_vtxfmt(struct _glapi_table *disp, const GLvertexformat *vfmt)'
+		print '{'
+		self.do_function_body(api, abi, 1)
+		print '}'
+
+		return
+
+
+def show_usage():
+	print "Usage: %s [-f input_file_name] [-m output_mode]" % sys.argv[0]
+	print "    -m output_mode   Output mode can be one of 'extensions' or 'exec_init'."
+	sys.exit(1)
+
+if __name__ == '__main__':
+	file_name = "gl_API.xml"
+    
+	try:
+		(args, trail) = getopt.getopt(sys.argv[1:], "f:m:")
+	except Exception,e:
+		show_usage()
+
+	mode = "extensions"
+	for (arg,val) in args:
+		if arg == "-f":
+			file_name = val
+		if arg == '-m':
+			mode = val
+
+
+	api = gl_XML.parse_GL_API( file_name )
+
+	if mode == "extensions":
+		printer = PrintGlExtensionGlue()
+	elif mode == "exec_init":
+		printer = PrintInitDispatch()
+	else:
+		show_usage()
+
+	printer.Print( api )