PocketPC SerialPort and turning off/on the device
Hi,
Here a simple C# example that reads data from a GPS Device
Assume two Buttons on the form and one Textbox.
Further a SerialPort with the DataReceived Event handled in the form.
| |
public classForm1 :Form { publicdelegatevoidSetText(string strPar); publicSetText myDelegate;
public Form1() {InitializeComponent(); } privatevoid Form1_Load(object sender,EventArgs e) { myDelegate =newSetText(SetTheText); serialPort1.BaudRate = 4800; serialPort1.Handshake = System.IO.Ports.Handshake.None; }privatevoid serialPort1_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e) { string strErg=serialPort1.ReadExisting(); this.Invoke(this.myDelegate,newobject[] { strErg }); }privatevoid SetTheText(string strText) { textBox1.Text=strText; }privatevoid btnOpen_Click(object sender,EventArgs e) { serialPort1.Open(); }privatevoid btnZu_Click(object sender,EventArgs e) { serialPort1.Close(); }
|
When i turn the power of the device off and back on -- there comes no data from the SerialPort.
After Close(); and Open(); it works again.
Is this by design (so I have to handle power up events) or a problem?
Cheers
Manfred
[4692 byte] By [
ManniAT] at [2008-2-5]
Hi Manfred,
Regarding the issue, do you mean that the DataReceived event of the SerialPort class works properly until you power off the device and then switch it back on, when the event does not fire until you close and re-open the port?
Cheers,
Anthony
Hi Anthony,
I mean that after power off/on only rare data (or nothing) is sent from the serial port.
Or in other words - I don't think the event isn't fired correctly.
Because (sometimes) the event is fired and since I read all the received data it should then bring a lot of text in my textbox. But it does not.
To see all whats coming just replace the textBox1.Text=... with textBox1.Text+=
So I think this has the reason in not receiving (or almost not) anymore from the comport.
I use an IPAQ 3070 clean setup (hardreset) with just this onyl one app installed on it.
The solution would be easy if MS had provided a "PowerEvent" for the PPC.
So we can do two three things -
a.) hope that this will be fixed
b.) write a simple driver (drivers get Power notifications) an let it inform my app
c.) write some kind of watchdog
Solution c.) is possilbe in this case since a GPS device sends at least n bytes per second - and if those bytes are not receive - i just have to close / reopen the SerialPort.
The only problem with it is if a user remove the device from the (lets say) car cradle I will also not receive any data - and reopen would not help.
I couldn't find any "Craddled status" (or "OnAuxPower status") in the .NET CF - so it's hard to detect whats going on.
And last not least if I use (for an example) a BarcodeReader which doesn't send data continuously this thing wont work too.
So we had a lot of hope for the new .NET CF 2.0 but since extreme essential things
--power notfications
--status informations
--reliable SerialPort class :-)
are still missing we have to go on using our "Private driver" which notifies us about power status changes.
Cheers
Manfred
Hi Manfred,
Thank you for your information. We will definitely consider your suggestions. Did you try the RequestPowerNotifications() API in Windows CE to obtain power notifications? Also, is it possible for you to prevent power suspension on the device by P/Invoking into SystemIdleTimerReset()?
Cheers,
Anthony
Hi Anthony,
RequestPowerNotification I think is not available in PPC 2003.
So we keep on having our Driver with the notification message.
The SystemIdleTimerReset would help - but nor for a user pressing the button :-)
By the way - we made settings, that the is no "AutoOff" if Powerconnected.
And as long as the device recides in the cradle there is power. When it is removed, there is no need to stay running - since GPS Data comes also from the cradle.
To be precise - our problem is not that the device can be powered off - that is OK an usefull (save battery life).
Our problem is that the SerialPort class fails to work correct after a power on/off.
Or in other words: Assume: you feel pain when you take a breath.
Do you think it is a solution when I tell to stop breathing? 

