February 02, 2005

Passing objects using .NET remoting

Following code demonstrates how to pass object (e.g. Image) using .NET remoting. The idea here to serialize object, transfer and then deserialize back. For actual class objects you can also use RawSerialize() method at the end of this post.

Server Code:

Create DLL with following code (Project - serverObject, class name - streamer.cs)

Note : This DLL is shared between client and server. (You need to copy this dll on client machine)

Add following method:

public byte[] getImageBytes(){

string strImagePath=@"C:\unit73.jpeg";

MemoryStream objMemStr = new MemoryStream();

Image objImg = new Bitmap(strImagePath);
objImg.Save(objMemStr, ImageFormat.Jpeg);

return objMemStr.GetBuffer();
}



Create Server (Console Project) with following code: (Project - ServerStarter)


[STAThread]
static void Main(string[] args)
{
TcpChannel channel = new TcpChannel(54321); //Create a new channel
ChannelServices.RegisterChannel (channel); //Register channel
RemotingConfiguration.RegisterWellKnownServiceType(typeof(serverObject.streamer),"streamer",WellKnownObjectMode.Singleton);
Console.WriteLine ("Server ON at port number:54321");
Console.WriteLine ("Please press enter to stop the server.");
Console.ReadLine ();
}


Client code:

Note : Add Refrence (copy dll on machine) to serverObject dll.

private void DisplayImage(){
TcpChannel channel = new TcpChannel (54322); //Create a new channel
ChannelServices.RegisterChannel (channel); //Register the channel
//Create Service class object
streamer svc = (streamer) Activator.GetObject (typeof (streamer),"tcp://localhost:54321/streamer"); //Localhost can be replaced by

byte [] imgData = svc.getImageBytes();

Image objDilbertImg;
MemoryStream objMemStr = new MemoryStream();

//StreamReader objStream = new StreamReader(@"C:\myimage.jpeg", Encoding.ASCII);
objMemStr.Write(imgData,0,imgData.Length);
objDilbertImg = new Bitmap(objMemStr);
pictureBox1.Image = objDilbertImg;
pictureBox1.SizeMode = PictureBoxSizeMode.StretchImage ;
ChannelServices.UnregisterChannel (channel);
}



You can also use RawSerialize() method in streamer class to stream the data. In such case you have to change client/server code accordingly.

private byte[] RawSerialize( object anyObject )
{
int rawsize = Marshal.SizeOf( anyObject );
IntPtr buffer = Marshal.AllocHGlobal( rawsize );
byte[] rawdata = new byte[ rawsize ];
Marshal.Copy( buffer, rawdata, 0, rawsize );
Marshal.FreeHGlobal( buffer );
return rawdata;
}