Setting up XSP to serve ASP.NET on FreeBSD

By : Scott Muc - May. 19th, 2004 (updated: Dec. 17th, 2005)

Update!

I've setup a new server running FreeBSD 6.0 and I was able to install mono from the ports collection without a problem. The port does not include XSP, so I downloaded the source from the Mono website and was able to compile and run the test site without any issues! (Dec. 17th, 2005)

Objective

I've now been doing system administration for a hosting company whose primary selling point is Asp.Net support. I've only written a couple small Asp.Net applications but the experiences were positive ones. My only dilema is that my OS of choice is FreeBSD, not Windows. The goal of this project is to be able to server Asp.Net webpages from my FreeBSD box using Ximian's Mono. At this moment there is very little documentation regarding Mono on FreeBSD, so I'm hoping that I can donate a little of my time to the Mono community and assist them getting Mono a solid foundation in the FreeBSD environment.

First Attempt

Of course the first thing I tried was to install Mono from the FreeBSD ports collection. It's been a couple weeks since the Mono beta 1 was released, but the port hasn't been updated in a while. I figured that it should allow me to do some testing so I installed the port.

	# cd /usr/ports/lang/mono
	# make && make install && make clean
  

The Asp.Net server (xsp) was not part of the mono port so I had to download the source and compile/install it on my own. This of course is trivial enough.

	$ cd /usr/local/src
	$ fetch http://go-mono.com/archive/beta1/xsp-0.13.tar.gz
	$ tar zxvf xsp-0.13.tar.gz && cd xsp-0.13
	$ ./configure --prefix=/usr/local
	$ gmake
	# gmake install
  

After reading a little bit of the xsp documentation, I tried running it in it's most basic configuration. This involves changing your directory to /usr/local/share/doc/xsp/test, and then starting the xsp server.

	$ mono /usr/local/bin/xsp.exe
	Listening on port: 8080
	Listening on address: 0.0.0.0
	Root directory: /usr/local/share/doc/xsp/test
	Hit Return to stop the server.
  

When making a request to the server, it core dumps. I've tried several of the older versions of xsp, and none of them worked. It's time to ditch the old port, and see what I can do with the current snapshots from the go-mono.com website.

Second Attempt

I was initially confused on how to install it from the snapshots because there are a couple ways to compile and install mono. Some builds require that you use an existing install of mono installed as a bootstrap (which reminds me of Java installs). Installing from the source was exactly the same as downloading/compiling/installing xsp. I had a couple problems with missing source code (abcremoval.h), but I just retrieved that file from CVS. As of the latest snapshot (May 18th), they've fixed that problem. Another quirk with the FreeBSD install from source is that you must edit the data/config file and replace libc.so.6 with whichever libc is applicable for you (which was libc.so.4 in my case). This problem has been confirmed by Miguel de Icaza in my correspondance with him on the Mono mailing list.

Mono managed to build without any errors, but the install is another story. Besides the libc mapping problem mentioned earlier, the install process would hang after the following text:

	./configure --prefix=/usr/local
	gmake
	gmake install
	...
	/bin/sh ../../mkinstalldirs /usr/local/lib
	/usr/bin/install -c -m 644 mscorlib.dll /usr/local/lib/mscorlib.dll
	MONO_PATH=. ../../mono/mini/mono --config ../../data/config
	./../gacutil.exe /i ./Accessibility.dll /f /package 1.0 /root
	/usr/local/lib
	Package exported to: /usr/local/lib/mono/1.0
	Accessibility installed into the gac (/usr/local/lib/mono/gac/)
	

After some more list activity, Paolo Molaro suggested I try the Boehm Garbage Collection library. I managed to build and install it, but the FreeBSD linker doesn't seem to accept the gc library.

	spark% gcc -lgc
	/usr/libexec/elf/ld: cannot find -lgc
	

Since Paolo thought it was a garbage collector issue I tried rebuilding mono using --with-gc=none to see if it would work. This allowed me to finally build and install the Mono beta 1 on FreeBSD!

	spark% mono --version
	Mono JIT compiler version 0.91.99.20040518, (C) 2002-2004 Novell, Inc
	and Contributors. www.go-mono.com
	        TLS:           normal
	        GC:            none
	        SIGSEGV      : normal
	        Globalization: none
	