I thank you that you tried to help me with this - aspecially the tip with RequestPowerNotification is great since (if available) could help us to prevent the thing with the "PowerNotificatioDriver".
So I would be interested to hear what MS-Guys say about that SerialPort class problems.
By the way I can solve (work around) this one. But for that http://forums.microsoft.com/msdn/ShowPost.aspx?PostID=9843 a driver wont help, since it fails to open the port.
Thankx
Manfred
Hi Manfred,
RequestPowerNotifications is available on Windows CE since 4.0, and so is available on PPC 2003 as well. NETCF V2 will not be provide managed API for power notifications, but you can create managed wrapper to obtain the power notifications and close/re-open any instances of serial port.
You can refer to my post below for codes of the managed PowerNotifications class:
http://blogs.msdn.com/anthonywong/archive/2005/06/07/426392.aspx
Cheers,
Anthony
Hi Anthony,
thanks for your response - and the code in your BLOG.
I think it is a good base to start from - my thinking that it is not available in PPC 2003 was because in the help there is no word about it.
But I will give it a try - two things I will change -- Close the Q and stop the powernotifications.
One question about your code - is there a practical reason why you dont wait infinite? Or is it just because the "simple shutdown" of the thread?
What I mean is - is there a known problem on waiting for Qs?
By the way - does this also work on Smartphones?
Thanks
Manfred
Hi Manfred,
I didn't wait infinitely in my code because there was a bug in NETCF V2 that caused the CLR to wait for a thread even if it is a background thread.
I have tried the code on PPC 2003 but not on Smartphone. I suppose the code should work on SP as well.
Cheers,
Anthony
Hi Anthony,
I ported the code to a windows app and I'm playing with it.
But your wrote about "the console add-in" in your blog.
Where can I get it?
Thanks
Manfred
Hi Anthony
I've included your code in my project http://blogs.msdn.com/anthonywong/archive/2005/06/07/426392.aspx and found that it works great on a Dell X50 running PPC 2003. I modified the code to use message boxes instead of Console and that seemed to work fine.
One thing I noticed is that since I'm using NETCF V1.1, I get a message when I try to complie regarding the t.Abort(); statement in
public void Stop()
{
done = true;
t.Abort();
}
Error Message: 'System.Threading.Thread' does not contain a definition for 'abort'
So, I just commented out 't.abort()' to get it to compile and it seems to work. My understand is that my code does not stop the power notification thread using the abort command and I'm hoping that it stops the 'DoWork' function by setting the variable done to true which terminates the infinite while loop.
Will the OS clean up this thread when the application is terminated or will threads start to accumulate in the device? If the OS will not clean up the thread, what steps should be taken to terminate the thread?
Thanks
Hello AllI
also used your code Anthony. I created a class library with event
handling that I now use in my app. If its OK with Anthony I could post
my changes here?
I don't terminate the thread either. Could this be a problem?
Cheers
Thomas
Thomas
I also added event handling to Anthony's code but it is not working as expected.
I added the following to Anthony's code
public delegate void PowerStatusChangeEventHandler (object sender, System.EventArgs e, string strPowerMessage);public event PowerStatusChangeEventHandler PowerStatusChanged;and for the case of 'power on'
case
65536:
msg = "Power On";
System.EventArgs p = new System.EventArgs();
PowerStatusChanged (this, p, msg);
break;Then in the code which loads the initial form, I added this.
PowerNotifications pn =
new PowerNotifications();
pn.Start();
pn.PowerStatusChanged += new PowerNotifications.PowerStatusChangeEventHandler(this.PowerNotifications_PowerStatusChanged);And I added this to handle the events in the main application
private void PowerNotifications_PowerStatusChanged (object sender, System.EventArgs e, string strPowerMessage)
{
if (strPowerMessage == "Power On")
code that opens the com port here
}
I'm having a couple problems.
1.) After the application runs and exits, I can't get it to run again without doing a soft reset. I'm guessing its because the thread started by power notification is still running. Not sure
2.) The other problem is the event seems to fire off correctly and my code which should re-open the com port is getting executed but I get a message the the com port is not available or still in use. I'm using the CFSerialIO.dll to manage the com port from Richard Grier
Any help would be greatly appreciated.
Hi TokenWorks
I implemented my event handling almost the same (only diffrence is that
I created an inherited class of eventargs to pass the args instead
of using a string).
I only use the power state to close the serialport wenn the PPC is turned of. Opening happens
only when the user tells my app to reopen the port to send or recieve
data. If I needed the port to be open all the time I would also first close
the port before the PPC is turned off, then reopen on the PowerOn
event, maybe this is causing your problem.
My app has no problem with exiting and reopening, even though I don't stop the thread myself.
I rewrote my app to use the .NET CF 2.0 serialport implementation, we
also used Richard Grier's com port implementation before. We rewrote
because it wasn't working on WM5.0 but it still doesn't work on WM5
because of Dells configuration of WM5.0 on the Axim :-(.
Cheers
Thomas
Hi Thomas
We discovered the solution to one of our problems yesterday, which was to put a delay before we opened the serial port after a power up event. We have a UART plugged into the CompactFlash slot and discovered the OS briefly turns on the CF slot after a power on event. We believe the OS accesses the CF card to figure out what is plugged into the CF slot and then turns off the power to the CF slot. Our problem was due to a conflict between drivers accessing the port at the same time. With the delay, we no longer get an exception stating ‘port not available or already in use’
So now our code re-opens the COM port after a power cycle but we still have an issue with being unable to re-launch the application without a soft reset after a power cycle event. If we don't have a power cycle event, then the app terminates fine but once we have a power cycle, a soft reset is required to restart the application.
When we try to install a new version of the code, we get a message stating the program is still in use or in ROM so we surmise part of the program is still running.
What is strange is this problem only starting happening once we added this power notification event. Previously, the application terminated properly and new installations or re-launching wasn’t an issue. We believe it has something to do with the COM port not being closed correctly now that this power notification code has been added to the project.
Thanks for the info on Richard Grier's code. Do you have a post or link that discusses the conflict with Dell's configuration of WM5.0 on the AXIM. We are aware of a bus timing issue with Dell X51 with WM5.0 which violates the CompactFlash specification – See http://forums.microsoft.com/MSDN/ShowPost.aspx?PostID=291568&SiteID=1 but if your using the built in COM port of the AXIM, this shouldn’t apply.
Regards