C# version of emserver.


April 2008,
The port of emserver to C-sharp has begun.
I'm totally new to C# so it is a struggle.
I've managed to get a simple dumb terminal working but that is a major milestone for me.


I had a curious little bug today.
Here is the fixed code.
	void ButtonClearClick(object sender, EventArgs e)
		richTextBox1.ZoomFactor= MyZoomFactor;

I allow the main text box to be zoomed from 50% to 200%.
All was fine until I clear the zoomed window.
When you clear the window the new text is un-zoomed.
So I changed the code to remember to zoom factor and apply it again after the clear function.
It didn't work.
Also if you set the zoom factor again to what you had before it didn't work.
If you changed it to something else it worked and you could then change it a second time to what you wanted.

It seems like the textbox get confused and thinks it is zoomed when it isn't and is smart enough not to apply the same zoom twice.

The work around is the set the zoom to one before applying the zoom you want.

I've noticed a little glitch.

When dumping lines 71 chars wide ( plus CR LF ) I'd get and extra linefeed every 7 lines.
If I add a delay after each line I get extra feeds every line.
It is possible I'm normally loosing LFs that should be there except when the serial buffer wraps?
(71+2)*7 is 511 one short of 2^9. The receive buffer should be 4096 bytes long.

Searching for ".NET 2.0 SerialPort BUG" shows others are having problems as well.

Apart from being annoying it may not affect me too much because in the "server" mode the packets are smaller than 512 bytes.
I'm running .NET 3.5. Hopefully the serial problem will be fixed in some future version of .net

Later... I'm seeing problems other dumps where the glitch happens more often than 511 bytes. More testing needed.

Even later... I've confirmed that the serial demo program by Noah Coad's has the same problem. link

Next day.. C# is being a pain.

To work around the problem mentioned yesterday I decided to use "serialPort1.ReadByte()" instead of "serialPort1.comport.ReadExisting()".
This fixed the problem but created others.
I now had extra line feeds on every line. EMforth sends a CR-LF and C# is no doubt doing a linefeed for the CR character and then another one for the LF character. I added the code to ignore LFs which are after a CR.

Everything worked until I sent big lots of data. With a 4K input buffer I'd loose about half the characters after around 7K was sent.

This is a dual core 3.4 gig PC and it can't keep up with 115 Kbaud serial data!

Reading bytes means either writing one character at a time to the textbox or assembling the bytes into a string first. Both work but both are slow.

I suspect it is adding the character to the string which is slow. Something uses lots of memory and I wouldn't be surprised if a new string is being created each time. Eventually the memory gets released again but this is surprisingly slow. I expected the garbage collection to be a sub-second thing but it takes many seconds.

In C or delphi I'd access the strings directly but I haven't found out how to do this in C# or if it is possible. There are demos of converting char arrays to strings but none with arrays built on the fly with unknown length.

This is annoying but not a show-stopper. In server mode it isn't going to be an issue and in dumb terminal mode you can just use a big receive buffer.

I tried using a 1 MB buffer and it seemed fine.


I give up.

I tried using an instance of stringbuilder instead of string for assembling the strings.
I expected a huge improvement but got almost none.
I was also going to try "unsafe pointers" to directly access strings.

Then I commented out the string code altogether found the CPU useage still went up to %70 and a meg or so of memory got chewed up for each test.
Even when I omit the call to the delegate altogether to CPU load remains high etc,
So there isn't much point in tweaking the string builder.

Even Coad's code which uses ReadExisting() instead of ReadByte() uses over 50% of the CPU cycles and chews up memory. I may have to take back the good things I've been saying about .NET

Image The windows performance monitor showing CPU usage spikes when my program receives blocks of serial data.

It looks like you need a super computer these days just to receive rs232.
An 8 meg 8 bit AVR micro can easily handle 500 Kbits streams in assembler code but this fast (for 08) dual core 32 bit machine can't do it in C#
We don't usually do single byte data transfers these days.
It will be interesting to see how well this runs on mono (on Windows and other OSs).

Compact framework is also of interest but I don't really expect this code to run on it as is.

I'm also wondering if the bug might be in the way richtextbox handles linefeeds.
It may simply be that the CRLF sequence is split across two ReadExisting() calls and richtextbox only suppresses the extra LF if it arrives in the same call to AppendText();

I tested it and this appears to be the case.
I've gone back to using ReadExisting(). I read into a byte array and then process it one byte at a time.
I initially set the array to 256 bytes and quickly got an out of bounds error.
It is now 4096 to match the input buffer length.

Did it work - well yes and no.
I can now receive large chunks of data without any apparent glitches - but the CPU usage is extremely high sometimes hitting 100%

Doing the same thing in hyper terminal uses well under 10% of the CPUs - I'd guess around 6%

I attempted to run the program using Mono instead of .NET
The program starts OK but no serial stuff happens and eventually the window closes.
Noah's demo doesn't run either.
These are not compiled using mono. The binaries should be compatible but maybe recompiling would fix it.

Image A screen shot of emserver2 trying to run in Mono instead of .NET

Mono has not reached ver2 yet. It is currently at 1.9.1 or ver2 beta. If all goes well my code will run in mono in the not to distant future.

My home PC has died again - another blown PSU. I might be out of action for a while...
Later, after replacing the PSU yet again and adding a UPS I found my bluehost account suspended and have had a wasted weekend sorting that out. We are back online but may need a new host.

It was also suggested I should be looking at python instead of C# so I've had a bit of a look into that.
It would be interesting to find a serial terminal in python and see what sort of CPU load it causes.

13'th Aug 08.

I tried mono-2 candidate. Much improved but serial coms don't work and nor does zoom.

My source will be posted when I get a bit further with it.

April 2009,

I tried mono2.4 and still no luck. It doesn't find the correct port and zoom still doesn't work.
I'm avoiding doing any more sharpdevel code because monodevelop is working on a windows port.
This won't help me too much unless serial coms starts working properly.

The next major mono release is expected to be in September 2009.

June 2009,

My GUI "runs" under mono on ubuntu 9.04 but dies when I try to open the COM or USB serial port.
Zoom doesn't work either.


Created by eddie. Last Modification: Friday 19 of June, 2009 09:56:35 AEST by eddie.

Main Index

Switch Theme


System Administrator, 13:56 AEST, Sun 07 of Aug, 2016: upgrading to tiki 15.2
eddie, 19:31 AEST, Sat 06 of Aug, 2016: This website is now served from Brisbane - in a Binarylane cloud.
System Administrator, 16:07 AEDT, Wed 06 of Mar, 2013: More f'n spam. No more anon posting from now on.
Anonymous, 18:44 AEDT, Mon 04 of Mar, 2013: deleted
Anonymous, 08:36 AEDT, Sun 03 of Mar, 2013: Very nice site!

Last-Visited Pages

Online Users

62 online users