Now it's time to rebuild xsp-0.13 and see if that works. I went through the same paces to get that done, and ran the xsp program and sent an HTTP request to my dev box.

	spark% mono /usr/local/bin/xsp.exe
	Listening on port: 8080
	Listening on address: 0.0.0.0
	Root directory: /usr/local/share/doc/xsp/test
	Hit Return to stop the server.
	System.ExecutionEngineException: No GCHandle support built-in
	in (unmanaged) (wrapper managed-to-native) System.Runtime.InteropServices.GCHandle:GetTargetHandle (object,int,System.Runtime.InteropServices.GCHandleType)
	in <0x00004> (wrapper managed-to-native) System.Runtime.InteropServices.GCHandle:GetTargetHandle (object,int,System.Runtime.InteropServices.GCHandleType)
	in <0x00023> System.Runtime.InteropServices.GCHandle:.ctor (object,System.Runtime.InteropServices.GCHandleType)
	in <0x0001b> System.Runtime.InteropServices.GCHandle:Alloc (object,System.Runtime.InteropServices.GCHandleType)
	in <0x00050> System.WeakReference:AllocateHandle (object)
	in <0x00026> System.WeakReference:.ctor (object,bool)
	in <0x00012> System.WeakReference:.ctor (object)
	in <0x0002b> System.Runtime.Remoting.ClientIdentity:set_ClientProxy (System.MarshalByRefObject)
	in <0x00323> System.Runtime.Remoting.RemotingServices:GetOrCreateClientIdentity (System.Runtime.Remoting.ObjRef,System.Type,object&)
	in <0x0001c> System.Runtime.Remoting.RemotingServices:GetRemoteObject (System.Runtime.Remoting.ObjRef,System.Type)
	in <0x00074> System.Runtime.Remoting.RemotingServices:GetProxyForRemoteObject (System.Runtime.Remoting.ObjRef,System.Type)
	in <0x0010f> System.Runtime.Remoting.RemotingServices:Unmarshal (System.Runtime.Remoting.ObjRef,bool)
	in <0x00010> System.Runtime.Remoting.RemotingServices:Unmarshal (System.Runtime.Remoting.ObjRef)
	in <0x0012e> System.Runtime.Remoting.RemotingServices:GetDomainProxy (System.AppDomain)
	in <0x00079> System.AppDomain:CreateDomain (string,System.Security.Policy.Evidence,System.AppDomainSetup)
	in <0x00216> System.Web.Hosting.ApplicationHost:CreateApplicationHost (System.Type,string,string)
	in <0x00013> Mono.ASPNET.XSPApplicationServer:CreateApplicationHost (string,string)
	in <0x0016c> Mono.ASPNET.XSPApplicationServer:GetApplicationForPath (string,bool)
	in <0x000b2> Mono.ASPNET.Worker:Run (object)
	

Great... so Asp.Net doesn't work if there's no garbage collection. Which of course makes sense, but I was really hoping to see it in action. Back to the drawing board!

Third Attempt

Since it doesn't work with no GC, and it doesn't work with the included GC, I now have to resort to getting the Boehm GC to work. I've tried running ./configure with --with-gc=boehm, but it always failed saying that it could not read gc.h, and load -lgc. I've installed the Boehm GC using the source and the FreeBSD ports tree. Both installation methods placed the headers and libs with the prefix /usr/local, and the configure script didn't seem to like that. I ended up getting the configure process to run to completion by building the Boehm GC from the source and adjusting the prefix. Enabling pthreads was done to handle an issue I had later one when trying to build mono. Some function references were not in the gc libs (GC_pthread_detach was one of them).

	$ ./configure --prefix=/usr --enable-threads=pthreads
	$ make && make check
	# make install
	

After that, I reconfigured mono (./configure --prefix=/usr/local --with-gc=boehm), and that worked! Now I can finally build mono with the Boehm GC library. My first effort resulted in some errors regarding pthreads which I mentioned in the previous paragraph. After re-installing the Boehm GC library, I managed to complete the build. The results? The same problem after my second attempt. It hangs at the following line during the gmake install.

	Package exported to: /usr/local/lib/mono/1.0
	Accessibility installed into the gac (/usr/local/lib/mono/gac/)
	

Now what?


Scott Muc is a computer geek with too much time on his hands.