[m-dev.] for review: add MC++ implementation of library and runtime

Tyson Dowd trd at cs.mu.OZ.AU
Sun Dec 24 19:37:16 AEDT 2000


On 10-Dec-2000, Fergus Henderson <fjh at cs.mu.OZ.AU> wrote:
> On 04-Dec-2000, Tyson Dowd <trd at cs.mu.OZ.AU> wrote:

> > +.class public generic {
> 
> Please document the purpose of this class
> and explain why it is implemented in IL.
> 
> > +.method static default  int32 generic_call2(class System.Object, 
> > +	class System.Object, class System.Object) 
> > +{
> > +	ldarg.1
> > +	ldarg.2
> > +	ldarg.0
> > +	call 	int32 convert_imp::ToInt32(class System.Object)
> > +	calli	int32 (class System.Object, class System.Object)
> > +	ret
> > +}
> 
> Please document this code.
> 
> Every `ldarg' in this file really ought to have a comment
> saying the name of the argument that it is loading.
> For every function, there should be documentation of what
> the function does, and the names and meaning of the function
> parameters.

This is a good idea.

I've done everything else you suggested too.

> OK, that completes this review.  I'd like to see a relative diff
> when you've addressed those issues.

Here's the diff.  I still need to write a log message for a few of the
compiler/*.m files.  There are some stray ^M characters in here from the
DOS/Unix conversion that interdiff didn't seem to handle so well.

And I've just noticed that mercury_mcpp.h hasn't yet been reviewed or
updated -- I need to comment this file.  It's included in this diff, but
isn't really in a good enough state to be worth a review.

But everything else should be pretty close now.

diff -u configure.in configure.in
--- configure.in
+++ configure.in
@@ -316,7 +316,9 @@
 AC_MSG_CHECKING(for Microsoft.NET Framework SDK)
 AC_CACHE_VAL(mercury_cv_microsoft_dotnet, [
 if test "$ILASM" != ""; then
-	MS_DOTNET_SDK_DIR=`expr $ILASM : '\(.*\)/bin/ilasm'`
+	changequote(<<,>>) 
+	MS_DOTNET_SDK_DIR=`expr "$ILASM" : '\(.*\)[/\\]*[bB]in[/\\]*ilasm'`
+	changequote([,]) 
 	mercury_cv_microsoft_dotnet="yes"
 else
 	MS_DOTNET_SDK_DIR=""
@@ -324,6 +326,7 @@
 fi
 ])
 AC_MSG_RESULT($mercury_cv_microsoft_dotnet)
+ILASM=`basename "$ILASM"`
 
 AC_SUBST(ILASM)
 AC_SUBST(MS_DOTNET_SDK_DIR)
diff -u compiler/mlds_to_ilasm.m compiler/mlds_to_ilasm.m
--- compiler/mlds_to_ilasm.m
+++ compiler/mlds_to_ilasm.m
@@ -178,10 +178,9 @@
 	io__nl,
 	io__write_strings([
 		"#using <mscorlib.dll>\n",
-		"using namespace System;\n",
 		"#include ""mercury_mcpp.h""\n",
-		"using namespace mercury;\n",
 		"#using ""mercury_mcpp.dll""\n",
+		"#using ""mercury_il.dll""\n",
 		"#using """, ModuleNameStr, ".dll""\n",
 		% XXX this supresses problems caused by references to 
 		% float.  If you don't do this, you'll get link errors.
@@ -449,6 +448,14 @@
 	write_managed_cpp_rval_const(RvalConst).
 write_managed_cpp_rval(unop(Unop, Rval)) -->
 	( 
+		{ Unop = std_unop(StdUnop) },
+		{ c_util__unary_prefix_op(StdUnop, UnopStr) }
+	->
+		io__write_string(UnopStr),
+		io__write_string("("),
+		write_managed_cpp_rval(Rval),
+		io__write_string(")")
+	;
 		{ Unop = cast(Type) }
 	->
 		io__write_string("("),
@@ -456,10 +463,24 @@
 		io__write_string(") "),
 		write_managed_cpp_rval(Rval)
 	;
-		io__write_string(" /* unop rval -- unimplemented */ ")
+		io__write_string(" /* XXX box or unbox unop -- unimplemented */ "),
+		write_managed_cpp_rval(Rval)
+	).
+write_managed_cpp_rval(binop(Binop, Rval1, Rval2)) -->
+	( 
+		{ c_util__binary_infix_op(Binop, BinopStr) }
+	->
+		io__write_string("("),
+		write_managed_cpp_rval(Rval1),
+		io__write_string(") "),
+		io__write_string(BinopStr),
+		io__write_string(" ("),
+		write_managed_cpp_rval(Rval2),
+		io__write_string(")")
+	;
+		io__write_string(" /* binop rval -- unimplemented */ ")
 	).
-write_managed_cpp_rval(binop(_, _, _)) -->
-	io__write_string(" /* binop rval -- unimplemented */ ").
+
 write_managed_cpp_rval(mem_addr(_)) -->
 	io__write_string(" /* mem_addr rval -- unimplemented */ ").
 	
@@ -511,8 +532,14 @@
 	{ FieldId = qual(_, FieldName) },
 	io__write_string(FieldName).
 
-write_managed_cpp_lval(field(_, _, offset(_), _, _)) -->
-	io__write_string(" /* offset field lval -- unimplemented */ ").
+write_managed_cpp_lval(field(_, Rval, offset(OffSet), _, _)) -->
+	io__write_string("("),
+	write_managed_cpp_rval(Rval),
+	io__write_string(")"),
+	io__write_string("["),
+	write_managed_cpp_rval(OffSet),
+	io__write_string("]").
+
 write_managed_cpp_lval(mem_ref(Rval, _)) -->
 	io__write_string("*"),
 	write_managed_cpp_rval(Rval).
diff -u library/Mmakefile library/Mmakefile
--- library/Mmakefile
+++ library/Mmakefile
@@ -86,8 +86,8 @@
 			$(INTERMODULE_OPTS) $(CHECK_TERM_OPTS)
 MGNUC	=	$(M_ENV) $(SCRIPTS_DIR)/mgnuc
 MGNUCFLAGS =	$(DLL_CFLAGS)
-MSCLFLAGS  =	-I$(RUNTIME_DIR) 
-MSCL_NOASM=:noAssembly
+MS_CLFLAGS  =	-I$(RUNTIME_DIR) 
+MS_CL_NOASM=:noAssembly
 LDFLAGS	=	-L$(BOEHM_GC_DIR) -L$(RUNTIME_DIR)
 ALL_LDFLAGS =	$(LDFLAGS) $(EXTRA_LDFLAGS)
 LDLIBS	=	-l$(RT_LIB_NAME) \
@@ -211,9 +211,11 @@
 lib_std: dlls mercury.dll
 
 # Instead of generating UNIX style libraries, we general a bunch of
-# DLLs.  We have to hardcode 
-RUNTIME_DLLS=../runtime/mercury_cpp.dll ../runtime/mercury_il.dll
-MODULES_CONTAINING_C_CODE=
+# DLLs.  We have to hardcode the names of the C code files and the
+# runtime files.
+RUNTIME_DLLS=../runtime/mercury_mcpp.dll ../runtime/mercury_il.dll
+
+MODULES_CONTAINING_C_CODE=	\
 		array 		\
 		benchmarking	\
 		builtin		\
@@ -233,16 +235,18 @@
 		table_builtin	\
 		time
 
-CPP_DLLS = $(MODULES_CONTAINING_C_CODE:%=%__c_code.dll)
+CPP_DLLS=$(MODULES_CONTAINING_C_CODE:%=%__c_code.dll)
 
 ALL_DLLS=$(library.dlls) $(CPP_DLLS) $(RUNTIME_DLLS) 
 
-EMBED_ALL_DLLS=$(foreach file,$(ALL_DLLS),/embed:$(file),$(patsubst %.dll,%,$(file)),Y)
+ALL_DLLS_BASE  = $(ALL_DLLS:%.dll=%)
+EMBED_ALL_DLLS = $(foreach dll_name,$(ALL_DLLS_BASE),$(EMBED_ONE_DLL))
+EMBED_ONE_DLL  = /embed:$(dll_name).dll,$(dll_name),Y
 
 # al is the assembly linker, it will create an assembly that references
 # all the modules (.dll files) in the library and runtime.
 mercury.dll: $(ALL_DLLS)
-	al -out:mercury.dll $(ALL_DLLS)
+	$(MS_AL) -out:mercury.dll $(ALL_DLLS)
 
 # This al command line will create a signed assembly that can be
 # installed into the assembly cache, but then you need to create a key
@@ -274,13 +278,13 @@
 		$(ALL_LDFLAGS) $(ALL_LDLIBS)				\
 		$(SHARED_LIBS)
 
+endif
+
 $(STD_LIB_NAME).init: $(deps_subdir)library.dep
 	for file in $(library.ms); do \
 		grep '^INIT ' $$file; \
 		echo "INIT mercury__`basename $$file .m`__init"; \
 	done > $(STD_LIB_NAME).init
-
-endif
 
 #-----------------------------------------------------------------------------#
 
diff -u library/array.m library/array.m
--- library/array.m
+++ library/array.m
@@ -303,8 +303,6 @@
 :- implementation.
 :- import_module int.
 
-:- type array(T).
-
 /****
 lower bounds other than zero are not supported
 	% array__resize takes an array and new lower and upper bounds.
@@ -396,34 +394,34 @@
     MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(array, array, 1, MR_TYPECTOR_REP_ARRAY)
 
     static int
-    mercury__array____Unify____array_1_0(MR_Word type_info, 
+    __Unify____array_1_0(MR_Word type_info, 
 		MR_Word x, MR_Word y)
     {
-            MR_Runtime::SORRY(""unify for array"");
+            mercury::runtime::Errors::SORRY(""unify for array"");
             return 0;
     }
 
     static void
-    mercury__array____Compare____array_1_0(
+    __Compare____array_1_0(
             MR_Word type_info, MR_Word_Ref result, MR_Word x, MR_Word y)
     {
-            MR_Runtime::SORRY(""compare for array"");
+            mercury::runtime::Errors::SORRY(""compare for array"");
     }
 
     static int
-    mercury__array__do_unify__array_1_0(MR_Word type_info, MR_Box x, MR_Box y)
+    do_unify__array_1_0(MR_Word type_info, MR_Box x, MR_Box y)
     {
-            return mercury__array____Unify____array_1_0(
+            return mercury::array__c_code::__Unify____array_1_0(
                     type_info, 
                     dynamic_cast<MR_Array>(x),
                     dynamic_cast<MR_Array>(y));
     }
 
     static void
-    mercury__array__do_compare__array_1_0(
+    do_compare__array_1_0(
             MR_Word type_info, MR_Word_Ref result, MR_Box x, MR_Box y)
     {
-            mercury__array____Compare____array_1_0(
+            mercury::array__c_code::__Compare____array_1_0(
                     type_info, result, 
                     dynamic_cast<MR_Array>(x),
                     dynamic_cast<MR_Array>(y));
@@ -529,7 +527,7 @@
 :- pragma foreign_code("MC++", 
 		array__init(Size::in, Item::in, Array::array_uo),
 		[will_not_call_mercury, thread_safe], "
-        MR_Runtime::SORRY(""unify for array"");
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 		// XXX still need to do init
 	Array = (MR_Word) System::Array::CreateInstance(Item->GetType(), Size);
 ").
@@ -537,10 +535,11 @@
 :- pragma foreign_code("MC++",
 		array__make_empty_array(Array::array_uo),
 		[will_not_call_mercury, thread_safe], "
-        MR_Runtime::SORRY(""unify for array"");
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 		// XXX this is inefficient.
 	Array = (MR_Word) 
-		System::Array::CreateInstance((new Object)->GetType(), 0);
+		System::Array::CreateInstance(
+			(new System::Object)->GetType(), 0);
 ").
 
 
@@ -562,12 +561,14 @@
 :- pragma foreign_code("MC++",
 		array__min(Array::array_ui, Min::out),
 		[will_not_call_mercury, thread_safe], "
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 	/* Array not used */
 	Min = 0;
 ").
 :- pragma foreign_code("MC++", 
 		array__min(Array::in, Min::out),
 		[will_not_call_mercury, thread_safe], "
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 	/* Array not used */
 	Min = 0;
 ").
@@ -585,11 +586,13 @@
 :- pragma foreign_code("MC++", 
 		array__max(Array::array_ui, Max::out), 
 		[will_not_call_mercury, thread_safe], "
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 	Max = Array->get_Length() - 1;
 ").
 :- pragma foreign_code("MC++",
 		array__max(Array::in, Max::out), 
 		[will_not_call_mercury, thread_safe], "
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 	Max = Array->get_Length() - 1;
 ").
 
@@ -614,11 +617,13 @@
 :- pragma foreign_code("MC++",
 		array__size(Array::array_ui, Max::out),
 		[will_not_call_mercury, thread_safe], "
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 	Max = Array->get_Length() - 1;
 ").
 :- pragma foreign_code("MC++",
 		array__size(Array::in, Max::out),
 		[will_not_call_mercury, thread_safe], "
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 	Max = Array->get_Length() - 1;
 ").
 
@@ -673,11 +678,13 @@
 :- pragma foreign_code("MC++",
 		array__lookup(Array::array_ui, Index::in, Item::out),
 		[will_not_call_mercury, thread_safe], "{
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 	Item = Array->GetValue(Index);
 }").
 :- pragma foreign_code("MC++",
 		array__lookup(Array::in, Index::in, Item::out),
 		[will_not_call_mercury, thread_safe], "{
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 	Item = Array->GetValue(Index);
 }").
 
@@ -704,6 +711,7 @@
 		[will_not_call_mercury, thread_safe], "{
 	Array0->SetValue(Item, Index);	/* destructive update! */
 	Array = Array0;
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
 }").
 
 
@@ -758,7 +766,7 @@
 :- pragma foreign_code("MC++",
 		array__resize(_Array0::array_di, _Size::in, _Item::in,
 		_Array::array_uo), [will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 
@@ -810,7 +818,7 @@
 :- pragma foreign_code("MC++",
 		array__shrink(_Array0::array_di, _Size::in, _Array::array_uo),
 		[will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 
@@ -863,7 +871,7 @@
 		array__copy(Array0::array_ui, Array::array_uo),
 		[will_not_call_mercury, thread_safe], "
 		// XXX need to deep copy it
-        MR_Runtime::SORRY(""copy for array"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	Array = Array0;
 
 ").
@@ -871,7 +879,7 @@
 :- pragma foreign_code("MC++",
 		array__copy(Array0::in, Array::array_uo),
 		[will_not_call_mercury, thread_safe], "
-        MR_Runtime::SORRY(""copy for array"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 		// XXX need to deep copy it
 	Array = Array0;
 ").
diff -u library/benchmarking.m library/benchmarking.m
--- library/benchmarking.m
+++ library/benchmarking.m
@@ -82,12 +82,12 @@
 
 :- pragma foreign_code("MC++", report_stats, will_not_call_mercury,
 "
-	// Do nothing
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", report_full_memory_stats, will_not_call_mercury,
 "
-	// Do nothing
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 %-----------------------------------------------------------------------------%
@@ -621,12 +621,16 @@
 	Time = MR_get_user_cpu_miliseconds();
 ").
 :- pragma foreign_code("MC++",
-	get_user_cpu_miliseconds(Time::out), [will_not_call_mercury],
+	get_user_cpu_miliseconds(_Time::out), [will_not_call_mercury],
 "
 	// This won't return the elapsed time since program start,
 	// as it begins timing after the first call.
 	// For computing time differences it should be fine.
-	Time = (int) (1000 * Diagnostics::Counter::GetElapsed());
+	// Time = (int) (1000 * System::Diagnostics::Counter::GetElapsed());
+	// XXX Can't seem to get this to work -- perhaps Diagnositcs isn't
+	// yet available in Beta 1 of the .NET frameworks.
+
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 /*
@@ -649,12 +653,15 @@
 /*
 ** To prevent the MC++ compiler from optimizing the benchmark code
 ** away, we assign the benchmark output to a volatile static variable.
+** XXX at least, we should do this but it doesn't seem to work.
 */
 :- pragma foreign_code("MC++", 
 	do_nothing(X::in), [will_not_call_mercury, thread_safe],
 "
-	static volatile MR_Word ML_benchmarking_dummy_word;
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
+/*	static volatile MR_Word ML_benchmarking_dummy_word;
 	ML_benchmarking_dummy_word = (MR_Word) X;
+*/
 ").
 
 %-----------------------------------------------------------------------------%
@@ -675,7 +682,7 @@
 :- pragma foreign_code("MC++",
 	new_int_reference(_X::in, _Ref::out), will_not_call_mercury, 
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 
@@ -692,7 +699,7 @@
 ").
 :- pragma foreign_code("MC++",
 	ref_value(_Ref::in, _X::out), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- impure pred update_ref(int_reference::in, T::in) is det.
@@ -703,7 +710,7 @@
 ").
 :- pragma foreign_code("MC++",
 	update_ref(_Ref::in, _X::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 %-----------------------------------------------------------------------------%
diff -u library/builtin.m library/builtin.m
--- library/builtin.m
+++ library/builtin.m
@@ -408,12 +408,11 @@
 
 ").
 
-/*
-
-XXX :- external stops us from using this
+:- pragma foreign_code("MC++", "
 
-:- pragma foreign_code("MC++", compare(Res::uo, X::in, Y::in),
-	[may_call_mercury], "
+static void compare_3_p_0(MR_TypeInfo TypeInfo_for_T, MR_Word_Ref Res, 
+		MR_Box X, MR_Box Y) 
+{
 
         MR_TypeInfo             type_info;
         MR_TypeCtorInfo         type_ctor_info;
@@ -423,101 +422,114 @@
         MR_Box                  ComparePred;
 
         type_info = (MR_TypeInfo) TypeInfo_for_T;
-        type_ctor_info = dynamic_cast<MR_Word> (type_info->GetValue(0));
+        type_ctor_info = dynamic_cast<MR_Word> (type_info->GetValue(
+		MR_TYPEINFO_TYPE_CTOR_INFO_SLOT));
 
         if (type_ctor_info == 0) {
             type_ctor_info = type_info;
         }
 
         if (0) {
-            // XXX code for higher order...
+            // XXX code for higher order still needs to be written...
         } else {
-            arity = mr_convert::ToInt32(type_ctor_info->GetValue(0));
+            arity = mercury::runtime::Convert::ToInt32(
+		type_ctor_info->GetValue(MR_TYPE_CTOR_INFO_ARITY_SLOT));
         }
 
-	
-	ComparePred = type_ctor_info->GetValue(3),
+	ComparePred = type_ctor_info->GetValue(
+		MR_TYPE_CTOR_INFO_COMPARE_PRED_SLOT);
 
         switch(arity) {
 	case 0: 
-		generic::generic_res_call3(
+		mercury::runtime::GenericCall::result_call_4(
 			ComparePred,
-			&Res, X, Y);
+			Res, X, Y);
 	break;
 	case 1:
-		generic::generic_res_call4(
+		mercury::runtime::GenericCall::result_call_5(
 			ComparePred,
 			type_info->GetValue(1), 
-			&Res, X, Y);
+			Res, X, Y);
 	break;
 	case 2:
-		generic::generic_res_call5(
+		mercury::runtime::GenericCall::result_call_6(
 			ComparePred,
 			type_info->GetValue(1), 
 			type_info->GetValue(2), 
-			&Res, X, Y);
+			Res, X, Y);
 	break;
 	case 3:
-		generic::generic_res_call6(
+		mercury::runtime::GenericCall::result_call_7(
 			ComparePred,
 			type_info->GetValue(1), 
 			type_info->GetValue(2), 
 			type_info->GetValue(3), 
-			&Res, X, Y);
+			Res, X, Y);
 	break;
 	case 4:
-		generic::generic_res_call7(
+		mercury::runtime::GenericCall::result_call_8(
 			ComparePred,
 			type_info->GetValue(1), 
 			type_info->GetValue(2), 
 			type_info->GetValue(3), 
 			type_info->GetValue(4), 
-			&Res, X, Y);
+			Res, X, Y);
 	break;
 	case 5:
-		generic::generic_res_call8(
+		mercury::runtime::GenericCall::result_call_9(
 			ComparePred,
 			type_info->GetValue(1), 
 			type_info->GetValue(2), 
 			type_info->GetValue(3), 
 			type_info->GetValue(4), 
 			type_info->GetValue(5), 
-			&Res, X, Y);
+			Res, X, Y);
 	break; 
 	default:
-		MR_Runtime::MR_fatal_error(
+		mercury::runtime::Errors::fatal_error(
 			""compare/3: type arity > 5 not supported"");
 	}
-").
+}
 
-:- pragma foreign_code("MC++", compare(Res::uo, X::ui, Y::ui),
-	[may_call_mercury], "
-	compare_3_p_0(TypeInfo_for_T, &Res, X, Y);
-").
+void compare_3_p_1(MR_TypeInfo TypeInfo_for_T, MR_Word_Ref Res, 
+		MR_Box X, MR_Box Y) 
+{
+	compare_3_p_0(TypeInfo_for_T, Res, X, Y);
+}
 
-:- pragma foreign_code("MC++", compare(Res::uo, X::ui, Y::in),
-	[may_call_mercury], "
-	compare_3_p_0(TypeInfo_for_T, &Res, X, Y);
-").
+void compare_3_p_2(MR_TypeInfo TypeInfo_for_T, MR_Word_Ref Res, 
+		MR_Box X, MR_Box Y) 
+{
+	compare_3_p_0(TypeInfo_for_T, Res, X, Y);
+}
 
-:- pragma foreign_code("MC++", compare(Res::uo, X::in, Y::ui),
-	[may_call_mercury], "
-	compare_3_p_0(TypeInfo_for_T, &Res, X, Y);
-").
+void compare_3_p_3(MR_TypeInfo TypeInfo_for_T, MR_Word_Ref Res, 
+		MR_Box X, MR_Box Y) 
+{
+	compare_3_p_0(TypeInfo_for_T, Res, X, Y);
+}
 
-:- pragma foreign_code("MC++", copy(_X::ui, _Y::uo),
-	[may_call_mercury], "
-	MR_Runtime::SORRY(""foreign code for this function"");
-").
+void copy_2_p_0(MR_TypeInfo TypeInfo_for_T,
+		MR_Box X, MR_Ref(MR_Box) Y) 
+{
+	// XXX this needs to be implemented -- just using Clone() won't work
+	// because it often does shallow copies.
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
+}
+
+void copy_2_p_1(MR_TypeInfo TypeInfo_for_T,
+		MR_Box X, MR_Ref(MR_Box) Y) 
+{
+	copy_2_p_0(TypeInfo_for_T, X, Y);
+}
 
-:- pragma foreign_code("MC++", copy(_X::in, _Y::uo),
-	[may_call_mercury], "
-	MR_Runtime::SORRY(""foreign code for this function"");
 ").
 
-:- pragma foreign_code("MC++", unify(X::in, Y::in),
-	[may_call_mercury], "
+:- pragma foreign_code("MC++", "
+
+static MR_Integer unify_2_p_0(MR_TypeInfo TypeInfo_for_T, MR_Box X, MR_Box Y) 
 {
+	int			SUCCESS_INDICATOR;
         MR_TypeInfo             type_info;
         MR_TypeCtorInfo         type_ctor_info;
         MR_Box                  tmp;
@@ -527,7 +539,8 @@
 	
         type_info = (MR_TypeInfo) TypeInfo_for_T;
 
-        type_ctor_info = dynamic_cast<MR_Word> (type_info->GetValue(0));
+        type_ctor_info = dynamic_cast<MR_Word> (type_info->GetValue(
+		MR_TYPEINFO_TYPE_CTOR_INFO_SLOT));
         if (type_ctor_info == 0) {
             type_ctor_info = type_info;
         }
@@ -536,356 +549,360 @@
         if (0) {
 
         } else {
-            arity = mr_convert::ToInt32(type_ctor_info->GetValue(0));
+            arity = mercury::runtime::Convert::ToInt32(
+		type_ctor_info->GetValue(MR_TYPE_CTOR_INFO_ARITY_SLOT));
         }
 
-	UnifyPred = GetValue(1);
+	UnifyPred = type_ctor_info->GetValue(
+		MR_TYPE_CTOR_INFO_UNIFY_PRED_SLOT);
 
 	switch(arity) {
 	case 0: 
-                SUCCESS_INDICATOR = generic::generic_call2(
-			UnifyPred,
-			X, Y);
+                SUCCESS_INDICATOR = 
+			mercury::runtime::GenericCall::semidet_call_3(
+				UnifyPred,
+				X, Y);
 	break;
 	case 1:
-                SUCCESS_INDICATOR = generic::generic_call3(
-			UnifyPred,
-			type_info->GetValue(1), 
-			X, Y);
+                SUCCESS_INDICATOR = 
+			mercury::runtime::GenericCall::semidet_call_4(
+				UnifyPred,
+				type_info->GetValue(1), 
+				X, Y);
 	break;
 	case 2:
-		SUCCESS_INDICATOR = generic::generic_call4(
-			UnifyPred,
-			type_info->GetValue(1), 
-			type_info->GetValue(2), 
-			X, Y);
+		SUCCESS_INDICATOR = 
+			mercury::runtime::GenericCall::semidet_call_5(
+				UnifyPred,
+				type_info->GetValue(1), 
+				type_info->GetValue(2), 
+				X, Y);
 	break;
 	case 3:
-		SUCCESS_INDICATOR = generic::generic_call5(
-			UnifyPred,
-			type_info->GetValue(1), 
-			type_info->GetValue(2), 
-			type_info->GetValue(3), 
-			X, Y);
+		SUCCESS_INDICATOR =
+			mercury::runtime::GenericCall::semidet_call_6(
+				UnifyPred,
+				type_info->GetValue(1), 
+				type_info->GetValue(2), 
+				type_info->GetValue(3), 
+				X, Y);
 	break;
 	case 4:
-		SUCCESS_INDICATOR = generic::generic_call6(
-			UnifyPred,
-			type_ctor_info->GetValue(1), 
-			type_info->GetValue(1), 
-			type_info->GetValue(2), 
-			type_info->GetValue(3), 
-			type_info->GetValue(4), 
-			X, Y);
+		SUCCESS_INDICATOR =
+			mercury::runtime::GenericCall::semidet_call_7(
+				UnifyPred,
+				type_info->GetValue(1), 
+				type_info->GetValue(2), 
+				type_info->GetValue(3), 
+				type_info->GetValue(4), 
+				X, Y);
 	break;
 	case 5:
-		SUCCESS_INDICATOR = generic::generic_call7(
-			UnifyPred,
-			type_info->GetValue(1), 
-			type_info->GetValue(2), 
-			type_info->GetValue(3), 
-			type_info->GetValue(4), 
-			type_info->GetValue(5), 
-			X, Y);
+		SUCCESS_INDICATOR = 
+			mercury::runtime::GenericCall::semidet_call_8(
+				UnifyPred,
+				type_info->GetValue(1), 
+				type_info->GetValue(2), 
+				type_info->GetValue(3), 
+				type_info->GetValue(4), 
+				type_info->GetValue(5), 
+				X, Y);
 	break;
 	default:
-		MR_Runtime::MR_fatal_error(
+		mercury::runtime::Errors::fatal_error(
 			""unify/2: type arity > 5 not supported"");
 	}
+
+	return SUCCESS_INDICATOR;
 }
 
 ").
 
-*/
-
 :- pragma foreign_code("MC++", "
 	
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, int, 0, MR_TYPECTOR_REP_INT) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, character, 0,
-        MR_TYPECTOR_REP_CHAR) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, string, 0,
-        MR_TYPECTOR_REP_STRING) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, c_pointer, 0,
-        MR_TYPECTOR_REP_C_POINTER) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, void, 0,
-        MR_TYPECTOR_REP_VOID) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, float, 0, 
-       MR_TYPECTOR_REP_FLOAT) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, func, 0,
-        MR_TYPECTOR_REP_PRED) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, pred, 0,
-        MR_TYPECTOR_REP_PRED) 
-
-    static int
-    mercury__builtin____Unify____int_0_0(MR_Integer x, MR_Integer y)
-    {
-            return x == y;
-    }
-
-    static int
-    mercury__builtin____Unify____string_0_0(MR_String x, MR_String y)
-    {
-            return String::Equals(x, y);
-    }
-
-    static int
-    mercury__builtin____Unify____character_0_0(MR_Char x, MR_Char y)
-    {
-            return x == y;
-    }
-
-    static int
-    mercury__builtin____Unify____float_0_0(MR_Float x, MR_Float y)
-    {
-            /* XXX what should this function do when x and y are both NaNs? */
-            return x == y;
-    }
-
-    static int
-    mercury__builtin____Unify____void_0_0(MR_Word x, MR_Word y)
-    {
-            MR_Runtime::MR_fatal_error(
-                ""called unify for type `void'"");
-            return 0;
-    }
-
-    static int
-    mercury__builtin____Unify____c_pointer_0_0(MR_Word x, MR_Word y)
-    {
-            MR_Runtime::MR_fatal_error(
-                ""called unify for type `c_pointer'"");
-            return 0;
-    }
-
-    static int
-    mercury__builtin____Unify____func_0_0(MR_Word x, MR_Word y)
-    {
-            MR_Runtime::MR_fatal_error(
-                ""called unify for `func' type"");
-            return 0;
-    }
-
-    static int
-    mercury__builtin____Unify____pred_0_0(MR_Word x, MR_Word y)
-    {
-            MR_Runtime::MR_fatal_error(
-                ""called unify for `pred' type"");
-            return 0;
-    }
-
-    static void
-    mercury__builtin____Compare____int_0_0(
-        MR_Word_Ref result, MR_Integer x, MR_Integer y)
-    {
-            int r = (x > y ? MR_COMPARE_GREATER :
-                     x == y ? MR_COMPARE_EQUAL :
-                    MR_COMPARE_LESS);
-            MR_newobj(*result, r, 0);
-    }
-
-    static void
-    mercury__builtin____Compare____float_0_0(
-          MR_Word_Ref result, MR_Float x, MR_Float y)
-    {
-          /* XXX what should this function do when x and y are both NaNs? */
-         int r = (x > y ? MR_COMPARE_GREATER :
-                      x == y ? MR_COMPARE_EQUAL :
-                      x < y ? MR_COMPARE_LESS :
-                              (MR_Runtime::MR_fatal_error(
-                                 ""incomparable floats in compare/3""),
-                              MR_COMPARE_EQUAL)); 
-        MR_newobj(*result, r, 0);
-    }
-
-
-    static void
-    mercury__builtin____Compare____string_0_0(MR_Word_Ref result,
-            MR_String x, MR_String y)
-    {
-        int res = String::Compare(x, y);
-        int r = (res > 0 ? MR_COMPARE_GREATER :
-                  res == 0 ? MR_COMPARE_EQUAL :
-                  MR_COMPARE_LESS);
-        MR_newobj(*result, r, 0);
-    }
-
-    static void
-    mercury__builtin____Compare____character_0_0(
-            MR_Word_Ref result, MR_Char x, MR_Char y)
-    {
-            int r = (x > y ? MR_COMPARE_GREATER :
-                      x == y ? MR_COMPARE_EQUAL :
-                      MR_COMPARE_LESS);
-            MR_newobj(*result, r, 0);
-    }
-
-    static void
-    mercury__builtin____Compare____void_0_0(MR_Word_Ref result,
-        MR_Word x, MR_Word y)
-    {
-        MR_Runtime::MR_fatal_error(
-            ""called compare/3 for type `void'"");
-    }
-
-    static void
-    mercury__builtin____Compare____c_pointer_0_0(
-        MR_Word_Ref result, MR_Word x, MR_Word y)
-    {
-        MR_Runtime::MR_fatal_error(
-            ""called compare/3 for type `c_pointer'"");
-    }
-
-    static void
-    mercury__builtin____Compare____func_0_0(MR_Word_Ref result,
-        MR_Word x, MR_Word y)
-    {
-        MR_Runtime::MR_fatal_error(
-            ""called compare/3 for `func' type"");
-    }
-
-    static void
-    mercury__builtin____Compare____pred_0_0(MR_Word_Ref result,
-        MR_Word x, MR_Word y)
-    {
-        MR_Runtime::MR_fatal_error(
-            ""called compare/3 for `pred' type"");
-    }
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, int, 0, MR_TYPECTOR_REP_INT) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, character, 0, MR_TYPECTOR_REP_CHAR) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, string, 0, MR_TYPECTOR_REP_STRING) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, c_pointer, 0,
+	MR_TYPECTOR_REP_C_POINTER) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, void, 0, MR_TYPECTOR_REP_VOID) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, float, 0, MR_TYPECTOR_REP_FLOAT) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, func, 0, MR_TYPECTOR_REP_PRED) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(builtin, pred, 0, MR_TYPECTOR_REP_PRED) 
+
+static int
+__Unify____int_0_0(MR_Integer x, MR_Integer y)
+{
+	return x == y;
+}
+
+static int
+__Unify____string_0_0(MR_String x, MR_String y)
+{
+	return System::String::Equals(x, y);
+}
+
+static int
+__Unify____character_0_0(MR_Char x, MR_Char y)
+{
+	return x == y;
+}
+
+static int
+__Unify____float_0_0(MR_Float x, MR_Float y)
+{
+	/* XXX what should this function do when x and y are both NaNs? */
+	return x == y;
+}
+
+static int
+__Unify____void_0_0(MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called unify for type `void'"");
+	return 0;
+}
+
+static int
+__Unify____c_pointer_0_0(MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called unify for type `c_pointer'"");
+	return 0;
+}
+
+static int
+__Unify____func_0_0(MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called unify for `func' type"");
+	return 0;
+}
+
+static int
+__Unify____pred_0_0(MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called unify for `pred' type"");
+	return 0;
+}
+
+static void
+__Compare____int_0_0(
+	MR_Word_Ref result, MR_Integer x, MR_Integer y)
+{
+	int r = (x > y ? MR_COMPARE_GREATER :
+		x == y ? MR_COMPARE_EQUAL :
+		MR_COMPARE_LESS);
+	MR_newenum(*result, r);
+}
+
+static void
+__Compare____float_0_0(
+	MR_Word_Ref result, MR_Float x, MR_Float y)
+{
+	/* XXX what should this function do when x and y are both NaNs? */
+	int r = (x > y ? MR_COMPARE_GREATER :
+		x == y ? MR_COMPARE_EQUAL :
+		x < y ? MR_COMPARE_LESS :
+		(mercury::runtime::Errors::fatal_error(
+			""incomparable floats in compare/3""),
+			MR_COMPARE_EQUAL)); 
+	MR_newenum(*result, r);
+}
+
+
+static void
+__Compare____string_0_0(MR_Word_Ref result,
+	MR_String x, MR_String y)
+{
+	int res = System::String::Compare(x, y);
+	int r = (res > 0 ? MR_COMPARE_GREATER :
+		res == 0 ? MR_COMPARE_EQUAL :
+		MR_COMPARE_LESS);
+	MR_newenum(*result, r);
+}
+
+static void
+__Compare____character_0_0(
+	MR_Word_Ref result, MR_Char x, MR_Char y)
+{
+	int r = (x > y ? MR_COMPARE_GREATER :
+		x == y ? MR_COMPARE_EQUAL :
+		MR_COMPARE_LESS);
+	MR_newenum(*result, r);
+}
+
+static void
+__Compare____void_0_0(MR_Word_Ref result,
+	MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called compare/3 for type `void'"");
+}
+
+static void
+__Compare____c_pointer_0_0(
+	MR_Word_Ref result, MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called compare/3 for type `c_pointer'"");
+}
+
+static void
+__Compare____func_0_0(MR_Word_Ref result,
+	MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called compare/3 for `func' type"");
+}
+
+static void
+__Compare____pred_0_0(MR_Word_Ref result,
+	MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called compare/3 for `pred' type"");
+}
 
 /*
 ** Unification procedures with the arguments boxed.
 ** These are just wrappers which call the unboxed version.
 */
 
-    static int
-    mercury__builtin__do_unify__int_0_0(MR_Box x, MR_Box y)
-    {
-            return mercury__builtin____Unify____int_0_0(
-                    mr_convert::ToInt32(x), 
-                    mr_convert::ToInt32(y)); 
-    }
-
-    static int
-    mercury__builtin__do_unify__string_0_0(MR_Box x, MR_Box y)
-    {
-            return mercury__builtin____Unify____string_0_0(
-                    dynamic_cast<MR_String>(x), 
-                    dynamic_cast<MR_String>(y));
-    }
-
-    static int
-    mercury__builtin__do_unify__float_0_0(MR_Box x, MR_Box y)
-    {
-            return mercury__builtin____Unify____float_0_0(
-                    mr_convert::ToDouble(x), mr_convert::ToDouble(y));
-    }
-
-    static int
-    mercury__builtin__do_unify__character_0_0(MR_Box x, MR_Box y)
-    {
-            return mercury__builtin____Unify____character_0_0(
-                    mr_convert::ToChar(x),
-                    mr_convert::ToChar(y));
-    }
-
-    static int
-    mercury__builtin__do_unify__void_0_0(MR_Box x, MR_Box y)
-    {
-            MR_Runtime::MR_fatal_error(
-            ""called unify for type `void'"");
-            return 0;
-    }
-
-    static int
-    mercury__builtin__do_unify__c_pointer_0_0(MR_Box x, MR_Box y)
-    {
-            return mercury__builtin____Unify____c_pointer_0_0(
-                dynamic_cast<MR_Word>(x), 
-                dynamic_cast<MR_Word>(y)); 
-    }
-
-    static int
-    mercury__builtin__do_unify__func_0_0(MR_Box x, MR_Box y)
-    {
-            MR_Runtime::MR_fatal_error(
-            ""called unify for `func' type"");
-            return 0;
-    }
-
-    static int
-    mercury__builtin__do_unify__pred_0_0(MR_Box x, MR_Box y)
-    {
-            MR_Runtime::MR_fatal_error(
-            ""called unify for `pred' type"");
-            return 0;
-    }
+static int
+do_unify__int_0_0(MR_Box x, MR_Box y)
+{
+	return mercury::builtin__c_code::__Unify____int_0_0(
+		mercury::runtime::Convert::ToInt32(x), 
+		mercury::runtime::Convert::ToInt32(y)); 
+}
+
+static int
+do_unify__string_0_0(MR_Box x, MR_Box y)
+{
+	return mercury::builtin__c_code::__Unify____string_0_0(
+		dynamic_cast<MR_String>(x), 
+		dynamic_cast<MR_String>(y));
+}
+
+static int
+do_unify__float_0_0(MR_Box x, MR_Box y)
+{
+	return mercury::builtin__c_code::__Unify____float_0_0(
+		mercury::runtime::Convert::ToDouble(x),
+		mercury::runtime::Convert::ToDouble(y));
+}
+
+static int
+do_unify__character_0_0(MR_Box x, MR_Box y)
+{
+	return mercury::builtin__c_code::__Unify____character_0_0(
+		mercury::runtime::Convert::ToChar(x),
+		mercury::runtime::Convert::ToChar(y));
+}
+
+static int
+do_unify__void_0_0(MR_Box x, MR_Box y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called unify for type `void'"");
+	return 0;
+}
+
+static int
+do_unify__c_pointer_0_0(MR_Box x, MR_Box y)
+{
+	return mercury::builtin__c_code::__Unify____c_pointer_0_0(
+		dynamic_cast<MR_Word>(x), 
+		dynamic_cast<MR_Word>(y)); 
+}
+
+static int
+do_unify__func_0_0(MR_Box x, MR_Box y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called unify for `func' type"");
+	return 0;
+}
+
+static int
+do_unify__pred_0_0(MR_Box x, MR_Box y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called unify for `pred' type"");
+	return 0;
+}
 
 /*
 ** Comparison procedures with the arguments boxed.
 ** These are just wrappers which call the unboxed version.
 */
 
-    static void
-    mercury__builtin__do_compare__int_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            mercury__builtin____Compare____int_0_0(result,
-                    mr_convert::ToInt32(x),
-                    mr_convert::ToInt32(y));
-    }
-
-    static void
-    mercury__builtin__do_compare__string_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            mercury__builtin____Compare____string_0_0(result,
-                    dynamic_cast<MR_String>(x),
-                    dynamic_cast<MR_String>(y));
-    }
-
-    static void
-    mercury__builtin__do_compare__float_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            mercury__builtin____Compare____float_0_0(result,
-                    mr_convert::ToDouble(x), mr_convert::ToDouble(y));
-    }
-
-    static void
-    mercury__builtin__do_compare__character_0_0(
-            MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            mercury__builtin____Compare____character_0_0(
-                    result, 
-                    mr_convert::ToChar(x),
-                    mr_convert::ToChar(y));
-    }
-
-    static void
-    mercury__builtin__do_compare__void_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            MR_Runtime::MR_fatal_error(
-            ""called compare/3 for type `void'"");
-    }
-
-    static void
-    mercury__builtin__do_compare__c_pointer_0_0(
-            MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            mercury__builtin____Compare____c_pointer_0_0(
-                    result, 
-                    dynamic_cast<MR_Word>(x),
-                    dynamic_cast<MR_Word>(y));
-    }
-    static void
-    mercury__builtin__do_compare__func_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            MR_Runtime::MR_fatal_error(
-            ""called compare/3 for func type"");
-    }
-
-    static void
-    mercury__builtin__do_compare__pred_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            MR_Runtime::MR_fatal_error(
-            ""called compare/3 for pred type"");
-    }
+static void
+do_compare__int_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::builtin__c_code::__Compare____int_0_0(result,
+		mercury::runtime::Convert::ToInt32(x),
+		mercury::runtime::Convert::ToInt32(y));
+}
+
+static void
+do_compare__string_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::builtin__c_code::__Compare____string_0_0(result,
+		dynamic_cast<MR_String>(x),
+		dynamic_cast<MR_String>(y));
+}
+
+static void
+do_compare__float_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::builtin__c_code::__Compare____float_0_0(result,
+		mercury::runtime::Convert::ToDouble(x),
+		mercury::runtime::Convert::ToDouble(y));
+}
+
+static void
+do_compare__character_0_0(
+	MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::builtin__c_code::__Compare____character_0_0(
+		result, 
+		mercury::runtime::Convert::ToChar(x),
+		mercury::runtime::Convert::ToChar(y));
+}
+
+static void
+do_compare__void_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called compare/3 for type `void'"");
+}
+
+static void
+do_compare__c_pointer_0_0(
+	MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::builtin__c_code::__Compare____c_pointer_0_0(
+		result, 
+		dynamic_cast<MR_Word>(x),
+		dynamic_cast<MR_Word>(y));
+}
+
+static void
+do_compare__func_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called compare/3 for func type"");
+}
+
+static void
+do_compare__pred_0_0(MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::runtime::Errors::fatal_error(
+		""called compare/3 for pred type"");
+}
 
 ").
 
diff -u library/char.m library/char.m
--- library/char.m
+++ library/char.m
@@ -472,7 +472,7 @@
 :- pragma foreign_code("MC++",
 		char__max_char_value(_Max::out),
 		[will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 ").
 
 
diff -u library/exception.m library/exception.m
--- library/exception.m
+++ library/exception.m
@@ -308,51 +308,51 @@
 	get_determinism(_Pred::pred(out) is det,
 			Det::out(bound(det))),
 	will_not_call_mercury,
-	"MR_newobj(Det, ML_DET, 0);"
+	"MR_newenum(Det, ML_DET);"
 ).
 :- pragma foreign_code("MC++",
 	get_determinism(_Pred::pred(out) is semidet,
 			Det::out(bound(semidet))),
 	will_not_call_mercury,
-	"MR_newobj(Det, ML_SEMIDET, 0);"
+	"MR_newenum(Det, ML_SEMIDET);"
 ).
 :- pragma foreign_code("MC++",
 	get_determinism(_Pred::pred(out) is cc_multi,
 			Det::out(bound(cc_multi))),
 	will_not_call_mercury,
-	"MR_newobj(Det, ML_CC_MULTI, 0);"
+	"MR_newenum(Det, ML_CC_MULTI);"
 ).
 :- pragma foreign_code("MC++",
 	get_determinism(_Pred::pred(out) is cc_nondet,
 			Det::out(bound(cc_nondet))),
 	will_not_call_mercury,
-	"MR_newobj(Det, ML_CC_NONDET, 0);"
+	"MR_newenum(Det, ML_CC_NONDET);"
 ).
 :- pragma foreign_code("MC++",
 	get_determinism(_Pred::pred(out) is multi,
 			Det::out(bound(multi))),
 	will_not_call_mercury,
-	"MR_newobj(Det, ML_MULTI, 0);"
+	"MR_newenum(Det, ML_MULTI);"
 ).
 :- pragma foreign_code("MC++",
 	get_determinism(_Pred::pred(out) is nondet,
 			Det::out(bound(nondet))),
 	will_not_call_mercury,
-	"MR_newobj(Det, ML_NONDET, 0);"
+	"MR_newenum(Det, ML_NONDET);"
 ).
 
 :- pragma foreign_code("MC++",
 	get_determinism_2(_Pred::pred(out, di, uo) is det,
 			Det::out(bound(det))),
 	will_not_call_mercury,
-	"MR_newobj(Det, ML_DET, 0);"
+	"MR_newenum(Det, ML_DET);"
 ).
 
 :- pragma foreign_code("MC++",
 	get_determinism_2(_Pred::pred(out, di, uo) is cc_multi,
 			Det::out(bound(cc_multi))),
 	will_not_call_mercury,
-	"MR_newobj(Det, ML_CC_MULTI, 0);"
+	"MR_newenum(Det, ML_CC_MULTI);"
 ).
 
 
diff -u library/float.m library/float.m
--- library/float.m
+++ library/float.m
@@ -384,7 +384,7 @@
 :- pragma foreign_code("MC++", float__ceiling_to_int(X :: in) = (Ceil :: out),
 	[will_not_call_mercury, thread_safe],
 "
-	Ceil = (MR_Integer) Math::Ceil(X);
+	Ceil = (MR_Integer) System::Math::Ceil(X);
 ").
 
 float__ceiling_to_int(X, float__ceiling_to_int(X)).
@@ -399,7 +399,7 @@
 :- pragma foreign_code("MC++", float__floor_to_int(X :: in) = (Floor :: out),
 	[will_not_call_mercury, thread_safe],
 "
-	Floor = (MR_Integer) Math::Floor(X);
+	Floor = (MR_Integer) System::Math::Floor(X);
 ").
 
 float__floor_to_int(X, float__floor_to_int(X)).
@@ -414,7 +414,7 @@
 :- pragma foreign_code("MC++", float__round_to_int(X :: in) = (Round :: out),
 	[will_not_call_mercury, thread_safe],
 "
-	Round = (MR_Integer) Math::Floor(X + 0.5);
+	Round = (MR_Integer) System::Math::Floor(X + 0.5);
 ").
 
 float__round_to_int(X, float__round_to_int(X)).
@@ -537,7 +537,7 @@
 	"Max = ML_FLOAT_MAX;").
 :- pragma foreign_code("MC++", float__max = (Max::out),
 		[will_not_call_mercury, thread_safe],
-	"Max = Double::MaxValue;").
+	"Max = MR_BoxedFloat::MaxValue;").
 
 
 float__max(float__max).
@@ -548,7 +548,7 @@
 	"Min = ML_FLOAT_MIN;").
 :- pragma foreign_code("MC++", float__min = (Min::out),
 		[will_not_call_mercury, thread_safe],
-	"Min = Double::MinValue;").
+	"Min = MR_BoxedFloat::MinValue;").
 
 float__min(float__min).
 
@@ -558,7 +558,7 @@
 	"Eps = ML_FLOAT_EPSILON;").
 :- pragma foreign_code("MC++", float__epsilon = (Eps::out),
 		[will_not_call_mercury, thread_safe],
-	"Eps = Double::Epsilon;").
+	"Eps = MR_BoxedFloat::Epsilon;").
 
 float__epsilon(float__epsilon).
 
@@ -568,7 +568,7 @@
 	"Radix = ML_FLOAT_RADIX;").
 :- pragma foreign_code("MC++", float__radix = (_Radix::out),
 		[will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 float__radix(float__radix).
@@ -579,7 +579,7 @@
 	"MantDig = ML_FLOAT_MANT_DIG;").
 :- pragma foreign_code("MC++", float__mantissa_digits = (_MantDig::out),
 		[will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 float__mantissa_digits(float__mantissa_digits).
@@ -592,7 +592,7 @@
 	"MinExp = ML_FLOAT_MIN_EXP;").
 :- pragma foreign_code("MC++", float__min_exponent = (_MinExp::out),
 		[will_not_call_mercury, thread_safe], "	
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 float__min_exponent(float__min_exponent).
@@ -606,7 +606,7 @@
 
 :- pragma foreign_code("MC++", float__max_exponent = (_MaxExp::out),
 		[will_not_call_mercury, thread_safe], "	
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 
diff -u library/gc.m library/gc.m
--- library/gc.m
+++ library/gc.m
@@ -51,7 +51,7 @@
 #endif
 ").
 :- pragma foreign_code("MC++", garbage_collect, [will_not_call_mercury], "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 %---------------------------------------------------------------------------%
diff -u library/int.m library/int.m
--- library/int.m
+++ library/int.m
@@ -472,6 +472,10 @@
 	#define ML_BITS_PER_INT		(sizeof(MR_Integer) * CHAR_BIT)
 ").
 
+:- pragma foreign_decl("MC++", "
+	#define ML_BITS_PER_INT		32
+").
+
 
 :- pragma foreign_code("C", int__max_int(Max::out),
 		[will_not_call_mercury, thread_safe], "
@@ -511,27 +515,27 @@
 
 :- pragma foreign_code("MC++", int__max_int(Max::out),
 		[will_not_call_mercury, thread_safe], "
-	Max = Int32::MaxValue;
+	Max = System::Int32::MaxValue;
 ").
 
 :- pragma foreign_code("MC++", int__min_int(Min::out),
 		[will_not_call_mercury, thread_safe], "
-	Min = Int32::MinValue;
+	Min = System::Int32::MinValue;
 ").
 
 :- pragma foreign_code("MC++", int__bits_per_int(Bits::out),
 		[will_not_call_mercury, thread_safe], "
-	Bits = 32;
+	Bits = ML_BITS_PER_INT;
 ").
 
 :- pragma foreign_code("MC++", int__quot_bits_per_int(Int::in) = (Div::out),
 		[will_not_call_mercury, thread_safe], "
-	Div = Int / 32;
+	Div = Int / ML_BITS_PER_INT;
 ").
 
 :- pragma foreign_code("MC++", int__times_bits_per_int(Int::in) = (Result::out),
 		[will_not_call_mercury, thread_safe], "
-	Result = Int * 32;
+	Result = Int * ML_BITS_PER_INT;
 ").
 
 
diff -u library/io.m library/io.m
--- library/io.m
+++ library/io.m
@@ -1433,7 +1433,7 @@
 	io__read_line_as_string_2(_File::in, _Res :: out, _RetString::out,
 		IO0::di, IO::uo), [will_not_call_mercury, thread_safe],
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	update_io(IO0, IO);
 ").
 
@@ -1541,7 +1541,7 @@
 :- pragma foreign_code("MC++", io__clear_err(_Stream::in, _IO0::di, _IO::uo),
 		[will_not_call_mercury, thread_safe],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -1580,7 +1580,7 @@
 		_IO0::di, _IO::uo),
 		[will_not_call_mercury, thread_safe],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -1602,7 +1602,7 @@
 	make_err_msg(_Msg0::in, _Msg::out, _IO0::di, _IO::uo),
 		will_not_call_mercury,
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -1652,7 +1652,7 @@
 		_IO0::di, _IO::uo),
 		[will_not_call_mercury, thread_safe],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -1754,7 +1754,7 @@
 	io__alloc_buffer(_Size::in, _Buffer::uo),
 		[will_not_call_mercury, thread_safe, tabled_for_io],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 :- pragma foreign_code("MC++",
@@ -1762,21 +1762,21 @@
 		_NewSize::in, _Buffer::uo),
 	[will_not_call_mercury, thread_safe, tabled_for_io],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 :- pragma foreign_code("MC++", 
 	io__buffer_to_string(_Buffer::di, _Len::in, _Str::uo),
 		[will_not_call_mercury, thread_safe, tabled_for_io],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 :- pragma foreign_code("MC++",
 	io__buffer_to_string(_Buffer::di, _Str::uo),
 		[will_not_call_mercury, thread_safe, tabled_for_io],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 :- pragma foreign_code("MC++",
@@ -1784,7 +1784,7 @@
 		    _Buffer::uo, _Pos::out, _IO0::di, _IO::uo),
 		[will_not_call_mercury, thread_safe, tabled_for_io],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -2945,14 +2945,21 @@
 
 :- pragma foreign_decl("MC++", "
 
+	// XXX we should re-use the same stream writer on a stream, perhaps
+	// we should store it with a stream.
+
 __gc struct MR_MercuryFileStruct {
 public:
-	IO::Stream 	*stream;
+	System::IO::Stream 	*stream;
 	int		line_number;
 	int		id;
 };
 
 typedef __gc struct MR_MercuryFileStruct *MR_MercuryFile;
+
+	// These macros aren't very safe -- they don't enforce
+	// safe casts in anyway.  Make sure you use them for good
+	// and not evil.
 #define ML_DownCast(Cast, Expr) dynamic_cast<Cast>(Expr)
 #define ML_UpCast(Cast, Expr) ((Cast) (Expr))
 
@@ -3013,7 +3020,8 @@
 
 :- pragma foreign_code("MC++", "
 
-static MR_MercuryFile new_mercury_file(IO::Stream *stream, int line_number) {
+static MR_MercuryFile new_mercury_file(System::IO::Stream *stream,
+		int line_number) {
 	MR_MercuryFile mf = new MR_MercuryFileStruct();
 	mf->stream = stream;
 	mf->line_number = line_number;
@@ -3021,22 +3029,28 @@
 	return mf;
 }
 
+	// XXX this will cause problems with GUI programs that have no
+	// consoles.
+
 static MR_MercuryFile mercury_stdin =
-	new_mercury_file(Console::OpenStandardInput(), 1);
+	new_mercury_file(System::Console::OpenStandardInput(), 1);
 static MR_MercuryFile mercury_stdout =
-	new_mercury_file(Console::OpenStandardOutput(), 1);
+	new_mercury_file(System::Console::OpenStandardOutput(), 1);
 static MR_MercuryFile mercury_stderr =
-	new_mercury_file(Console::OpenStandardError(), 1);
+	new_mercury_file(System::Console::OpenStandardError(), 1);
 
 static MR_MercuryFile mercury_stdin_binary =
 	new_mercury_file(0, 1);
 static MR_MercuryFile mercury_stdout_binary =
 	new_mercury_file(0, 1);
 
+	// XXX these should not create extra copies, instead we should
+	// use the mercury_files above.
+
 static MR_MercuryFile mercury_current_text_input =
-	new_mercury_file(Console::OpenStandardInput(), 1);
+	new_mercury_file(System::Console::OpenStandardInput(), 1);
 static MR_MercuryFile mercury_current_text_output =
-	new_mercury_file(Console::OpenStandardOutput(), 1);
+	new_mercury_file(System::Console::OpenStandardOutput(), 1);
 static MR_MercuryFile mercury_current_binary_input =
         new_mercury_file(0, 1);
 static MR_MercuryFile mercury_current_binary_output =
@@ -3068,18 +3082,20 @@
 static mercury_open(MR_String filename, MR_String type)
 {
         MR_MercuryFile mf = new MR_MercuryFileStruct();
-        IO::FileMode fa;
-        IO::Stream *stream;
+        System::IO::FileMode fa;
+        System::IO::Stream *stream;
 
                 // XXX get this right...
         if (type == ""r"") {
-                fa = IO::FileMode::Open;
+                fa = System::IO::FileMode::Open;
         } else if (type == ""w"") {
-                fa = IO::FileMode::Append;
+                fa = System::IO::FileMode::Append;
         } else {
-                fa = IO::FileMode::OpenOrCreate;
+		mercury::runtime::Errors::SORRY(
+			""foreign code for this function"");
+                // fa = System::IO::FileMode::OpenOrCreate;
         }
-        stream = IO::File::Open(filename, fa);
+        stream = System::IO::File::Open(filename, fa);
 
         if (!stream) {
                 return 0;
@@ -3156,7 +3172,8 @@
 static void
 mercury_print_string(MR_MercuryFile mf, MR_String s)
 {
-        IO::StreamWriter *w = new IO::StreamWriter(mf->stream);
+	// XXX we should re-use the same stream writer...
+        System::IO::StreamWriter *w = new System::IO::StreamWriter(mf->stream);
         w->Write(s);
         w->Flush();
         for (int i = 0; i < s->Length; i++) {
@@ -3200,7 +3217,8 @@
 static void
 mercury_print_binary_string(MR_MercuryFile mf, MR_String s)
 {
-        IO::StreamWriter *w = new IO::StreamWriter(mf->stream);
+	// XXX we should re-use the same stream writer...
+        System::IO::StreamWriter *w = new System::IO::StreamWriter(mf->stream);
         w->Write(s);
         w->Flush();
 }
@@ -3384,7 +3402,7 @@
             mf != mercury_stderr)
         {
                 mf->stream->Close();
-                mf->stream = 0;
+                mf->stream = NULL;
         }
 }
 
@@ -3457,14 +3475,14 @@
 :- pragma foreign_code("MC++", 
 	io__putback_char(_File::in, _Character::in, IO0::di, IO::uo),
 		may_call_mercury, "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	update_io(IO0, IO);
 }").
 
 :- pragma foreign_code("MC++",
 	io__putback_byte(_File::in, _Character::in, IO0::di, IO::uo),
 		may_call_mercury, "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	update_io(IO0, IO);
 }").
 
@@ -3565,9 +3583,9 @@
 	io__write_char(Character::in, IO0::di, IO::uo),
 		[may_call_mercury, thread_safe, tabled_for_io],
 "
-	IO::StreamWriter *w = new IO::StreamWriter(
+	System::IO::StreamWriter *w = new System::IO::StreamWriter(
 		mercury_current_text_output->stream);
-	w->Write(Val.ToString());
+	w->Write(Character);
 	w->Flush();
 	if (Character == '\\n') {
 		mercury_current_text_output->line_number++;
@@ -3579,10 +3597,7 @@
 	io__write_int(Val::in, IO0::di, IO::uo),
 		[may_call_mercury, thread_safe, tabled_for_io],
 "
-	IO::StreamWriter *w = new IO::StreamWriter(
-		mercury_current_text_output->stream);
-	w->Write(Val.ToString());
-	w->Flush();
+	mercury_print_string(mercury_current_text_output, Val.ToString());
 	update_io(IO0, IO);
 ").
 
@@ -3590,10 +3605,7 @@
 	io__write_float(Val::in, IO0::di, IO::uo),
 		[may_call_mercury, thread_safe, tabled_for_io],
 "
-	IO::StreamWriter *w = new IO::StreamWriter(
-		mercury_current_text_output->stream);
-	w->Write(Val.ToString());
-	w->Flush();
+	mercury_print_string(mercury_current_text_output, Val.ToString());
 	update_io(IO0, IO);
 ").
 
@@ -3601,7 +3613,9 @@
 	io__write_byte(Byte::in, _IO0::di, _IO::uo),
 		[may_call_mercury, thread_safe, tabled_for_io],
 "
-	IO::StreamWriter *w = new IO::StreamWriter(
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
+		// XXX something like this...
+	System::IO::StreamWriter *w = new System::IO::StreamWriter(
 		mercury_current_text_output->stream);
 	w->Write(Byte.ToString());
 	w->Flush();
@@ -3688,7 +3702,7 @@
 		IO0::di, IO::uo),
 		[will_not_call_mercury, thread_safe, tabled_for_io],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	IO = IO0;
 }").
 
@@ -3697,7 +3711,7 @@
 		IO0::di, IO::uo),
 		[will_not_call_mercury, thread_safe, tabled_for_io],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	IO = IO0;
 }").
 
@@ -3798,7 +3812,7 @@
 "{
 	MR_MercuryFile stream = ML_DownCast(MR_MercuryFile, 
 		MR_word_to_c_pointer(Stream));
-	IO::StreamWriter *w = new IO::StreamWriter(
+	System::IO::StreamWriter *w = new System::IO::StreamWriter(
 		mercury_current_binary_output->stream);
 	w->Write(Message);
 	w->Flush();
@@ -3811,7 +3825,7 @@
 "{
 	MR_MercuryFile stream = ML_DownCast(MR_MercuryFile, 
 		MR_word_to_c_pointer(Stream));
-	IO::StreamWriter *w = new IO::StreamWriter(
+	System::IO::StreamWriter *w = new System::IO::StreamWriter(
 		mercury_current_binary_output->stream);
 	w->Write(Character);
 	w->Flush();
@@ -3824,7 +3838,7 @@
 "{
 	MR_MercuryFile stream = ML_DownCast(MR_MercuryFile, 
 		MR_word_to_c_pointer(Stream));
-	IO::StreamWriter *w = new IO::StreamWriter(
+	System::IO::StreamWriter *w = new System::IO::StreamWriter(
 		mercury_current_binary_output->stream);
 	w->Write(Val.ToString());
 	w->Flush();
@@ -3837,7 +3851,7 @@
 "{
 	MR_MercuryFile stream = ML_DownCast(MR_MercuryFile, 
 		MR_word_to_c_pointer(Stream));
-	IO::StreamWriter *w = new IO::StreamWriter(
+	System::IO::StreamWriter *w = new System::IO::StreamWriter(
 		mercury_current_binary_output->stream);
 	w->Write(Val.ToString());
 	w->Flush();
@@ -3848,9 +3862,11 @@
 	io__write_byte(Stream::in, Byte::in, IO0::di, IO::uo),
 		[may_call_mercury, thread_safe, tabled_for_io],
 "{
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
+		// something like this...
 	MR_MercuryFile stream = ML_DownCast(MR_MercuryFile, 
 		MR_word_to_c_pointer(Stream));
-	IO::StreamWriter *w = new IO::StreamWriter(
+	System::IO::StreamWriter *w = new System::IO::StreamWriter(
 		mercury_current_binary_output->stream);
 	w->Write(Byte.ToString());
 	w->Flush();
@@ -3878,10 +3894,12 @@
 }").
 
 :- pragma foreign_code("MC++",
-	io__flush_binary_output(_Stream::in, IO0::di, IO::uo),
+	io__flush_binary_output(Stream::in, IO0::di, IO::uo),
 		[may_call_mercury, thread_safe, tabled_for_io],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	MR_MercuryFile stream = ML_DownCast(MR_MercuryFile, 
+		MR_word_to_c_pointer(Stream));
+	stream->stream->Flush();
 	update_io(IO0, IO);
 }").
 
@@ -4449,14 +4467,14 @@
 :- pragma foreign_code("MC++",
 	io__progname(_DefaultProgname::in, _PrognameOut::out, IO0::di, IO::uo),
 		[will_not_call_mercury, tabled_for_io, thread_safe], "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	update_io(IO0, IO);
 ").
 
 :- pragma foreign_code("MC++",
 	io__command_line_arguments(Args::out, IO0::di, IO::uo),
 		[will_not_call_mercury, tabled_for_io, thread_safe], "
-	MR_String arg_vector __gc[] = Environment::GetCommandLineArgs();
+	MR_String arg_vector __gc[] = System::Environment::GetCommandLineArgs();
 	int i = arg_vector->Length;
 	MR_list_nil(Args);
 		/* We don't get the 0th argument: it is the executable name */
@@ -4491,9 +4509,9 @@
 	MR_String commandstr = Command->Substring(index);
 	MR_String argstr = Command->Remove(0, index);
 		// XXX	This seems to be missing...
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 //	Diagnostics::Process::Start(commandstr, argstr);
-	Status = 0;
+	Status = NULL;
 	update_io(IO0, IO);
 ").
 
@@ -4518,14 +4536,15 @@
 :- pragma foreign_code("MC++", io__getenv(Var::in, Value::out),
 		[will_not_call_mercury, tabled_for_io],
 "{
-	Value = Environment::GetEnvironmentVariable(Var);
+	Value = System::Environment::GetEnvironmentVariable(Var);
 	SUCCESS_INDICATOR = (Value != 0);
 }").
 
 :- pragma foreign_code("MC++", io__putenv(_VarAndValue::in),
 		[will_not_call_mercury, tabled_for_io],
 "
-	MR_Runtime::SORRY(""No SetEnvironmentVariable method appears to be available."");
+	mercury::runtime::Errors::SORRY(
+		""No SetEnvironmentVariable method appears to be available."");
 	SUCCESS_INDICATOR = 0;
 ").
 
@@ -4651,7 +4670,7 @@
 		_Error::out, _ErrorMessage::out, IO0::di, IO::uo),
 		[will_not_call_mercury, thread_safe],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	update_io(IO0, IO);
 }").
 
@@ -4729,7 +4748,7 @@
 		IO0::di, IO::uo),
 		[will_not_call_mercury, tabled_for_io, thread_safe],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	System::IO::File::Delete(FileName);
 	RetVal = 0;
 	RetStr = """";
@@ -4768,7 +4787,7 @@
 			_RetVal::out, _RetStr::out, IO0::di, IO::uo),
 		[will_not_call_mercury, tabled_for_io, thread_safe],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	update_io(IO0, IO);
 }").
 
diff -u library/library.m library/library.m
--- library/library.m
+++ library/library.m
@@ -67,8 +67,9 @@
 :- pragma foreign_code("MC++",
 	library__version(Version::out), will_not_call_mercury,
 "
-	Version = String::Concat(MR_VERSION,
-		"", configured for "", MR_FULLARCH);
+	// XXX we should use string literals with an S at the start
+	// so this code uses just managed types.
+	Version = MR_VERSION "", configured for "", MR_FULLARCH;
 ").
 
 %---------------------------------------------------------------------------%
diff -u library/math.m library/math.m
--- library/math.m
+++ library/math.m
@@ -230,6 +230,7 @@
 :- pragma foreign_decl("MC++", "
 
 	// This is not defined in the .NET Frameworks.
+	// For pi and e we use the constants defined in System::Math.
 
 	#define	ML_FLOAT_LN2		0.69314718055994530941
 ").
@@ -266,7 +267,7 @@
 static void
 ML_math_domain_error(MR_String where)
 {
-	throw new mercury_exception(where);
+	throw new mercury::runtime::Exception(where);
 }
 
 "). % end pragma foreign_code
@@ -281,7 +282,7 @@
 ").
 :- pragma foreign_code("MC++", 
 	math__pi = (Pi::out), [will_not_call_mercury, thread_safe],"
-	Pi = Math::PI;
+	Pi = System::Math::PI;
 ").
 
 	% Base of natural logarithms
@@ -291,7 +292,7 @@
 ").
 :- pragma foreign_code("MC++", 
 	math__e = (E::out), [will_not_call_mercury, thread_safe],"
-	E = Math::E;
+	E = System::Math::E;
 ").
 
 %
@@ -306,7 +307,7 @@
 :- pragma foreign_code("MC++", 
 	math__ceiling(Num::in) = (Ceil::out),
 		[will_not_call_mercury, thread_safe],"
-	Ceil = Math::Ceil(Num);
+	Ceil = System::Math::Ceil(Num);
 ").
 
 %
@@ -321,7 +322,7 @@
 :- pragma foreign_code("MC++", 
 	math__floor(Num::in) = (Floor::out),
 		[will_not_call_mercury, thread_safe],"
-	Floor = Math::Floor(Num);
+	Floor = System::Math::Floor(Num);
 ").
 
 %
@@ -337,9 +338,9 @@
 :- pragma foreign_code("MC++", 
 	math__round(Num::in) = (Rounded::out),
 		[will_not_call_mercury, thread_safe],"
-	// XXX the semantics of Math::Round() are not the same as ours.
+	// XXX the semantics of System::Math::Round() are not the same as ours.
 	// Unfortunately they are better (round to nearest even number).
-	Rounded = Math::Floor(Num+0.5);
+	Rounded = System::Math::Floor(Num+0.5);
 ").
 
 %
@@ -359,9 +360,9 @@
 	math__truncate(X::in) = (Trunc::out),
 		[will_not_call_mercury, thread_safe],"
 	if (X < 0.0) {
-		Trunc = Math::Ceil(X);
+		Trunc = System::Math::Ceil(X);
 	} else {
-		Trunc = Math::Floor(X);
+		Trunc = System::Math::Floor(X);
 	}
 ").
 
@@ -388,7 +389,7 @@
 		ML_math_domain_error(""math__sqrt"");
 	}
 #endif
-	SquareRoot = Math::Sqrt(X);
+	SquareRoot = System::Math::Sqrt(X);
 ").
 
 
@@ -474,10 +475,10 @@
 		}
 		Res = 0.0;
 	} else {
-		Res = Math::Pow(X, Y);
+		Res = System::Math::Pow(X, Y);
 	}
 #else
-	Res = Math::Pow(X, Y);
+	Res = System::Math::Pow(X, Y);
 #endif
 ").
 
@@ -492,7 +493,7 @@
 ").
 :- pragma foreign_code("MC++", math__exp(X::in) = (Exp::out),
 		[will_not_call_mercury, thread_safe],"
-	Exp = Math::Exp(X);
+	Exp = System::Math::Exp(X);
 ").
 
 %
@@ -518,7 +519,7 @@
 		ML_math_domain_error(""math__ln"");
 	}
 #endif
-	Log = Math::Log(X);
+	Log = System::Math::Log(X);
 ").
 
 %
@@ -544,7 +545,7 @@
 		ML_math_domain_error(""math__log10"");
 	}
 #endif
-	Log10 = Math::Log10(X);
+	Log10 = System::Math::Log10(X);
 ").
 
 %
@@ -570,7 +571,7 @@
 		ML_math_domain_error(""math__log2"");
 	}
 #endif
-	Log2 = Math::Log(X) / ML_FLOAT_LN2;
+	Log2 = System::Math::Log(X) / ML_FLOAT_LN2;
 ").
 
 %
@@ -604,7 +605,7 @@
 		ML_math_domain_error(""math__log"");
 	}
 #endif
-	Log = Math::Log(X,B);
+	Log = System::Math::Log(X,B);
 ").
 
 
@@ -617,7 +618,7 @@
 ").
 :- pragma foreign_code("MC++", math__sin(X::in) = (Sin::out),
 		[will_not_call_mercury, thread_safe],"
-	Sin = Math::Sin(X);
+	Sin = System::Math::Sin(X);
 ").
 
 
@@ -630,7 +631,7 @@
 ").
 :- pragma foreign_code("MC++", math__cos(X::in) = (Cos::out),
 		[will_not_call_mercury, thread_safe],"
-	Cos = Math::Cos(X);
+	Cos = System::Math::Cos(X);
 ").
 
 %
@@ -642,7 +643,7 @@
 ").
 :- pragma foreign_code("MC++", math__tan(X::in) = (Tan::out),
 		[will_not_call_mercury, thread_safe],"
-	Tan = Math::Tan(X);
+	Tan = System::Math::Tan(X);
 ").
 
 %
@@ -668,7 +669,7 @@
 		ML_math_domain_error(""math__asin"");
 	}
 #endif
-	ASin = Math::Asin(X);
+	ASin = System::Math::Asin(X);
 ").
 
 %
@@ -694,7 +695,7 @@
 		ML_math_domain_error(""math__acos"");
 	}
 #endif
-	ACos = Math::Acos(X);
+	ACos = System::Math::Acos(X);
 ").
 
 
@@ -708,7 +709,7 @@
 ").
 :- pragma foreign_code("MC++", math__atan(X::in) = (ATan::out),
 		[will_not_call_mercury, thread_safe],"
-	ATan = Math::Atan(X);
+	ATan = System::Math::Atan(X);
 ").
 
 %
@@ -721,7 +722,7 @@
 ").
 :- pragma foreign_code("MC++", math__atan2(Y::in, X::in) = (ATan2::out), 
 		[will_not_call_mercury, thread_safe], "
-	ATan2 = Math::Atan2(Y, X);
+	ATan2 = System::Math::Atan2(Y, X);
 ").
 
 %
@@ -734,7 +735,7 @@
 ").
 :- pragma foreign_code("MC++", math__sinh(X::in) = (Sinh::out),
 		[will_not_call_mercury, thread_safe],"
-	Sinh = Math::Sinh(X);
+	Sinh = System::Math::Sinh(X);
 ").
 
 %
@@ -747,7 +748,7 @@
 ").
 :- pragma foreign_code("MC++", math__cosh(X::in) = (Cosh::out),
 		[will_not_call_mercury, thread_safe],"
-	Cosh = Math::Cosh(X);
+	Cosh = System::Math::Cosh(X);
 ").
 
 %
@@ -760,7 +761,7 @@
 ").
 :- pragma foreign_code("MC++", math__tanh(X::in) = (Tanh::out),
 		[will_not_call_mercury, thread_safe],"
-	Tanh = Math::Tanh(X);
+	Tanh = System::Math::Tanh(X);
 ").
 
 %---------------------------------------------------------------------------%
diff -u library/private_builtin.m library/private_builtin.m
--- library/private_builtin.m
+++ library/private_builtin.m
@@ -168,7 +168,7 @@
 :- pragma foreign_code("MC++", builtin_strcmp(Res::out, S1::in, S2::in),
 	[will_not_call_mercury, thread_safe],
 "
-	Res = String::Compare(S1, S2);
+	Res = System::String::Compare(S1, S2);
 ").
 	
 
@@ -447,27 +447,27 @@
 static MR_TypeInfo MR_typeclass_info_type_info(
 	MR_TypeClassInfo tcinfo, int index)
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	return 0;
 }
 static MR_TypeInfo MR_typeclass_info_unconstrained_type_info(
 	MR_TypeClassInfo tcinfo, int index) 
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	return 0;
 }
 
 static MR_TypeClassInfo MR_typeclass_info_superclass_info(
 	MR_TypeClassInfo tcinfo, int index)
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	return 0;
 }
 
 static MR_TypeClassInfo MR_typeclass_info_arg_typeclass_info(
 	MR_TypeClassInfo tcinfo, int index) 
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	return 0;
 }
 
@@ -475,14 +475,14 @@
 
 :- pragma foreign_code("MC++", "
 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(private_builtin, type_ctor_info, 1,
-		MR_TYPECTOR_REP_TYPEINFO) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(private_builtin, type_info, 1,
-		MR_TYPECTOR_REP_TYPEINFO) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(private_builtin, base_typeclass_info, 1,
-		MR_TYPECTOR_REP_TYPECLASSINFO) 
-    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(private_builtin, typeclass_info, 1,
-		MR_TYPECTOR_REP_TYPECLASSINFO) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(private_builtin, type_ctor_info, 1,
+	MR_TYPECTOR_REP_TYPEINFO) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(private_builtin, type_info, 1,
+	MR_TYPECTOR_REP_TYPEINFO) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(private_builtin, base_typeclass_info, 1,
+	MR_TYPECTOR_REP_TYPECLASSINFO) 
+MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(private_builtin, typeclass_info, 1,
+	MR_TYPECTOR_REP_TYPECLASSINFO) 
 
 	// XXX These static constants are duplicated both here and in
 	// mercury_cpp.cpp.
@@ -491,186 +491,188 @@
 	// make the dependencies simple) whereas the compiler generates
 	// references to the ones here. 
 
-    static int MR_TYPECTOR_REP_ENUM 			= MR_TYPECTOR_REP_ENUM_val;
-    static int MR_TYPECTOR_REP_ENUM_USEREQ 		= MR_TYPECTOR_REP_ENUM_USEREQ_val;
-    static int MR_TYPECTOR_REP_DU				= MR_TYPECTOR_REP_DU_val;
-    static int MR_TYPECTOR_REP_DU_USEREQ		= 3;
-    static int MR_TYPECTOR_REP_NOTAG			= 4;
-    static int MR_TYPECTOR_REP_NOTAG_USEREQ		= 5;
-    static int MR_TYPECTOR_REP_EQUIV			= 6;
-    static int MR_TYPECTOR_REP_EQUIV_VAR		= 7;
-    static int MR_TYPECTOR_REP_INT		    	= 8;
-    static int MR_TYPECTOR_REP_CHAR		    	= 9;
-    static int MR_TYPECTOR_REP_FLOAT			=10;
-    static int MR_TYPECTOR_REP_STRING			=11;
-    static int MR_TYPECTOR_REP_PRED		    	=12;
-    static int MR_TYPECTOR_REP_UNIV		    	=13;
-    static int MR_TYPECTOR_REP_VOID		    	=14;
-    static int MR_TYPECTOR_REP_C_POINTER		=15;
-    static int MR_TYPECTOR_REP_TYPEINFO			=16;
-    static int MR_TYPECTOR_REP_TYPECLASSINFO	=17;
-    static int MR_TYPECTOR_REP_ARRAY			=18;
-    static int MR_TYPECTOR_REP_SUCCIP			=19;
-    static int MR_TYPECTOR_REP_HP				=20;
-    static int MR_TYPECTOR_REP_CURFR			=21;
-    static int MR_TYPECTOR_REP_MAXFR			=22;
-    static int MR_TYPECTOR_REP_REDOFR			=23;
-    static int MR_TYPECTOR_REP_REDOIP			=24;
-    static int MR_TYPECTOR_REP_TRAIL_PTR		=25;
-    static int MR_TYPECTOR_REP_TICKET			=26;
-    static int MR_TYPECTOR_REP_NOTAG_GROUND		=27;
-    static int MR_TYPECTOR_REP_NOTAG_GROUND_USEREQ	=28;
-    static int MR_TYPECTOR_REP_EQUIV_GROUND		=29;
-
-    static int MR_SECTAG_NONE				= 0;
-    static int MR_SECTAG_LOCAL				= 1;
-    static int MR_SECTAG_REMOTE				= 2;
-
-
-    static int
-    mercury__private_builtin____Unify____type_info_1_0(
-            MR_Word type_info, MR_Word x, MR_Word y)
-    {
-            MR_Runtime::SORRY(""unify for type_info"");
-            return 0;
-    }
-
-    static int
-    mercury__private_builtin____Unify____typeclass_info_1_0(
-            MR_Word type_info, MR_Word x, MR_Word y)
-    {
-            MR_Runtime::SORRY(""unify for typeclass_info"");
-            return 0;
-    }
-
-    static int
-    mercury__private_builtin____Unify____base_typeclass_info_1_0(
-            MR_Word type_info, MR_Word x, MR_Word y)
-    {
-            MR_Runtime::SORRY(""unify for base_typeclass_info"");
-            return 0;
-    }
-
-    static int
-    mercury__private_builtin____Unify____type_ctor_info_1_0(
-            MR_Word type_info, MR_Word x, MR_Word y)
-    {
-            MR_Runtime::SORRY(""unify for type_ctor_info"");
-            return 0;
-    }
-
-    static void
-    mercury__private_builtin____Compare____type_ctor_info_1_0(
-        MR_Word type_info, MR_Word_Ref result, MR_Word x, MR_Word y)
-    {
-        MR_Runtime::SORRY(""compare for type_ctor_info"");
-    }
-
-    static void
-    mercury__private_builtin____Compare____type_info_1_0(
-        MR_Word type_info, MR_Word_Ref result, MR_Word x, MR_Word y)
-    {
-        MR_Runtime::SORRY(""compare for type_info"");
-    }
-
-    static void
-    mercury__private_builtin____Compare____typeclass_info_1_0(
-        MR_Word type_info, MR_Word_Ref result, MR_Word x, MR_Word y)
-    {
-        MR_Runtime::SORRY(""compare for typeclass_info"");
-    }
-
-    static void
-    mercury__private_builtin____Compare____base_typeclass_info_1_0(
-        MR_Word type_info, MR_Word_Ref result, MR_Word x, MR_Word y)
-    {
-        MR_Runtime::SORRY(""compare for base_typeclass_info"");
-    }
-
-    static int
-    mercury__private_builtin__do_unify__type_ctor_info_1_0(
-            MR_Word type_info, MR_Box x, MR_Box y)
-    {
-            return mercury__private_builtin____Unify____type_ctor_info_1_0(
-                    type_info, 
-                    dynamic_cast<MR_Word>(x),
-                    dynamic_cast<MR_Word>(y));
-    }
-
-    static int
-    mercury__private_builtin__do_unify__type_info_1_0(
-            MR_Word type_info, MR_Box x, MR_Box y)
-    {
-            return mercury__private_builtin____Unify____type_info_1_0(
-                    type_info,
-                    dynamic_cast<MR_Word>(x),
-                    dynamic_cast<MR_Word>(y));
-    }
-
-    static int
-    mercury__private_builtin__do_unify__typeclass_info_1_0(
-            MR_Word type_info, MR_Box x, MR_Box y)
-    {
-            return mercury__private_builtin____Unify____typeclass_info_1_0(
-                    type_info, 
-                    dynamic_cast<MR_Word>(x),
-                    dynamic_cast<MR_Word>(y));
-    }
-
-    static int
-    mercury__private_builtin__do_unify__base_typeclass_info_1_0(
-            MR_Word type_info, MR_Box x, MR_Box y)
-    {
-            return mercury__private_builtin____Unify____base_typeclass_info_1_0(
-                    type_info,
-                    dynamic_cast<MR_Word>(x),
-                    dynamic_cast<MR_Word>(y));
-    }
-
-    static void
-    mercury__private_builtin__do_compare__type_ctor_info_1_0(
-            MR_Word type_info, MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            mercury__private_builtin____Compare____type_ctor_info_1_0(
-                    type_info, result, 
-                    dynamic_cast<MR_Word>(x),
-                    dynamic_cast<MR_Word>(y));
-    }
-
-    static void
-    mercury__private_builtin__do_compare__type_info_1_0(
-            MR_Word type_info, MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            mercury__private_builtin____Compare____type_info_1_0(
-                    type_info, result,
-                    dynamic_cast<MR_Word>(x),
-                    dynamic_cast<MR_Word>(y));
-    }
-
-    static void
-    mercury__private_builtin__do_compare__typeclass_info_1_0(
-            MR_Word type_info, MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            mercury__private_builtin____Compare____typeclass_info_1_0(
-                    type_info, result,
-                    dynamic_cast<MR_Word>(x),
-                    dynamic_cast<MR_Word>(y));
-    }
-
-    static void
-    mercury__private_builtin__do_compare__base_typeclass_info_1_0(
-            MR_Word type_info, MR_Word_Ref result, MR_Box x, MR_Box y)
-    {
-            mercury__private_builtin____Compare____base_typeclass_info_1_0(
-                    type_info, result,
-                    dynamic_cast<MR_Word>(x),
-                    dynamic_cast<MR_Word>(y));
-    }
-
-    static void init_runtime(void)
-    {
-        mercury::init::init_runtime();
-    }
+static int MR_TYPECTOR_REP_ENUM 			= MR_TYPECTOR_REP_ENUM_val;
+static int MR_TYPECTOR_REP_ENUM_USEREQ 		= MR_TYPECTOR_REP_ENUM_USEREQ_val;
+static int MR_TYPECTOR_REP_DU				= MR_TYPECTOR_REP_DU_val;
+static int MR_TYPECTOR_REP_DU_USEREQ		= 3;
+static int MR_TYPECTOR_REP_NOTAG			= 4;
+static int MR_TYPECTOR_REP_NOTAG_USEREQ		= 5;
+static int MR_TYPECTOR_REP_EQUIV			= 6;
+static int MR_TYPECTOR_REP_EQUIV_VAR		= 7;
+static int MR_TYPECTOR_REP_INT		    	= 8;
+static int MR_TYPECTOR_REP_CHAR		    	= 9;
+static int MR_TYPECTOR_REP_FLOAT			=10;
+static int MR_TYPECTOR_REP_STRING			=11;
+static int MR_TYPECTOR_REP_PRED		    	=12;
+static int MR_TYPECTOR_REP_UNIV		    	=13;
+static int MR_TYPECTOR_REP_VOID		    	=14;
+static int MR_TYPECTOR_REP_C_POINTER		=15;
+static int MR_TYPECTOR_REP_TYPEINFO			=16;
+static int MR_TYPECTOR_REP_TYPECLASSINFO	=17;
+static int MR_TYPECTOR_REP_ARRAY			=18;
+static int MR_TYPECTOR_REP_SUCCIP			=19;
+static int MR_TYPECTOR_REP_HP				=20;
+static int MR_TYPECTOR_REP_CURFR			=21;
+static int MR_TYPECTOR_REP_MAXFR			=22;
+static int MR_TYPECTOR_REP_REDOFR			=23;
+static int MR_TYPECTOR_REP_REDOIP			=24;
+static int MR_TYPECTOR_REP_TRAIL_PTR		=25;
+static int MR_TYPECTOR_REP_TICKET			=26;
+static int MR_TYPECTOR_REP_NOTAG_GROUND		=27;
+static int MR_TYPECTOR_REP_NOTAG_GROUND_USEREQ	=28;
+static int MR_TYPECTOR_REP_EQUIV_GROUND		=29;
+
+static int MR_SECTAG_NONE				= 0;
+static int MR_SECTAG_LOCAL				= 1;
+static int MR_SECTAG_REMOTE				= 2;
+
+
+static int
+__Unify____type_info_1_0(
+	MR_Word type_info, MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::SORRY(""unify for type_info"");
+	return 0;
+}
+
+static int
+__Unify____typeclass_info_1_0(
+	MR_Word type_info, MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::SORRY(""unify for typeclass_info"");
+	return 0;
+}
+
+static int
+__Unify____base_typeclass_info_1_0(
+	MR_Word type_info, MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::SORRY(""unify for base_typeclass_info"");
+	return 0;
+}
+
+static int
+__Unify____type_ctor_info_1_0(
+	MR_Word type_info, MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::SORRY(""unify for type_ctor_info"");
+	return 0;
+}
+
+static void
+__Compare____type_ctor_info_1_0(
+	MR_Word type_info, MR_Word_Ref result, MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::SORRY(""compare for type_ctor_info"");
+}
+
+static void
+__Compare____type_info_1_0(
+	MR_Word type_info, MR_Word_Ref result, MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::SORRY(""compare for type_info"");
+}
+
+static void
+__Compare____typeclass_info_1_0(
+	MR_Word type_info, MR_Word_Ref result, MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::SORRY(""compare for typeclass_info"");
+}
+
+static void
+__Compare____base_typeclass_info_1_0(
+	MR_Word type_info, MR_Word_Ref result, MR_Word x, MR_Word y)
+{
+	mercury::runtime::Errors::SORRY(""compare for base_typeclass_info"");
+}
+
+static int
+do_unify__type_ctor_info_1_0(
+	MR_Word type_info, MR_Box x, MR_Box y)
+{
+	return mercury::private_builtin__c_code::__Unify____type_ctor_info_1_0(
+		type_info, 
+		dynamic_cast<MR_Word>(x),
+		dynamic_cast<MR_Word>(y));
+}
+
+static int
+do_unify__type_info_1_0(
+	MR_Word type_info, MR_Box x, MR_Box y)
+{
+	return mercury::private_builtin__c_code::__Unify____type_info_1_0(
+		type_info,
+		dynamic_cast<MR_Word>(x),
+		dynamic_cast<MR_Word>(y));
+}
+
+static int
+do_unify__typeclass_info_1_0(
+	MR_Word type_info, MR_Box x, MR_Box y)
+{
+	return mercury::private_builtin__c_code::__Unify____typeclass_info_1_0(
+		type_info, 
+		dynamic_cast<MR_Word>(x),
+		dynamic_cast<MR_Word>(y));
+}
+
+static int
+do_unify__base_typeclass_info_1_0(
+	MR_Word type_info, MR_Box x, MR_Box y)
+{
+	return
+	mercury::private_builtin__c_code::__Unify____base_typeclass_info_1_0(
+		type_info,
+		dynamic_cast<MR_Word>(x),
+		dynamic_cast<MR_Word>(y));
+}
+
+static void
+do_compare__type_ctor_info_1_0(
+	MR_Word type_info, MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::private_builtin__c_code::__Compare____type_ctor_info_1_0(
+		type_info, result, 
+		dynamic_cast<MR_Word>(x),
+		dynamic_cast<MR_Word>(y));
+}
+
+static void
+do_compare__type_info_1_0(
+	MR_Word type_info, MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::private_builtin__c_code::__Compare____type_info_1_0(
+		type_info, result,
+		dynamic_cast<MR_Word>(x),
+		dynamic_cast<MR_Word>(y));
+}
+
+static void
+do_compare__typeclass_info_1_0(
+	MR_Word type_info, MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::private_builtin__c_code::__Compare____typeclass_info_1_0(
+		type_info, result,
+		dynamic_cast<MR_Word>(x),
+		dynamic_cast<MR_Word>(y));
+}
+
+static void
+do_compare__base_typeclass_info_1_0(
+	MR_Word type_info, MR_Word_Ref result, MR_Box x, MR_Box y)
+{
+	mercury::private_builtin__c_code::__Compare____base_typeclass_info_1_0(
+		type_info, result,
+		dynamic_cast<MR_Word>(x),
+		dynamic_cast<MR_Word>(y));
+}
+
+static void init_runtime(void)
+{
+	mercury::runtime::Init::init_runtime();
+}
+
 ").
 
 :- pragma foreign_code("C",
@@ -768,15 +770,14 @@
 		true
 	).
 
-/*
+:- pragma foreign_code("MC++", "
 
-XXX :- external stops us from using this
+static void free_heap_1_p_0(MR_Box X) 
+{ 
+        mercury::runtime::Errors::SORRY(""foreign code for this predicate"");
+}
 
-:- pragma foreign_code("MC++", free_heap(_A::di),
-		[will_not_call_mercury], "
-        MR_Runtime::SORRY(""foreign code for this predicate"");
 ").
-*/
 
 %-----------------------------------------------------------------------------%
 %-----------------------------------------------------------------------------%
diff -u library/sparse_bitset.m library/sparse_bitset.m
--- library/sparse_bitset.m
+++ library/sparse_bitset.m
@@ -777,8 +777,8 @@
 		[will_not_call_mercury, thread_safe],
 "{
 	MR_newobj((Pair), 0, 2);
-	MR_objset((Pair), 1, (mr_convert::ToObject(A)));	
-	MR_objset((Pair), 2, (mr_convert::ToObject(B)));
+	MR_objset((Pair), 1, (mercury::runtime::Convert::ToObject(A)));	
+	MR_objset((Pair), 2, (mercury::runtime::Convert::ToObject(B)));
 }").
 
 %-----------------------------------------------------------------------------%
diff -u library/std_util.m library/std_util.m
--- library/std_util.m
+++ library/std_util.m
@@ -814,10 +814,22 @@
 ").
 
 :- pragma foreign_code("MC++", 
-		get_registers(_HeapPtr::out, _SolutionsHeapPtr::out,
-		_TrailPtr::out), will_not_call_mercury,
+		get_registers(HeapPtr::out, SolutionsHeapPtr::out,
+		TrailPtr::out), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	/*
+	** For MC++, we always use the MS garbage collector,
+	** so we don't have to worry here about heap reclamation on failure.
+	*/
+	HeapPtr = SolutionsHeapPtr = 0;
+
+#ifdef MR_USE_TRAIL
+	/* XXX trailing not yet implemented for the MLDS back-end */
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
+#else
+	TrailPtr = 0
+#endif
+
 ").
 
 
@@ -833,7 +845,9 @@
 :- pragma foreign_code("MC++", 
 	check_for_floundering(_TrailPtr::in), [will_not_call_mercury],
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+#ifdef MR_USE_TRAIL
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
+#endif
 ").
 
 %
@@ -850,7 +864,9 @@
 :- pragma foreign_code("MC++", 
 	discard_trail_ticket, [will_not_call_mercury],
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+#ifdef MR_USE_TRAIL
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
+#endif
 ").
 
 %
@@ -879,7 +895,13 @@
 	swap_heap_and_solutions_heap,
 	will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	/*
+	** For the .NET back-end, we use the system heap, rather
+	** than defining our own heaps.  So we don't need to
+	** worry about swapping them.  Hence do nothing here.
+	*/
+
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 %
@@ -941,20 +963,25 @@
 
 :- pragma foreign_code("MC++",
 	partial_deep_copy(_SolutionsHeapPtr::in,
-		_OldVal::in, _NewVal::out), will_not_call_mercury,
+		OldVal::in, NewVal::out), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	/*
+	** For the IL back-end, we don't do heap reclamation on failure,
+	** so we don't need to worry about making deep copies here.
+	** Shallow copies will suffice.
+	*/
+	NewVal = OldVal;
 ").
 :- pragma foreign_code("MC++", 
 	partial_deep_copy(_SolutionsHeapPtr::in,
-		_OldVal::mdi, _NewVal::muo), will_not_call_mercury,
+		OldVal::mdi, NewVal::muo), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	NewVal = OldVal;
 ").
 :- pragma foreign_code("MC++", partial_deep_copy(_SolutionsHeapPtr::in,
-		_OldVal::di, _NewVal::uo), will_not_call_mercury,
+		OldVal::di, NewVal::uo), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	NewVal = OldVal;
 ").
 
 %
@@ -977,7 +1004,10 @@
 	reset_solutions_heap(_SolutionsHeapPtr::in),
 	will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	/*
+	** For the IL back-end, we don't have a separate `solutions heap'.
+	** Hence this operation is a NOP.
+	*/
 ").
 
 %-----------------------------------------------------------------------------%
@@ -1041,26 +1071,26 @@
 :- pragma foreign_code("MC++", 
 	new_mutvar(_X::in, _Ref::out), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 :- pragma foreign_code("MC++", 
 	new_mutvar(_X::di, _Ref::uo), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma inline(get_mutvar/2).
 :- pragma foreign_code("MC++",
 	get_mutvar(_Ref::in, _X::uo), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma inline(set_mutvar/2).
 :- pragma foreign_code("MC++",
 	set_mutvar(_Ref::in, _X::in), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 
@@ -1169,7 +1199,7 @@
 :- pragma foreign_code("MC++", 
 	univ_value(_Univ::in) = (_Value::out), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 
@@ -1262,8 +1292,8 @@
 	% The variable `TypeInfo_for_T' used in the C code
 	% is the compiler-introduced type-info variable.
 :- pragma foreign_code("MC++",
-	type_to_univ(Value::out, Univ::in), will_not_call_mercury, 
-"{
+	type_to_univ(Value::out, Univ::in), will_not_call_mercury, "
+{
 	MR_Word univ_type_info = Value->GetValue(0);
 	if (MR_compare_type_info(TypeInfo_for_T, univ_type_info)
 			== MR_COMPARE_EQUAL) {
@@ -1456,69 +1486,69 @@
         MR_TYPECTOR_REP_C_POINTER)
 
 static int MR_compare_type_info(MR_TypeInfo x, MR_TypeInfo y) {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	return 0;
 }
 
 static int
-mercury__std_util____Unify____univ_0_0(MR_Word x, MR_Word y)
+__Unify____univ_0_0(MR_Word x, MR_Word y)
 {
-	MR_Runtime::SORRY(""unify for univ"");
+	mercury::runtime::Errors::SORRY(""unify for univ"");
 	return 0;
 }
 
 static int
-mercury__std_util____Unify____type_desc_0_0(MR_Word x, MR_Word y)
+__Unify____type_desc_0_0(MR_Word x, MR_Word y)
 {
-	MR_Runtime::SORRY(""unify for type_desc"");
+	mercury::runtime::Errors::SORRY(""unify for type_desc"");
 	return 0;
 }
 
 static void
-mercury__std_util____Compare____univ_0_0(MR_Word_Ref result,
+__Compare____univ_0_0(MR_Word_Ref result,
 MR_Word x, MR_Word y)
 {
-	MR_Runtime::SORRY(""compare for univ"");
+	mercury::runtime::Errors::SORRY(""compare for univ"");
 }
 
 static void
-mercury__std_util____Compare____type_desc_0_0(
+__Compare____type_desc_0_0(
     MR_Word_Ref result, MR_Word x, MR_Word y)
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 
 static int
-mercury__std_util__do_unify__univ_0_0(MR_Box x, MR_Box y)
+do_unify__univ_0_0(MR_Box x, MR_Box y)
 {
-	return mercury__std_util____Unify____univ_0_0(
+	return mercury::std_util__c_code::__Unify____univ_0_0(
 		dynamic_cast<MR_Word>(x),
 		dynamic_cast<MR_Word>(y));
 }
 
 static int
-mercury__std_util__do_unify__type_desc_0_0(MR_Box x, MR_Box y)
+do_unify__type_desc_0_0(MR_Box x, MR_Box y)
 {
-    return mercury__std_util____Unify____type_desc_0_0(
+    return mercury::std_util__c_code::__Unify____type_desc_0_0(
 	    dynamic_cast<MR_Word>(x),
 	    dynamic_cast<MR_Word>(y));
 }
 
 static void
-mercury__std_util__do_compare__univ_0_0(MR_Word_Ref result,
+do_compare__univ_0_0(MR_Word_Ref result,
     MR_Box x, MR_Box y)
 {
-    mercury__std_util____Compare____univ_0_0(
+    mercury::std_util__c_code::__Compare____univ_0_0(
 	    result,
 	    dynamic_cast<MR_Word>(x),
 	    dynamic_cast<MR_Word>(y));
 }
 
 static void
-mercury__std_util__do_compare__type_desc_0_0(
+do_compare__type_desc_0_0(
     MR_Word_Ref result, MR_Box x, MR_Box y)
 {
-    mercury__std_util____Compare____type_desc_0_0(
+    mercury::std_util__c_code::__Compare____type_desc_0_0(
 	    result,
 	    dynamic_cast<MR_Word>(x),
 	    dynamic_cast<MR_Word>(y));
@@ -1821,7 +1851,7 @@
 :- pragma foreign_code("MC++", type_ctor(_TypeInfo::in) = (_TypeCtor::out),
 	will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
@@ -1922,7 +1952,7 @@
 :- pragma foreign_code("MC++", type_ctor_and_args(_TypeDesc::in,
 		_TypeCtorDesc::out, _ArgTypes::out), will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
@@ -1976,7 +2006,7 @@
 	make_type(_TypeCtorDesc::in, _ArgTypes::in) = (_TypeDesc::out),
 		will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
@@ -2323,7 +2353,7 @@
 	make_type(_TypeCtorDesc::out, _ArgTypes::out) = (_TypeDesc::in),
 		will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
@@ -2332,14 +2362,14 @@
 		_TypeCtorArity::out),
         will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
 :- pragma foreign_code("MC++", num_functors(_TypeInfo::in) = (_Functors::out),
 	will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
@@ -2347,7 +2377,7 @@
         _FunctorName::out, _Arity::out, _TypeInfoList::out),
 		will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
@@ -2355,7 +2385,7 @@
 	get_functor_ordinal(_TypeDesc::in, _FunctorNumber::in,
 		_Ordinal::out), will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
@@ -2363,7 +2393,7 @@
 	construct(_TypeDesc::in, _FunctorNumber::in,
 		_ArgList::in) = (_Term::out), will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
@@ -2419,7 +2449,7 @@
 	construct_tuple_2(_Args::in, _ArgTypes::in, _Arity::in) = (_Term::out),
 		will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""compare for type_desc"");
+	mercury::runtime::Errors::SORRY(""compare for type_desc"");
 }
 ").
 
@@ -3595,7 +3625,7 @@
 :- pragma foreign_code("MC++", functor(_Term::in, _Functor::out, _Arity::out),
     will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 /*
@@ -3607,14 +3637,14 @@
 	arg(_Term::in, _ArgumentIndex::in) = (_Argument::out),
         will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 :- pragma foreign_code("MC++",
 	argument(_Term::in, _ArgumentIndex::in) = (_ArgumentUniv::out),
         will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 det_arg(Type, ArgumentIndex) = Argument :-
@@ -3707,7 +3737,7 @@
 	deconstruct(_Term::in, _Functor::out, _Arity::out,
         _Arguments::out), will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }
 ").
 
@@ -3785,7 +3815,7 @@
 	get_notag_functor_info(_Univ::in, _ExpUniv::out),
 	will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
     % Given a value of an arbitrary type, succeed if its type is defined
@@ -3833,7 +3863,7 @@
 	get_equiv_functor_info(_Univ::in, _ExpUniv::out),
     will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
     % Given a value of an arbitrary type, succeed if it is an enum type,
@@ -3867,7 +3897,7 @@
 	get_enum_functor_info(_Univ::in, _Enum::out),
 	will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
     % Given a value of an arbitrary type, succeed if it is a general du type
@@ -3968,7 +3998,7 @@
 :- pragma foreign_code("MC++", get_du_functor_info(_Univ::in, _Where::out,
     _Ptag::out, _Sectag::out, _Args::out), will_not_call_mercury, "
 {
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 %-----------------------------------------------------------------------------%
diff -u library/store.m library/store.m
--- library/store.m
+++ library/store.m
@@ -455,86 +455,86 @@
 :- pragma foreign_code("MC++", new_mutvar(_Val::in, _Mutvar::out,
 		_S0::di, _S::uo), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", get_mutvar(_Mutvar::in, _Val::out,
 		_S0::di, _S::uo), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", set_mutvar(_Mutvar::in, _Val::in,
 		_S0::di, _S::uo), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", unsafe_new_uninitialized_mutvar(
 		_Mutvar::out, _S0::di, _S::uo), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", new_ref(_Val::di, _Ref::out, _S0::di, _S::uo),
 		will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", unsafe_ref_value(_Ref::in, _Val::uo,
 		_S0::di, _S::uo), will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", 
 	arg_ref(_Ref::in, _ArgNum::in, _ArgRef::out, _S0::di, _S::uo),
 		will_not_call_mercury,
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 :- pragma foreign_code("MC++", 
 	new_arg_ref(_Val::di, _ArgNum::in, _ArgRef::out, _S0::di, _S::uo),
 		will_not_call_mercury,
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 :- pragma foreign_code("MC++", 
 	set_ref(_Ref::in, _ValRef::in, _S0::di, _S::uo),
 		will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",	
 	set_ref_value(_Ref::in, _Val::di, _S0::di, _S::uo),
 		will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	extract_ref_value(_S::di, _Ref::in, _Val::out),
 		will_not_call_mercury,
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	unsafe_arg_ref(_Ref::in, _Arg::in, _ArgRef::out, _S0::di, _S::uo),
 		will_not_call_mercury,
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 :- pragma foreign_code("MC++",
 	unsafe_new_arg_ref(_Val::di, _Arg::in, _ArgRef::out,
 			_S0::di, _S::uo), will_not_call_mercury,
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
diff -u library/string.m library/string.m
--- library/string.m
+++ library/string.m
@@ -782,7 +782,8 @@
         MR_list_nil(prev);
 
         for (i = length - 1; i >= 0; i--) {
-		MR_list_cons(tmp, mr_convert::ToObject(Str->get_Chars(i)),
+		MR_list_cons(tmp,
+			mercury::runtime::Convert::ToObject(Str->get_Chars(i)),
 			prev);
 		prev = tmp;
         }
@@ -791,13 +792,13 @@
 
 :- pragma foreign_code("MC++", string__to_char_list(Str::out, CharList::in),
 		[will_not_call_mercury, thread_safe], "{
-        Text::StringBuilder *tmp;
+        System::Text::StringBuilder *tmp;
 	MR_Char c;
        
-        tmp = new Text::StringBuilder();
+        tmp = new System::Text::StringBuilder();
         while (1) {
             if (MR_list_is_cons(CharList)) {
-		c = mr_convert::ToChar(MR_list_head(CharList));
+		c = mercury::runtime::Convert::ToChar(MR_list_head(CharList));
                 tmp->Append(c);
                 CharList = MR_list_tail(CharList);
             } else {
@@ -810,7 +811,7 @@
 :- pragma foreign_code("MC++", string__from_rev_char_list(_Chars::in,
 		_Str::out), [will_not_call_mercury, thread_safe], "
 {
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 :- pred string__int_list_to_char_list(list(int), list(char)).
@@ -965,7 +966,7 @@
 
 :- pragma foreign_code("MC++", string__append_list(_Strs::in) = (_Str::out),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 
@@ -1016,7 +1017,7 @@
 	string__sub_string_search(_WholeString::in, _SubString::in,
 			_Index::out) , [will_not_call_mercury, thread_safe],
 "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 %-----------------------------------------------------------------------------%
@@ -1397,7 +1398,7 @@
 :- pragma foreign_code("MC++", 
 	int_length_modifer = (_LengthModifier::out),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 
@@ -1415,7 +1416,7 @@
 :- pragma foreign_code("MC++",
 	format_float(_FormatStr::in, _Val::in) = (_Str::out),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 	% Create a string from a int using the format string.
@@ -1432,7 +1433,7 @@
 :- pragma foreign_code("MC++",
 	format_int(_FormatStr::in, _Val::in) = (_Str::out),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 	% Create a string from a string using the format string.
@@ -1447,7 +1448,7 @@
 :- pragma foreign_code("MC++", 
 	format_string(_FormatStr::in, _Val::in) = (_Str::out),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 	% Create a string from a char using the format string.
@@ -1464,7 +1465,7 @@
 :- pragma foreign_code("MC++", 
 	format_char(_FormatStr::in, _Val::in) = (_Str::out),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 
@@ -1490,7 +1491,7 @@
 :- pragma foreign_code("MC++",
 	string__float_to_string(_FloatVal::in, _FloatString::out),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 	% Beware that the implementation of string__format depends
@@ -1521,13 +1522,13 @@
 :- pragma foreign_code("MC++",
 	string__float_to_f_string(_FloatVal::in, _FloatString::out),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 :- pragma foreign_code("MC++",
 	string__to_float(_FloatString::in, _FloatVal::out),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 /*-----------------------------------------------------------------------*/
@@ -1600,7 +1601,8 @@
         MR_list_nil(prev);
 
         for (i = length - 1; i >= 0; i--) {
-		MR_list_cons(tmp, mr_convert::ToObject(Str->get_Chars(i)),
+		MR_list_cons(tmp,
+			mercury::runtime::Convert::ToObject(Str->get_Chars(i)),
 			prev);
 		prev = tmp;
         }
@@ -1610,12 +1612,13 @@
 :- pragma foreign_code("MC++",
 	string__to_int_list(Str::out, IntList::in),
 		[will_not_call_mercury, thread_safe], "{
-        Text::StringBuilder *tmp;
+        System::Text::StringBuilder *tmp;
        
-        tmp = new Text::StringBuilder();
+        tmp = new System::Text::StringBuilder();
         while (1) {
-            if (mr_convert::ToInt32(IntList->GetValue(0))) {
-                tmp->Append(mr_convert::ToChar(IntList->GetValue(1)));
+            if (mercury::runtime::Convert::ToInt32(IntList->GetValue(0))) {
+                tmp->Append(mercury::runtime::Convert::ToChar(
+			IntList->GetValue(1)));
                 IntList = dynamic_cast<MR_Word>(IntList->GetValue(2));
             } else {
                 break;
@@ -1637,7 +1640,7 @@
 ").
 :- pragma foreign_code("MC++", string__contains_char(_Str::in, _Ch::in),
 		[will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 ").
 
 /*-----------------------------------------------------------------------*/
@@ -1728,7 +1731,7 @@
 :- pragma foreign_code("MC++",
 	string__set_char(_Ch::in, _Index::in, _Str0::in, _Str::out),
 		[will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 ").
 
 /*
@@ -1749,7 +1752,7 @@
 :- pragma foreign_code("MC++",
 	string__set_char(_Ch::in, _Index::in, _Str0::di, _Str::uo),
 		[will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 ").
 
 /*-----------------------------------------------------------------------*/
@@ -1769,7 +1772,7 @@
 :- pragma foreign_code("MC++",
 	string__unsafe_set_char(_Ch::in, _Index::in, _Str0::in, _Str::out),
 		[will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 ").
 
 /*
@@ -1785,7 +1788,7 @@
 :- pragma foreign_code("MC++",
 	string__unsafe_set_char(_Ch::in, _Index::in, _Str0::di, _Str::uo),
 		[will_not_call_mercury, thread_safe], "
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 ").
 
 /*-----------------------------------------------------------------------*/
@@ -1845,7 +1848,7 @@
 :- pragma foreign_code("MC++",
 	string__append(_S1::in, _S2::in, _S3::in),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 /*
@@ -1874,7 +1877,7 @@
 :- pragma foreign_code("MC++",
 	string__append(_S1::in, _S2::out, _S3::in),
 		[will_not_call_mercury, thread_safe], "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 /*
@@ -1893,7 +1896,7 @@
 :- pragma foreign_code("MC++",
 	string__append(S1::in, S2::in, S3::out),
 		[will_not_call_mercury, thread_safe], "{
-	S3 = String::Concat(S1, S2);
+	S3 = System::String::Concat(S1, S2);
 }").
 
 :- pragma foreign_code("C",
@@ -1938,7 +1941,7 @@
 	retry_code("
 	"),
 	common_code("
-		MR_Runtime::SORRY(""c code for this function"");
+		mercury::runtime::Errors::SORRY(""c code for this function"");
 	")
 ).
 
@@ -1977,7 +1980,7 @@
 		_SubString::out),
 		[will_not_call_mercury, thread_safe],
 "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 
@@ -2002,7 +2005,7 @@
 		_SubString::out),
 		[will_not_call_mercury, thread_safe],
 "{
-	MR_Runtime::SORRY(""c code for this function"");
+	mercury::runtime::Errors::SORRY(""c code for this function"");
 }").
 
 
@@ -2094,7 +2097,7 @@
 	SUCCESS_INDICATOR = (
 		len > 0 &&
 		Str->get_Chars(0) == First &&
-		String::Compare(Str, 1, Rest, 0, len) == 0
+		System::String::Compare(Str, 1, Rest, 0, len) == 0
 	);
 ").
 
@@ -2113,7 +2116,7 @@
 	MR_Integer len = Str->get_Length();
 	if (len > 0) {
 		SUCCESS_INDICATOR = 
-			(String::Compare(Str, 1, Rest, 0, len) == 0);
+			(System::String::Compare(Str, 1, Rest, 0, len) == 0);
 		First = Str->get_Chars(0);
 	} else {
 		SUCCESS_INDICATOR = FALSE;
@@ -2146,7 +2149,7 @@
 	MR_Integer len = Str->get_Length();
 	if (len > 0) {
 		SUCCESS_INDICATOR = (First == Str->get_Chars(0) &&
-			String::Compare(Str, 1, Rest, 0, len) == 0);
+			System::String::Compare(Str, 1, Rest, 0, len) == 0);
 		Rest = (Str)->Substring(1);
 	} else {
 		SUCCESS_INDICATOR = FALSE;
@@ -2202,8 +2205,8 @@
 	string__first_char(Str::out, First::in, Rest::in),
 		[will_not_call_mercury, thread_safe], "{
 	MR_String FirstStr;
-	FirstStr = new String(First, 1);
-	Str = String::Concat(FirstStr, Rest);
+	FirstStr = new System::String(First, 1);
+	Str = System::String::Concat(FirstStr, Rest);
 }").
 
 
diff -u library/table_builtin.m library/table_builtin.m
--- library/table_builtin.m
+++ library/table_builtin.m
@@ -325,47 +325,47 @@
 
 :- pragma foreign_code("MC++",
 	table_simple_is_complete(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_simple_has_succeeded(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_simple_has_failed(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_simple_is_active(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_simple_is_inactive(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_simple_mark_as_succeeded(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_simple_mark_as_failed(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_simple_mark_as_active(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_simple_mark_as_inactive(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 %-----------------------------------------------------------------------------%
@@ -511,19 +511,19 @@
 	table_io_in_range(_T::out, _Counter::out, _Start::out),
 	[will_not_call_mercury],
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", table_io_has_occurred(_T::in),
 	[will_not_call_mercury],
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", table_io_copy_io_state(_S0::di, _S::uo),
 	[will_not_call_mercury],
 "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 %-----------------------------------------------------------------------------%
@@ -657,7 +657,7 @@
 
 :- pragma foreign_code("MC++",
 	table_nondet_setup(_T0::in, _T::out), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 	% The definitions of these two predicates are in the runtime system,
@@ -675,13 +675,14 @@
 	first_code(""),
 	retry_code(""),
 	common_code("
-		MR_Runtime::SORRY(""foreign code for this function"");
+		mercury::runtime::Errors::SORRY(
+			""foreign code for this function"");
 	")
 ).
 
 :- pragma foreign_code("MC++",
 	table_nondet_resume(_A::in), [will_not_call_mercury], "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 */
@@ -905,35 +906,35 @@
 
 :- pragma foreign_code("MC++",
 	table_nondet_is_complete(_T::in), [will_not_call_mercury], "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_nondet_is_active(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_nondet_mark_as_active(_T::in), will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_nondet_get_ans_table(_T::in, _AT::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_nondet_answer_is_not_duplicate(_T::in),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_nondet_new_ans_slot(_T::in, _Slot::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
@@ -946,7 +947,7 @@
 	retry_code("
 	"),
 	shared_code("
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	")
 ).
 
@@ -965,7 +966,7 @@
 	retry_code("
 	"),
 	shared_code("
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 	")
 ).
 
@@ -1333,133 +1334,133 @@
 :- pragma foreign_code("MC++",
 	table_lookup_insert_int(_T0::in, _I::in, _T::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_lookup_insert_start_int(_T0::in, _S::in, _I::in, _T::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_lookup_insert_char(_T0::in, _C::in, _T::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_lookup_insert_string(_T0::in, _S::in, _T::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_lookup_insert_float(_T0::in, _F::in, _T::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++", 
 	table_lookup_insert_enum(_T0::in, _R::in, _V::in, _T::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_lookup_insert_user(_T0::in, _V::in, _T::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_lookup_insert_poly(_T0::in, _V::in, _T::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_save_int_ans(_T::in, _Offset::in, _I::in),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_save_char_ans(_T::in, _Offset::in, _C::in),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_save_string_ans(_T::in, _Offset::in, _S::in),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_save_float_ans(_T::in, _Offset::in, _F::in),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_save_io_state_ans(_T::in, _Offset::in, _S::ui),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 
 :- pragma foreign_code("MC++",
 	table_save_any_ans(_T::in, _Offset::in, _V::in),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_restore_int_ans(_T::in, _Offset::in, _I::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_restore_char_ans(_T::in, _Offset::in, _C::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_restore_string_ans(_T::in, _Offset::in, _S::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_restore_float_ans(_T::in, _Offset::in, _F::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_restore_io_state_ans(_T::in, _Offset::in, _V::uo),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_restore_any_ans(_T::in, _Offset::in, _V::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_create_ans_block(_T0::in, _Size::in, _T::out),
 		will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 :- pragma foreign_code("MC++",
 	table_report_statistics, will_not_call_mercury, "
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 ").
 
 
diff -u library/time.m library/time.m
--- library/time.m
+++ library/time.m
@@ -188,7 +188,7 @@
 :- pragma foreign_code("MC++", time__c_clock(_Ret::out, _IO0::di, _IO::uo),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -210,7 +210,7 @@
 :- pragma foreign_code("MC++", time__c_clocks_per_sec(_Ret::out),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 %-----------------------------------------------------------------------------%
@@ -254,7 +254,7 @@
                                _CSt::out, _IO0::di, _IO::uo),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -285,7 +285,7 @@
 	time__c_time(_Ret::out, _IO0::di, _IO::uo),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 %-----------------------------------------------------------------------------%
@@ -308,7 +308,7 @@
 	time__c_difftime(_T1::in, _T0::in, _Diff::out),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 %-----------------------------------------------------------------------------%
@@ -360,7 +360,7 @@
                                    _Yr::out, _N::out),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -411,7 +411,7 @@
                                    _Yr::out, _N::out),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -459,7 +459,7 @@
                                 _N::in, _Time::out),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
@@ -509,7 +509,7 @@
 				 _Str::out),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 %-----------------------------------------------------------------------------%
@@ -540,7 +540,7 @@
 	time__c_ctime(_Time::in, _Str::out),
 	[will_not_call_mercury],
 "{
-	MR_Runtime::SORRY(""foreign code for this function"");
+	mercury::runtime::Errors::SORRY(""foreign code for this function"");
 }").
 
 
diff -u runtime/Mmakefile runtime/Mmakefile
--- runtime/Mmakefile
+++ runtime/Mmakefile
@@ -210,10 +210,15 @@
 #-----------------------------------------------------------------------------#
 
 ifneq (,$(findstring il,$(GRADE)))
- 
-MSCL_NOASM=:noAssembly
+
+# Managed C++ files compiled in this directory should not be put in an
+# assembly of their own.  We put the runtime and library dlls into a single
+# assembly called `mercury'
+MS_CL_NOASM=:noAssembly
  
 runtime: mercury_il.dll mercury_mcpp.dll
+
+mercury_mcpp.dll: mercury_il.dll
  
 else
 
diff -u mercury_il.il mercury_il.il
--- mercury_il.il
+++ mercury_il.il
@@ -1,7 +1,15 @@
+//
+// Copyright (C) 2000 The University of Melbourne.
+// This file may only be copied under the terms of the GNU Library General
+// Public License - see the file COPYING.LIB in the Mercury distribution.
+//
+
+// mercury_mcpp.cpp - This file defines the system runtime types and
+// methods that ** are used when generating code for the .NET backend.
+// It is written in Microsoft's IL assembly language. 
 
-// .module 'generic.dll'
 
-// .assembly extern mscorlib { }
+// Declare the assemblies we use
 
 .assembly extern mercury { }
 
@@ -9,497 +17,538 @@
 
 .assembly extern 'mercury.io' { }
 
-.class public 'mercury.init' {
-    .method static default void init_runtime() {
-        call void mercury.io::init_state_2_p_0()
-    }
-}
+// ------------------------------------------------------------------------
+
+.namespace mercury.runtime {
 
+// Managed C++ can't call or create function pointers.
+// So we have to do it in IL.  
+// MC++ used to handle this, and then it stopped working, so now it's just
+// not supported at all.  I hope it will make a comeback.
 
-.class public temphack {
+.class public TempHack {
 
 .method static default int32 
-get_ftn_ptr_mercury__private_builtin__do_compare__typeclass_info_1_0() {
+get_ftn_ptr_typeclass_info_compare() {
 	ldftn void ['mercury'] 'mercury'.'private_builtin__c_code'::
-	mercury__private_builtin__do_compare__typeclass_info_1_0(
+	do_compare__typeclass_info_1_0(
 		class System.Object[], class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__private_builtin__do_unify__typeclass_info_1_0() {
+get_ftn_ptr_typeclass_info_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'private_builtin__c_code'::
-	mercury__private_builtin__do_unify__typeclass_info_1_0(
+	do_unify__typeclass_info_1_0(
 		class System.Object[], class System.Object,
 		class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__private_builtin__do_compare__base_typeclass_info_1_0() {
+get_ftn_ptr_base_typeclass_info_compare() {
 	ldftn void ['mercury'] 'mercury'.'private_builtin__c_code'::
-	mercury__private_builtin__do_compare__base_typeclass_info_1_0(
+	do_compare__base_typeclass_info_1_0(
 		class System.Object[], class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__private_builtin__do_unify__base_typeclass_info_1_0() {
+get_ftn_ptr_base_typeclass_info_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'private_builtin__c_code'::
-	mercury__private_builtin__do_unify__base_typeclass_info_1_0(
+	do_unify__base_typeclass_info_1_0(
 		class System.Object[], class System.Object,
 		class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__private_builtin__do_compare__type_info_1_0() {
+get_ftn_ptr_type_info_compare() {
 	ldftn void ['mercury'] 'mercury'.'private_builtin__c_code'::
-	mercury__private_builtin__do_compare__type_info_1_0(
+	do_compare__type_info_1_0(
 		class System.Object[], class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__private_builtin__do_unify__type_info_1_0() {
+get_ftn_ptr_type_info_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'private_builtin__c_code'::
-	mercury__private_builtin__do_unify__type_info_1_0(
+	do_unify__type_info_1_0(
 		class System.Object[], class System.Object,
 		class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__private_builtin__do_compare__type_ctor_info_1_0() {
+get_ftn_ptr_type_ctor_info_compare() {
 	ldftn void ['mercury'] 'mercury'.'private_builtin__c_code'::
-	mercury__private_builtin__do_compare__type_ctor_info_1_0(
+	do_compare__type_ctor_info_1_0(
 		class System.Object[], class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__private_builtin__do_unify__type_ctor_info_1_0() {
+get_ftn_ptr_type_ctor_info_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'private_builtin__c_code'::
-	mercury__private_builtin__do_unify__type_ctor_info_1_0(
+	do_unify__type_ctor_info_1_0(
 		class System.Object[], class System.Object,
 		class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_compare__pred_0_0() {
+get_ftn_ptr_pred_compare() {
 	ldftn void ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_compare__pred_0_0(
+	do_compare__pred_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_unify__pred_0_0() {
+get_ftn_ptr_pred_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_unify__pred_0_0(
+	do_unify__pred_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_compare__func_0_0() {
+get_ftn_ptr_func_compare() {
 	ldftn void ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_compare__func_0_0(
+	do_compare__func_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_unify__func_0_0() {
+get_ftn_ptr_func_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_unify__func_0_0(
+	do_unify__func_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
-
-
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_compare__float_0_0() {
+get_ftn_ptr_float_compare() {
 	ldftn void ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_compare__float_0_0(
+	do_compare__float_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_unify__float_0_0() {
+get_ftn_ptr_float_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_unify__float_0_0(
+	do_unify__float_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
-
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_compare__void_0_0() {
+get_ftn_ptr_void_compare() {
 	ldftn void ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_compare__void_0_0(
+	do_compare__void_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_unify__void_0_0() {
+get_ftn_ptr_void_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_unify__void_0_0(
+	do_unify__void_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
-
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_compare__c_pointer_0_0() {
+get_ftn_ptr_c_pointer_compare() {
 	ldftn void ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_compare__c_pointer_0_0(
+	do_compare__c_pointer_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_unify__c_pointer_0_0() {
+get_ftn_ptr_c_pointer_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_unify__c_pointer_0_0(
+	do_unify__c_pointer_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_compare__string_0_0() {
+get_ftn_ptr_string_compare() {
 	ldftn void ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_compare__string_0_0(
+	do_compare__string_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_unify__string_0_0() {
+get_ftn_ptr_string_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_unify__string_0_0(
+	do_unify__string_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_compare__character_0_0() {
+get_ftn_ptr_character_compare() {
 	ldftn void ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_compare__character_0_0(
+	do_compare__character_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_unify__character_0_0() {
+get_ftn_ptr_character_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_unify__character_0_0(
+	do_unify__character_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_compare__int_0_0() {
+get_ftn_ptr_int_compare() {
 	ldftn void ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_compare__int_0_0(
+	do_compare__int_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__builtin__do_unify__int_0_0() {
+get_ftn_ptr_int_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'builtin__c_code'::
-	mercury__builtin__do_unify__int_0_0(
+	do_unify__int_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__array__do_compare__array_1_0() {
+get_ftn_ptr_array_compare() {
 	ldftn void ['mercury'] 'mercury'.'array__c_code'::
-	mercury__array__do_compare__array_1_0(
+	do_compare__array_1_0(
 		class System.Object[], class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__array__do_unify__array_1_0() {
+get_ftn_ptr_array_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'array__c_code'::
-	mercury__array__do_unify__array_1_0(
+	do_unify__array_1_0(
 		class System.Object[], class System.Object,
 		class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__std_util__do_compare__type_desc_0_0() {
+get_ftn_ptr_type_desc_compare() {
 	ldftn void ['mercury'] 'mercury'.'std_util__c_code'::
-	mercury__std_util__do_compare__type_desc_0_0(
+	do_compare__type_desc_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__std_util__do_unify__type_desc_0_0() {
+get_ftn_ptr_type_desc_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'std_util__c_code'::
-	mercury__std_util__do_unify__type_desc_0_0(
+	do_unify__type_desc_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
 .method static default int32 
-get_ftn_ptr_mercury__std_util__do_compare__univ_0_0() {
+get_ftn_ptr_univ_compare() {
 	ldftn void ['mercury'] 'mercury'.'std_util__c_code'::
-	mercury__std_util__do_compare__univ_0_0(
+	do_compare__univ_0_0(
 		class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
+
 .method static default int32 
-get_ftn_ptr_mercury__std_util__do_unify__univ_0_0() {
+get_ftn_ptr_univ_unify() {
 	ldftn int32 ['mercury'] 'mercury'.'std_util__c_code'::
-	mercury__std_util__do_unify__univ_0_0(
+	do_unify__univ_0_0(
 		class System.Object, class System.Object)
 	ret
 }
 
-}
+} // end of class TempHack
+
+// ------------------------------------------------------------------------
+
+// Implement some classes for boxing values.  Hopefully this is just
+// temporary while the box/unbox instructions were broken, apparently
+// they work now, so it's just SMOP to get rid of this code.
+
+.class public BoxedInt {
 
-.class public boxedint {
 .field public int32 val
-.method default void .ctor(int32)
+
+.method default void .ctor(int32 'intval')
 {
+	// call the parent constructor
 	ldarg.0
 	call instance void System.Object::.ctor()
+
+	// set the value
 	ldarg.0
-	ldarg.1
-	stfld int32 boxedint::val
+	ldarg 'intval'
+	stfld int32 mercury.runtime.BoxedInt::val
 	ret
 }
 
 }
 
-.class public boxedfloat {
+.class public BoxedFloat {
+
 .field public float64 val
-.method default void .ctor(float64)
+
+.method default void .ctor(float64 'floatval')
 {
+	// call the parent constructor
 	ldarg.0
 	call instance void System.Object::.ctor()
+
+	// set the value
 	ldarg.0
-	ldarg.1
-	stfld float64 boxedfloat::val
+	ldarg 'floatval'
+	stfld float64 mercury.runtime.BoxedFloat::val
 	ret
 }
 
 }
 
-.class public convert_imp {
+// ------------------------------------------------------------------------
+
+// The implementation of conversion routines.  Written in IL so that we can
+// just plug in an implementation using box/unbox and see if it works.
+
+.class public ConvertImpl {
 
 .method static default class System.Object ToObject(int32 ival)
 {
 	ldarg ival
-	newobj instance void boxedint::.ctor(int32)
+	newobj instance void mercury.runtime.BoxedInt::.ctor(int32)
 	ret
 }
 
 .method static default int32 ToInt32(class System.Object obj)
 {
 	ldarg obj
-	ldnull
-	beq l1
-
-	ldarg obj
-	isinst class boxedint
-	ldfld int32 boxedint::val
-	ret
-l1:
-	ldc.i4 42
+	isinst class mercury.runtime.BoxedInt
+	ldfld int32 mercury.runtime.BoxedInt::val
 	ret
 }
 
 .method static default float64 ToFloat64(class System.Object obj)
 {
 	ldarg obj
-	ldnull
-	beq l1
-
-	ldarg obj
-	isinst class boxedfloat
-	ldfld float64 boxedfloat::val
-	ret
-l1:
-	ldc.i4 42
+	isinst class mercury.runtime.BoxedFloat
+	ldfld float64 mercury.runtime.BoxedFloat::val
 	ret
 }
 
 
 }
 
-.class public generic {
+// ------------------------------------------------------------------------
 
-.method static default  int32 generic_call2(class System.Object, 
-	class System.Object, class System.Object) 
+// This class implements some specific instances of call/N, mostly used for 
+// doing unify and compare.  You can't call using a function pointer in MC++
+// so we have to do it in IL.
+
+.class public GenericCall {
+
+.method static default  int32 semidet_call_3(class System.Object 'procedure', 
+	class System.Object 'X', class System.Object 'Y') 
 {
-	ldarg.1
-	ldarg.2
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	int32 (class System.Object, class System.Object)
 	ret
 }
 
 
-.method static default  int32 generic_call3(class System.Object, 
-	class System.Object, class System.Object, class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  int32 semidet_call_4(class System.Object 'procedure', 
+	class System.Object 'T1', class System.Object 'X',
+	class System.Object 'Y') 
+{
+	ldarg 'T1'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	int32 (class System.Object, class System.Object, class System.Object)
 	ret
 }
 
-.method static default  int32 generic_call4(class System.Object, 
-	class System.Object, class System.Object, class System.Object, class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg 4
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  int32 semidet_call_5(class System.Object 'procedure', 
+	class System.Object 'T1', class System.Object 'T2',
+	class System.Object 'X', class System.Object 'Y')
+{
+	ldarg 'T1'
+	ldarg 'T2'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	int32 (class System.Object, class System.Object, class System.Object, class System.Object)
 	ret
 }
 
-.method static default  int32 generic_call5(class System.Object, 
-	class System.Object, class System.Object, class System.Object, class System.Object, class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg 4
-	ldarg 5
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  int32 semidet_call_6(class System.Object 'procedure', 
+	class System.Object 'T1', class System.Object 'T2',
+	class System.Object 'T3', class System.Object 'X',
+	class System.Object 'Y')
+{
+	ldarg 'T1'
+	ldarg 'T2'
+	ldarg 'T3'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	int32 (class System.Object, class System.Object, class System.Object, class System.Object, class System.Object)
 	ret
 }
 
-.method static default  int32 generic_call6(class System.Object, 
-	class System.Object, class System.Object, class System.Object, class System.Object, class System.Object, class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg 4
-	ldarg 5
-	ldarg 6
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  int32 semidet_call_7(class System.Object 'procedure', 
+	class System.Object 'T1', class System.Object 'T2',
+	class System.Object 'T3', class System.Object 'T4',
+	class System.Object 'X', class System.Object 'Y')
+{
+	ldarg 'T1'
+	ldarg 'T2'
+	ldarg 'T3'
+	ldarg 'T4'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	int32 (class System.Object, class System.Object, class System.Object, class System.Object, class System.Object, class System.Object)
 	ret
 }
 
 
-.method static default  int32 generic_call7(class System.Object, 
-	class System.Object, class System.Object, class System.Object, class System.Object, class System.Object, class System.Object, class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg 4
-	ldarg 5
-	ldarg 6
-	ldarg 7
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  int32 semidet_call_8(class System.Object 'procedure', 
+	class System.Object 'T1', class System.Object 'T2',
+	class System.Object 'T3', class System.Object 'T4',
+	class System.Object 'T5', class System.Object 'X',
+	class System.Object 'Y')
+{
+	ldarg 'T1'
+	ldarg 'T2'
+	ldarg 'T3'
+	ldarg 'T4'
+	ldarg 'T5'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	int32 (class System.Object, class System.Object, class System.Object, class System.Object, class System.Object, class System.Object, class System.Object)
 	ret
 }
 
-.method static default  void generic_res_call3(class System.Object, 
-	class System.Object[]&, class System.Object, class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+	// The result_call methods are intended to interface to polymorphic
+	// procedures that have two real parameters, and a variable number of
+	// type parameters.
+
+.method static default  void result_call_4(class System.Object 'procedure', 
+	class System.Object[]& 'result', class System.Object 'X', 
+	class System.Object 'Y') 
+{
+	ldarg 'result'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	void (class System.Object[]&, class System.Object, class System.Object)
 	ret
 }
 
-.method static default  void generic_res_call4(class System.Object, 
-	class System.Object, class System.Object[]&, class System.Object,
-	class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg 4
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  void result_call_5(class System.Object 'procedure', 
+	class System.Object[]& 'result', class System.Object 'T1', 
+	class System.Object 'X', class System.Object 'Y') 
+{
+	ldarg 'T1'
+	ldarg 'result'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	void (class System.Object, class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
 
-.method static default  void generic_res_call5(class System.Object, 
-	class System.Object, class System.Object, class System.Object[]&,
-	class System.Object, class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg 4
-	ldarg 5
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  void result_call_6(class System.Object 'procedure', 
+	class System.Object[]& 'result', class System.Object 'T1', 
+	class System.Object 'T2', class System.Object 'X', 
+	class System.Object 'Y')
+{
+	ldarg 'T1'
+	ldarg 'T2'
+	ldarg 'result'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	void (class System.Object,
 		class System.Object, class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
 
-.method static default  void generic_res_call6(class System.Object, 
-	class System.Object, class System.Object, class System.Object, 
-	class System.Object[]&, class System.Object, class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg 4
-	ldarg 5
-	ldarg 6
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  void result_call_7(class System.Object 'procedure', 
+	class System.Object[]& 'result', class System.Object 'T1', 
+	class System.Object 'T2', class System.Object 'T3', 
+	class System.Object 'X', class System.Object 'Y') 
+{
+	ldarg 'T1'
+	ldarg 'T2'
+	ldarg 'T3'
+	ldarg 'result'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	void (class System.Object, class System.Object,
 		class System.Object, class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
 }
 
-.method static default  void generic_res_call7(class System.Object, 
-	class System.Object, class System.Object, class System.Object, 
-	class System.Object, class System.Object[]&, class System.Object,
-	class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg 4
-	ldarg 5
-	ldarg 6
-	ldarg 7
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  void result_call_8(class System.Object 'procedure', 
+	class System.Object[]& 'result', class System.Object 'T1', 
+	class System.Object 'T2', class System.Object 'T3', 
+	class System.Object 'T4', class System.Object 'X', 
+	class System.Object 'Y') 
+{
+	ldarg 'T1'
+	ldarg 'T2'
+	ldarg 'T3'
+	ldarg 'T4'
+	ldarg 'result'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	void (class System.Object, class System.Object,
 		class System.Object,
 		class System.Object, class System.Object[]&,
@@ -507,27 +556,40 @@
 	ret
 }
 
-.method static default  void generic_res_call8(class System.Object, 
-	class System.Object, class System.Object, class System.Object, 
-	class System.Object,
-	class System.Object, class System.Object[]&, class System.Object,
-	class System.Object) 
-{
-	ldarg.1
-	ldarg.2
-	ldarg.3
-	ldarg 4
-	ldarg 5
-	ldarg 6
-	ldarg 7
-	ldarg 8
-	ldarg.0
-	call 	int32 convert_imp::ToInt32(class System.Object)
+.method static default  void result_call_9(class System.Object 'procedure', 
+	class System.Object[]& 'result', class System.Object 'T1', 
+	class System.Object 'T2', class System.Object 'T3', 
+	class System.Object 'T4', class System.Object 'T5', 
+	class System.Object 'X', class System.Object 'Y') 
+{
+	ldarg 'T1'
+	ldarg 'T2'
+	ldarg 'T3'
+	ldarg 'T4'
+	ldarg 'T5'
+	ldarg 'result'
+	ldarg 'X'
+	ldarg 'Y'
+	ldarg 'procedure'
+	call 	int32 mercury.runtime.ConvertImpl::ToInt32(class System.Object)
 	calli	void (class System.Object, class System.Object,
 		class System.Object, class System.Object,
 		class System.Object, class System.Object[]&,
 		class System.Object, class System.Object)
 	ret
+}
+
+}
+
+// Call init_state/2 in the IO module.
+// This gets called before main runs.
+// It has to be written in IL because we call something that might not
+// yet be available in a .DLL.
+
+.class public 'Init' {
+    .method static default void init_runtime() {
+        call void mercury.io::init_state_2_p_0()
+    }
 }
 
 
diff -u mercury_mcpp.cpp mercury_mcpp.cpp
--- mercury_mcpp.cpp
+++ mercury_mcpp.cpp
@@ -1,43 +1,53 @@
+//
+// Copyright (C) 2000 The University of Melbourne.
+// This file may only be copied under the terms of the GNU Library General
+// Public License - see the file COPYING.LIB in the Mercury distribution.
+//
+
+// mercury_mcpp.cpp - This file defines the system runtime types and
+// methods that are used when generating code for the .NET backend.
+// It is written using Managed Extensions for C++ (usually called Managed C++ 
+// or MC++).
+
 // vi: ts=4 sw=4 et tw=0 wm=0
 
 #using <mscorlib.dll>
 #using "mercury_il.dll"
-using namespace System;
 
     // This line (somehow) stops the compiler from
     // linking in the C library (and it will then complain about main being
     // missing)
 extern "C" int _fltused=0;
 
-#include "mercury_cpp.h"
-using namespace mercury;
+#include "mercury_mcpp.h"
 
 namespace mercury {
 
+namespace runtime {
 
-__gc public class mercury_exception : public Exception
+	// XXX Exception support is utterly incomplete.
+__gc public class Exception : public System::Exception
 {
 public:
-    mercury_exception()
-    { }
-
-    mercury_exception(MR_String Msg) : Exception(Msg)
+	// XXX there should be a Mercury object here.
+    Exception(MR_String Msg) : Exception(Msg)
     { 
+	// XXX this should set the exception message
     }
 };
 
 
 
-__gc public class mr_convert
+__gc public class Convert
 {
-    public:
+public:
     static MR_Box ToObject(MR_Integer x)
     {
-        return convert_imp::ToObject(x);
+        return ConvertImpl::ToObject(x);
     }
     static MR_Box ToObject(MR_Char x)
     {
-        return convert_imp::ToObject((MR_Integer) x);
+        return ConvertImpl::ToObject((MR_Integer) x);
     }
     static MR_Box ToObject(MR_Word x)
     {
@@ -47,15 +57,15 @@
 
     static MR_Char ToChar(MR_Box x)
     {
-        return (Char) convert_imp::ToInt32(x);
+        return (MR_Char) ConvertImpl::ToInt32(x);
     }
     static MR_Integer ToInt32(MR_Box x)
     {
-        return convert_imp::ToInt32(x);
+        return ConvertImpl::ToInt32(x);
     }
     static MR_Float ToDouble(MR_Box x)
     {
-        return convert_imp::ToFloat64(x);
+        return ConvertImpl::ToFloat64(x);
     }
     static MR_Word ToArray(MR_Box x)
     {
@@ -64,29 +74,34 @@
 };
 
 
-__gc public class MR_Runtime {
+__gc public class Errors {
     public:
     static void SORRY(MR_String s) 
     {
         MR_String msg;
-        mercury_exception *ex;
-
-        msg = String::Concat("Sorry, unimplemented: ", s);
-
-        ex = new mercury_exception(msg);
-        throw ex;
+        msg = System::String::Concat("Sorry, unimplemented: ", s);
+        throw new mercury::runtime::Exception(msg);
     }
 
-    static void MR_fatal_error(MR_String s)
+    static void fatal_error(MR_String s)
     {
         MR_String msg;
-        mercury_exception *ex;
+        msg = System::String::Concat("Fatal error: ", s);
+        throw new mercury::runtime::Exception(msg);
+    }
+};
 
-        msg = String::Concat("Fatal error: ", s);
 
-        ex = new mercury_exception(msg);
-        throw ex;
-    }
+__gc public class Constants {
+    public:
+
+        // These constants are duplicated in library/private_builtin.m.
+        // They must be kept sychronized.
+
+	// XXX it would be nice if these could be const or an enum.  But
+	// there are some problems with accessing the values from IL if we do
+	// that because neither alternatives seem to define field names we
+	// can reference from IL.
 
     static int MR_TYPECTOR_REP_ENUM 			= MR_TYPECTOR_REP_ENUM_val;
     static int MR_TYPECTOR_REP_ENUM_USEREQ 		= MR_TYPECTOR_REP_ENUM_USEREQ_val;
@@ -122,28 +137,19 @@
     static int MR_SECTAG_NONE				= 0;
     static int MR_SECTAG_LOCAL				= 1;
     static int MR_SECTAG_REMOTE				= 2;
-
 };
 
-__gc public class envptr
+__gc public class Environment
 {
 public:
 };
 
-__gc public class continuation
+__gc public class Commit : public System::Exception
 {
 public:
-	envptr *a;
-	continuation() {
-		this->a = new envptr();
-
-	}
 };
 
-__gc public class commit : public Exception
-{
-public:
-};
+}
 
 }
 
diff -u scripts/Mmake.rules scripts/Mmake.rules
--- scripts/Mmake.rules
+++ scripts/Mmake.rules
@@ -183,15 +183,20 @@
 	rm -f $(ils_subdir)$*.il
 	$(MCG) $(ALL_GRADEFLAGS) $(ALL_MCGFLAGS) --il-only $< > $*.err 2>&1
 
+# These rules are only available in *il* backends, because we'd like to avoid
+# processing user code that is in a .cpp file, and we'd like to avoid going via
+# IL to generate a DLL if we are in a non-IL grade.
+ifneq (,$(findstring il,$(GRADE)))
 $(os_subdir)%.dll : %.cpp
 	rm -f $(os_subdir)$*.dll
-	$(MSCL) -com+$(MSCL_NOASM) -I$(MERC_C_INCL_DIR) \
-		-I$(MERC_DLL_DIR) $(ALL_MSCLFLAGS) $< -link -noentry \
-		-dll $(MSCL_LIBS) -out:$@
+	$(MS_CL) -com+$(MS_CL_NOASM) -I$(MERC_C_INCL_DIR) \
+		-I$(MERC_DLL_DIR) $(ALL_MS_CLFLAGS) $< -link -noentry \
+		-dll $(MS_CL_LIBS) -out:$@
 
 $(os_subdir)%.dll : %.il
 	rm -f $(os_subdir)$*.dll
-	$(MSILASM) $(ALL_MSILASMFLAGS) /dll /quiet /OUT=$@ $<
+	$(MS_ILASM) $(ALL_MS_ILASMFLAGS) /dll /quiet /OUT=$@ $<
+endif
 
 # If we are removing the .c files, we need to tell Make that we're
 # generating the .$O files directly from the .m files, but
@@ -293,24 +298,33 @@
 #-----------------------------------------------------------------------------#
 #
 # Rules for compiling IL files in the user's source directory.
+# Note that we need both these rules and the ones above,
+# since even if the compiler generates all of its files in subdirectories,
+# the user may have some il or cpp files of their own which need to be
+# compiled.
+#
+# To avoid possible problems with invoking these commands unintentionally,
+# we only activate these rules when in an IL grade.
 #
 
+ifneq (,$(findstring il,$(GRADE)))
 ifneq ("$(ils_subdir)","")
 
 .il.dll:
-	$(MSILASM) $(ALL_MSILASMFLAGS) /dll /OUT=$@ $<
+	$(MS_ILASM) $(ALL_MS_ILASMFLAGS) /dll /quiet /OUT=$@ $<
 
 .il.exe:
-	$(MSILASM) $(ALL_MSILASMFLAGS) /OUT=$@ $< 
+	$(MS_ILASM) $(ALL_MS_ILASMFLAGS) /quiet /OUT=$@ $< 
 	cp default.cfg $*.cfg
 
 .cpp.dll:
-	$(MSCL) -com+($MSCL_NOASM) -I$(MERCURY_LIBRARY_PATH) $< -link -noentry -dll $(MSCL_LIBS) -out:$@
+	$(MS_CL) -com+($MS_CL_NOASM) -I$(MERCURY_LIBRARY_PATH) $< -link -noentry -dll $(MS_CL_LIBS) -out:$@
 
 .cpp.exe:
-	$(MSCL) -com+($MSCL_NOASM) -I$(MERCURY_LIBRARY_PATH) $< -link -entry:main $(MSCL_LIBS) -out:$@
+	$(MS_CL) -com+($MS_CL_NOASM) -I$(MERCURY_LIBRARY_PATH) $< -link -entry:main $(MS_CL_LIBS) -out:$@
 
 endif # $(ils_subdir) != ""
+endif # $(findstring il,$(GRADE)) != ""
 
 #-----------------------------------------------------------------------------#
 #
diff -u scripts/Mmake.vars.in scripts/Mmake.vars.in
--- scripts/Mmake.vars.in
+++ scripts/Mmake.vars.in
@@ -130,25 +130,37 @@
 CFLAGS		=
 EXTRA_CFLAGS	=
 
-MSCL		= cl
-ALL_MSCLFLAGS	= $(MSCLFLAGS) $(EXTRA_MSCLFLAGS) $(TARGET_MSCLFLAGS) \
-		$(LIB_MSCLFLAGS) $(ALL_CFLAGS)
-MSCLFLAGS	=
-EXTRA_MSCLFLAGS =
-LIB_MSCLFLAGS	= $(patsubst %,-I %,$(EXTRA_C_INCL_DIRS))
-MSCL_NOASM	=
+# MS_CL is the command line version of Microsoft VC++, which we use to compile
+# Managed C++ code in the .NET backend.
+MS_CL		= cl
+ALL_MS_CLFLAGS	= $(MS_CLFLAGS) $(EXTRA_MS_CLFLAGS) $(TARGET_MS_CLFLAGS) \
+		$(LIB_MS_CLFLAGS) $(ALL_CFLAGS)
+MS_CLFLAGS	=
+EXTRA_MS_CLFLAGS =
+LIB_MS_CLFLAGS	= $(patsubst %,-I %,$(EXTRA_C_INCL_DIRS))
+
+# MS_CL_NOASM can be used to turn off assembly generation.  Use
+# MS_CL_NOASM=:noAssembly to turn it off, leave it blank to turn it on.
+MS_CL_NOASM	=
 MS_DOTNET_SDK_DIR=@MS_DOTNET_SDK_DIR@
-MSCL_LIBS	= $(MS_DOTNET_SDK_DIR)/Lib/mscoree.lib \
-		  $(MS_DOTNET_SDK_DIR)/Lib/kernel32.lib
+# The system libraries.
+MS_CL_LIBS	= "$(MS_DOTNET_SDK_DIR)/Lib/mscoree.lib" \
+		  "$(MS_DOTNET_SDK_DIR)/Lib/kernel32.lib"
 MERC_C_INCL_DIR = @LIBDIR@/inc
 MERC_DLL_DIR    = @LIBDIR@/inc
 
-MSILASM		= @ILASM@
-ALL_MSILASMFLAGS= $(MSILASMFLAGS) $(EXTRA_MSILASMFLAGS) $(TARGET_MSILASMFLAGS) \
-		  $(LIB_MSILASMFLAGS)
-MSILASMFLAGS	=
-EXTRA_MSILASMFLAGS =
-LIB_MSILASMFLAGS= $(patsubst %,-I %,$(EXTRA_C_INCL_DIRS))
+# MS_ILASM is the Microsoft IL assembler, which turns IL assembly code
+# into bytecode.
+MS_ILASM		= @ILASM@
+ALL_MS_ILASMFLAGS= $(MS_ILASMFLAGS) $(EXTRA_MS_ILASMFLAGS) \
+		$(TARGET_MS_ILASMFLAGS) $(LIB_MS_ILASMFLAGS)
+MS_ILASMFLAGS	=
+EXTRA_MS_ILASMFLAGS =
+LIB_MS_ILASMFLAGS= $(patsubst %,-I %,$(EXTRA_C_INCL_DIRS))
+
+# MS_AL is the Microsoft assembly linker, which creates and installs
+# assemblies.
+MS_AL		= al
 
 ML		= ml
 ALL_MLFLAGS	= $(MLFLAGS) $(EXTRA_MLFLAGS) $(TARGET_MLFLAGS) $(LIB_MLFLAGS)
@@ -343,15 +355,15 @@
 maybe-base-EXTRA_LIBGRADES- = $(EXTRA_LIBGRADES-$*)
 maybe-base-EXTRA_LIBGRADES-undefined =
 
-TARGET_MSCLFLAGS = \
-  $(maybe-base-MSCLFLAGS-$(findstring undefined,$(origin MSCLFLAGS-$*)))
-maybe-base-MSCLFLAGS- = $(MSCLFLAGS-$*)
-maybe-base-MSCLFLAGS-undefined =
-
-TARGET_MSILASMFLAGS = \
-   $(maybe-base-MSILASMFLAGS-$(findstring undefined,$(origin MSILASMFLAGS-$*)))
-maybe-base-MSILASMFLAGS- = $(MSILASMFLAGS-$*)
-maybe-base-MSILASMFLAGS-undefined =
+TARGET_MS_CLFLAGS = \
+  $(maybe-base-MS_CLFLAGS-$(findstring undefined,$(origin MS_CLFLAGS-$*)))
+maybe-base-MS_CLFLAGS- = $(MS_CLFLAGS-$*)
+maybe-base-MS_CLFLAGS-undefined =
+
+TARGET_MS_ILASMFLAGS = \
+   $(maybe-base-MS_ILASMFLAGS-$(findstring undefined,$(origin MS_ILASMFLAGS-$*)))
+maybe-base-MS_ILASMFLAGS- = $(MS_ILASMFLAGS-$*)
+maybe-base-MS_ILASMFLAGS-undefined =
 
 # Support for compiling Mercury programs with Prolog will probably be
 # dropped one of these days, so it's probably not worth bothering with these.
only in patch2:
--- /dev/null	Wed Nov 15 09:24:47 2000
+++ mercury_mcpp.h	Sun Dec 24 16:04:05 2000
@@ -0,0 +1,216 @@
+
+#include <stddef.h>
+
+
+namespace mercury {
+
+typedef int		MR_Integer;
+typedef System::Int32	MR_BoxedInt;
+
+typedef System::Char	MR_Char; // `Char' is MS's name for unicode characters 
+
+typedef double 		MR_Float;
+#define MR_BoxedFloat System::Double
+
+typedef System::String *MR_String;
+typedef void (*MR_Cont) (void *);
+
+
+// Should these be MR_ qualified?
+#define TRUE 1
+#define FALSE 0
+
+
+
+typedef __gc public class System::Object * MR_Word[];
+typedef __gc public class System::Object * MR_Box;
+typedef __gc public class System::Object * MR_Array;
+
+#define MR_Ref(type) type __gc *
+typedef MR_Ref(MR_Box) MR_Box_Ref;
+typedef MR_Ref(MR_Word) MR_Word_Ref;
+
+typedef __gc public class System::Object * MR_TypeInfo[];
+typedef __gc public class System::Object * MR_TypeCtorInfo[];
+typedef __gc public class System::Object * MR_TypeInfoParams[];
+typedef __gc public class System::Object * MR_TypeClassInfo[];
+
+#define MR_COMPARE_EQUAL 0
+#define MR_COMPARE_LESS 1
+#define MR_COMPARE_GREATER 2
+
+#define MR_STRINGIFY(x)         MR_STRINGIFY_2(x)
+#define MR_STRINGIFY_2(x)       #x
+
+#define MR_PASTE2(a,b)                    MR_PASTE2_2(a,b)
+#define MR_PASTE2_2(a,b)          a##b
+#define MR_PASTE3(a,b,c)          MR_PASTE3_2(a,b,c)
+#define MR_PASTE3_2(a,b,c)                a##b##c
+#define MR_PASTE4(a,b,c,d)                MR_PASTE4_2(a,b,c,d)
+#define MR_PASTE4_2(a,b,c,d)              a##b##c##d
+#define MR_PASTE5(a,b,c,d,e)              MR_PASTE5_2(a,b,c,d,e)
+#define MR_PASTE5_2(a,b,c,d,e)            a##b##c##d##e
+#define MR_PASTE6(a,b,c,d,e,f)            MR_PASTE6_2(a,b,c,d,e,f)
+#define MR_PASTE6_2(a,b,c,d,e,f)  a##b##c##d##e##f
+#define MR_PASTE7(a,b,c,d,e,f,g)  MR_PASTE7_2(a,b,c,d,e,f,g)
+#define MR_PASTE7_2(a,b,c,d,e,f,g)        a##b##c##d##e##f##g
+
+#define Declare_entry(a) 
+#define Declare_struct(a) 
+
+#define MR_BOX_INT(a) mercury::runtime::Convert::ToObject(a)
+#define MR_NULL 0
+#define MR_MAYBE_STATIC_CODE(a) \
+	MR_BOX_INT(mercury::runtime::TempHack::get_ftn_ptr_##a())
+#define ENTRY(a) a
+#define MR_STRUCT_INIT(a) 
+#define MR_STRUCT_INIT_END(a) 
+#define MR_CLASS_INIT(a) \
+    static MR_Word a(void) { \
+        System::Object *arr[] = { 
+#define MR_CLASS_INIT_END(m, f, i)             \
+        }; return arr;                      \
+        }                                   \
+        static MR_Word f = i();  \
+        static MR_Word MR_PASTE2(m, f) = i();
+
+#define MR_string_const(a, s) ((MR_String) a)
+#define MR_TYPECTOR_REP(a) MR_BOX_INT(mercury::runtime::Constants::a)
+#define MR_RTTI_VERSION MR_BOX_INT(1)
+
+#define MR_TYPECTOR_REP_ENUM_val 			0
+#define MR_TYPECTOR_REP_ENUM_USEREQ_val 		1
+#define MR_TYPECTOR_REP_DU_val				2
+#define MR_TYPECTOR_REP_DU_USEREQ_val			3
+#define MR_TYPECTOR_REP_NOTAG_val			4
+#define MR_TYPECTOR_REP_NOTAG_USEREQ_val		5
+#define MR_TYPECTOR_REP_EQUIV_val			6
+#define MR_TYPECTOR_REP_EQUIV_VAR_val			7
+#define MR_TYPECTOR_REP_INT_val		    		8
+#define MR_TYPECTOR_REP_CHAR_val		    	9
+#define MR_TYPECTOR_REP_FLOAT_val			10
+#define MR_TYPECTOR_REP_STRING_val			11
+#define MR_TYPECTOR_REP_PRED_val		    	12
+#define MR_TYPECTOR_REP_UNIV_val		    	13
+#define MR_TYPECTOR_REP_VOID_val		    	14
+#define MR_TYPECTOR_REP_C_POINTER_val			15
+#define MR_TYPECTOR_REP_TYPEINFO_val			16
+#define MR_TYPECTOR_REP_TYPECLASSINFO_val		17
+#define MR_TYPECTOR_REP_ARRAY_val			18
+#define MR_TYPECTOR_REP_SUCCIP_val			19
+#define MR_TYPECTOR_REP_HP_val				20
+#define MR_TYPECTOR_REP_CURFR_val			21
+#define MR_TYPECTOR_REP_MAXFR_val			22
+#define MR_TYPECTOR_REP_REDOFR_val			23
+#define MR_TYPECTOR_REP_REDOIP_val			24
+#define MR_TYPECTOR_REP_TRAIL_PTR_val			25
+#define MR_TYPECTOR_REP_TICKET_val			26
+#define MR_TYPECTOR_REP_NOTAG_GROUND_val		27
+#define MR_TYPECTOR_REP_NOTAG_GROUND_USEREQ_val		28
+#define MR_TYPECTOR_REP_EQUIV_GROUND_val		29
+
+
+#define MR_DEFINE_BUILTIN_TYPE_CTOR_INFO_FULL(m, n, a, cr, u, c)    \
+    Declare_entry(u)                                                   \
+    Declare_entry(c)                                                   \
+    Declare_struct(MR_STATIC_CODE_CONST struct MR_TypeCtorInfo_Struct)  \
+    MR_STRUCT_INIT(MR_PASTE5(mercury_data_, __type_ctor_info_, n, _, a) = {)   \
+    MR_CLASS_INIT(MR_PASTE4(type_ctor_init_, n, _, a))   \
+        MR_BOX_INT(a),                                              \
+        MR_MAYBE_STATIC_CODE(n##_unify),                                 \
+        MR_MAYBE_STATIC_CODE(n##_unify),                                 \
+        MR_MAYBE_STATIC_CODE(n##_compare),                                 \
+        MR_TYPECTOR_REP(cr),                                              \
+        MR_NULL,                                                           \
+        MR_NULL,                                                           \
+        MR_string_const(MR_STRINGIFY(m), sizeof(MR_STRINGIFY(m))-1),    \
+        MR_string_const(MR_STRINGIFY(n), sizeof(MR_STRINGIFY(n))-1),    \
+        MR_RTTI_VERSION,                                                \
+        MR_NULL,                                                          \
+        MR_NULL,                                                          \
+        MR_BOX_INT(-1),                                                 \
+        MR_BOX_INT(-1)                                                  \
+    MR_STRUCT_INIT_END(})                                               \
+    MR_CLASS_INIT_END(m, MR_PASTE5(__, type_ctor_info_, n, _, a), MR_PASTE4(type_ctor_init_, n, _, a))
+
+#define MR_DEFINE_BUILTIN_TYPE_CTOR_INFO_PRED(m, n, a, cr, u, c)        \
+    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO_FULL(m, m, n, a, cr, u, c)
+
+#define MR_DEFINE_BUILTIN_TYPE_CTOR_INFO(m, n, a, cr)           \
+    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO_FULL(m, n, a, cr,       \
+        MR_PASTE7(mercury::, m, ::do_unify__, n, _, a, _0),     \
+        MR_PASTE7(mercury::, m, ::do_compare__, n, _, a, _0))  
+
+#define MR_DEFINE_BUILTIN_TYPE_CTOR_INFO_UNUSED(n, a, cr)       \
+    MR_DEFINE_BUILTIN_TYPE_CTOR_INFO_FULL(builtin, , n, a, cr,  \
+        mercury__unused_0_0,                                    \
+        mercury__unused_0_0)
+
+#define MR_list_cons(List, Head, Tail)                          \
+    	do {							\
+		MR_Word _tmp;					\
+		MR_newobj((_tmp), 1, 2);				\
+		MR_objset((_tmp), 1, (Head));			\
+		MR_objset((_tmp), 2, (Tail));			\
+		List = _tmp;					\
+	} while (0)
+
+#define MR_list_nil(List)                         		 \
+    	MR_newobj(List, 0, 0);
+
+
+#define MR_list_is_cons(List)	\
+	(mercury::runtime::Convert::ToInt32((List)->GetValue(0)))
+
+#define MR_list_is_nil(List)	\
+	(mercury::runtime::Convert::ToInt32((List)->GetValue(0)) == 0)
+
+#define MR_list_head(List)	\
+	((List)->GetValue(1))
+
+#define MR_list_tail(List)	\
+	(dynamic_cast<MR_Word>((List)->GetValue(2)))
+
+#define MR_newobj(Obj, Tag, Size)                                           \
+    do {                                                                    \
+    (Obj) = System::Array::CreateInstance(				    \
+	System::Type::GetType("System.Object"), (Size) + 1);  		    \
+    (Obj)->SetValue(mercury::runtime::Convert::ToObject(Tag), 0);           \
+    } while (0)
+
+#define MR_untagged_newobj(Obj, Size)                                       \
+    do {                                                                    \
+    (Obj) = System::Array::CreateInstance(				    \
+		System::Type::GetType("System.Object"),   		    \
+	(Size));						   	    \
+    } while (0)
+
+#define MR_newobj_preboxed_tag(Obj, Tag, Size)                                           \
+    do {                                                                    \
+    (Obj) = System::Array::CreateInstance(				    \
+		System::Type::GetType("System.Object"), (Size) + 1);	    \
+    (Obj)->SetValue((Tag), 0);                               		    \
+    } while (0)
+
+#define MR_objset(Obj, Offset, Element)                                     \
+    do {                                                                    \
+    (Obj)->SetValue((Element), (Offset));                                     \
+    } while (0)
+
+#define MR_c_pointer_to_word(Obj, CPointer)                                    \
+    	MR_newobj_preboxed_tag(Obj, CPointer, 0)
+
+#define MR_word_to_c_pointer(CPointer)                                    \
+    	( (CPointer)[0] )
+
+#define MR_newenum(Obj, Tag)                                           \
+		MR_newobj(Obj, Tag, 0)
+
+#define MR_TYPEINFO_TYPE_CTOR_INFO_SLOT		0
+
+#define MR_TYPE_CTOR_INFO_ARITY_SLOT		0
+#define MR_TYPE_CTOR_INFO_UNIFY_PRED_SLOT	1
+#define MR_TYPE_CTOR_INFO_COMPARE_PRED_SLOT	3
+
+}
+
only in patch2:
--- compiler/mlds_to_il.m	2000/11/21 13:37:43	1.7
+++ compiler/mlds_to_il.m	2000/12/24 05:03:40
@@ -288,7 +288,14 @@
 		( { MaybeStatement = yes(Statement) } -> 
 			statement_to_il(Statement, InstrsTree0)
 		;
-			{ InstrsTree0 = empty }
+				% If there is no function body,
+				% generate forwarding code instead.
+				% This can happen with :- external
+			atomic_statement_to_il(target_code(lang_C, []),
+				InstrsTree0),
+				% The code might reference locals...
+			il_info_add_locals(["succeeded" - 
+				mlds__native_bool_type])
 		),
 
 			% If this is main, add the entrypoint, set a
@@ -1744,7 +1751,7 @@
 	ILType = ilds__type([], class(FullClassName)).
 
 mlds_type_to_ilds_type(mlds__commit_type) =
-	ilds__type([], class(["mercury", "commit"])).
+	ilds__type([], class(["mercury", "runtime", "Commit"])).
 
 mlds_type_to_ilds_type(mlds__generic_env_ptr_type) = il_envptr_type.
 
@@ -2181,22 +2188,22 @@
 
 convert_to_object(Type) = methoddef(call_conv(no, default), 
 		simple_type(il_generic_simple_type),
-		class_member_name(ConvertClass, id("ToObject")), [Type]) :-
-	ConvertClass = ["mercury", "mr_convert"].
+		class_member_name(il_conversion_class_name, id("ToObject")),
+		[Type]).
 
 :- func convert_from_object(ilds__type) = methodref.
 
 convert_from_object(Type) = 
 	methoddef(call_conv(no, default), simple_type(SimpleType),
-		class_member_name(ConvertClass, id(Id)), [il_generic_type]) :-
-	ConvertClass = ["mercury", "mr_convert"],
+		class_member_name(il_conversion_class_name, id(Id)),
+			[il_generic_type]) :-
 	Type = ilds__type(_, SimpleType),
 	ValueClassName = simple_type_to_value_class_name(SimpleType),
 	string__append("To", ValueClassName, Id).
 
 
 	% XXX String and Array should be converted to/from Object using a
-	% cast, not a call to mr_convert.  When that is done they can be
+	% cast, not a call to runtime convert.  When that is done they can be
 	% removed from this list
 :- func simple_type_to_value_class_name(simple_type) = string.
 simple_type_to_value_class_name(int8) = "Int8".
@@ -2281,6 +2288,28 @@
 
 %-----------------------------------------------------------------------------%
 %
+% The class that performs conversion operations
+%
+
+:- func il_conversion_class_name = ilds__class_name.
+il_conversion_class_name = ["mercury", "runtime", "Convert"].
+
+%-----------------------------------------------------------------------------%
+%
+% The mapping to the exception type.
+%
+
+:- func il_exception_type = ilds__type.
+il_exception_type = ilds__type([], il_exception_simple_type).
+
+:- func il_exception_simple_type = simple_type.
+il_exception_simple_type = class(il_exception_class_name).
+
+:- func il_exception_class_name = ilds__class_name.
+il_exception_class_name = ["mercury", "runtime", "Exception"].
+
+%-----------------------------------------------------------------------------%
+%
 % The mapping to the environment type.
 %
 
@@ -2291,7 +2320,7 @@
 il_envptr_simple_type = class(il_envptr_class_name).
 
 :- func il_envptr_class_name = ilds__class_name.
-il_envptr_class_name = ["mercury", "envptr"].
+il_envptr_class_name = ["mercury", "runtime", "Environment"].
 
 
 %-----------------------------------------------------------------------------%
@@ -2306,7 +2335,7 @@
 il_commit_simple_type = class(il_commit_class_name).
 
 :- func il_commit_class_name = ilds__class_name.
-il_commit_class_name = ["mercury", "commit"].
+il_commit_class_name = ["mercury", "runtime", "Commit"].
 
 %-----------------------------------------------------------------------------
 
@@ -2436,7 +2465,7 @@
 throw_unimplemented(String) = 
 	node([
 		ldstr(String),
-		newobj(get_instance_methodref(["mercury", "mercury_exception"],
+		newobj(get_instance_methodref(il_exception_class_name,
 			ctor, void, [il_string_type])),
 		throw]
 	).
only in patch2:
--- compiler/mlds_to_c.m	2000/12/11 04:52:46	1.73
+++ compiler/mlds_to_c.m	2000/12/24 05:03:38
@@ -10,7 +10,7 @@
 % TODO:
 %	- RTTI for debugging (module_layout, proc_layout, internal_layout)
 %	- trail ops
-%	- foreign language interfacing and inline target code
+%	- foreign language interfacing (trd: what does this mean?)
 %	- packages, classes and inheritance
 %	  (currently we just generate all classes as structs)
 
only in patch2:
--- compiler/inlining.m	2000/11/23 04:32:23	1.94
+++ compiler/inlining.m	2000/12/24 05:03:38
@@ -835,6 +835,14 @@
 		( Detism = nondet ; Detism = multidet )
 	),
 
+	% don't inline foreign_code if we are generating IL
+	module_info_globals(ModuleInfo, Globals),
+	globals__get_target(Globals, Target),
+	\+ (
+		Target = il,
+		CalledGoal = pragma_foreign_code(_,_,_,_,_,_,_) - _
+	),
+
 	% Don't inline memoed Aditi predicates.
 	pred_info_get_markers(PredInfo, CalledPredMarkers),
 	\+ check_marker(CalledPredMarkers, aditi_memo),

-- 
       Tyson Dowd           # 
                            #  Surreal humour isn't everyone's cup of fur.
     trd at cs.mu.oz.au        # 
http://www.cs.mu.oz.au/~trd #
--------------------------------------------------------------------------
mercury-developers mailing list
Post messages to:       mercury-developers at cs.mu.oz.au
Administrative Queries: owner-mercury-developers at cs.mu.oz.au
Subscriptions:          mercury-developers-request at cs.mu.oz.au
--------------------------------------------------------------------------



More information about the developers mailing list