How to make perfect client-server communication program using iPhone and C# - c#

I have built a iPhone application, which capture the voice and streamed to server using NSOutputStream instance. Once the stream stops, iPhone sends a text message as "---end---" to the server and starts to listing on NSOutputStream.
When server(built using C#) captured the "---end---" message, it does some processing and write back the text to the client. Once client receive the end message it close NSOutputStream and NSInputStream connections.
Every time, before send the "end" message I put the application to sleep for 0.5 sec. Then I can guaranteed the end message is not mix with other data. This system works well with the simulator and in my network (100Mbps).
However, when I connected the whole application to slow network (1.2 Mbps), the whole communication went vanished. Sometimes the end message is mixing with voice data as similarly the end message is concatenated with the text sending from the server.
But when I change the thread sleeping time for 3 sec in server and client, the error occurrence rate was reduced.
I know that this might be a issue of design my network client-server communication protocol. But I cannot figure out how to fix it exactly.
Can anybody explain me, how can I overcome from these issues ?

Figure out how to wait for the transfer to complete, instead of adding an arbitrary sleep time.

Related

Sync clock over ethernet using custom message

I have a setup where I have some PLC's connected to a windows PC, I am doing the code on the windows PC in C#. I want to be able to sync the clock of the PLC's with the PC.
The PLC don't support the windows built in time sync services, so I need to do it myself.
My first idea is to just send a message (TCP) to the PLC periodically containing the time of the windows PC. I don't need to be precise on milliseconds, a second would be fine. So my first guess is that this would be enough.
But now I think that if it wasn't so difficult it could be cool to make something that took the time of sending a message on TCP into account to get a more precise sync.
Any ideas on how to achieve that?
Since TCP has some overhead and the amount of data is pretty small, why not use UDP?
Send a UDP request to the server, receive the current time as answer and use half of the answer time as transport delay - rough but easy to do.

Why doesn't the server receive all UDP packets in a local transfer using sockets in C#?

I have a server and a client application where the client sends a bunch of packets to the server. The protocol used is UDP. The client application spawns a new thread to send the packets in a loop. The server application also spwans a new thread to wait for packets in a loop.
Both of these applications need to keep the UI updated with the transfer progress. How to properly keep the UI updated has been solved with this question. Basically, both the server and client applications will raise an event (code below) for each loop iteration and both will keep the UI updated with the progress. Something like this:
private void EVENTHANDLER_UpdateTransferProgress(long transferedBytes) {
receivedBytesCount += transferedBytes;
packetCount++;
}
A timer in each application will keep the UI updated with the latest info from receivedBytesCount and packetCount.
The client application has no problems at all, everything seems to be working as expected and the UI is updated properly every time a packet is sent. The server is the problematic one...
When the transfer is complete, receivedBytesCount and packetCount will not match the total size in bytes sent nor the number of packets the client sent. Each packet is 512 bytes in size by the way. The server application is counting the packets received right after the call from Socket.ReceiveFrom() is returned. And it seems that for some reason is not receiving all the packets it should.
I know that I'm using UDP which doesn't guarantee the packets will actually arrive at the destination and no retransmission will be performed so there might be some packet loss. But my question is, since I'm actually testing this locally, both the server/client are on the same machine, why exactly is this happening?
If I put a Thread.Sleep(1) (which seems to translates to a 15ms pause) in the client sending loop, the server will receive all the packets. Since I'm doing this locally, the client is sending packets so fast (without the Sleep() call) that the server can't keep up. Is this the problem or it may lie somewhere else?
'If I put a Thread.Sleep(1) (which seems to translates to a 15ms pause) in the client sending loop, the server will receive all the packets'
The socket buffers are getting full and the stack is discarding messages. UDP has no flow-control and so, if you try send a huge number of datagrams in a tight loop, some will be discarded.
Use your sleep() loop, (ugh!), implement some form of flow-control on top of UDP, implement some form of non-network flow-control, (eg. using async calls, buffer pools and inter-thread comms), or use a different protocol with flow-control built in.
If you shovel stuff at the network stack faster than it can digest it, you should not be surprised if it throws up occasionally.

CF app two way communications with server

Users in field with PDA's will generate messages and send to the server; users at the server end will generate messages which need to be sent to the PDA.
Messages are between the app and server code; not 100% user entered data. Ie, we'll capture some data in a form, add GPS location, time date and such and send that to the server.
Server may send us messages like updates to database records used in the PDA app, messages for the user etc.
For messages from the PDA to server, that's easy. PDA initiates call to server and passes data. Presently using web services at the server end and "add new web reference" and associated code on the PDA.
I'm coming unstuck trying to get messages from the the server to the PDA in a timely fashion. In some instances receiving the message quickly is important.
If the server had a message for a particular PDA, it would be great for the PDA to receive that within a few seconds of it being available. So polling once a minute is out; polling once a second will generate a lot of traffic and, maybe draim the PDA battery some ?
This post is the same question as mine and suggests http long polling:
Windows Mobile 6.0/6.5 - Push Notification
I've looked into WCF callbacks and they appear to be exactly what I want however, unavailable for compact framework.
This next post isn't for CF but raises issues of service availability:
To poll or not to poll (in a web services context)
In my context i'll have 500-700 devices wanting to communicate with a small number of web services (between 2-5).
That's a lot of long poll requests to keep open.
Is sockets the way to go ? Again that's a lot of connections.
I've also read about methods using exchange or gmail; i'm really hesitant to go down those paths.
Most of the posts i've found here and in google are a few years old; something may have come up since then ?
What's the best way to handle 500-700 PDA CF devices wanting near-instant communication from a server, whilst maintaing battery life ? Tall request i'm sure.
Socket communication seems like the easiest approach. You say you're using webservices for client-server comms, and that is essentially done behind the scenes by the server (webservice) opening a socket and listening for packets arriving, then responding to those packets.
You want to take the same approach in reverse, so each client opens a socket on its machine and waits for traffic to arrive. The client will basically need to poll its own socket (which doesnt incur any network traffic). Client will also need to communicate its ip address and socket to the server so that when the server needs to communicate back to the client it has a means of reaching it. The server will then use socket based comms (as opposed to webservices) to send messages out as required. Server can just open a socket, send message, then close socket again. No need to have lots of permanently open sockets.
There are potential catches though if the client is roaming around and hopping between networks. If this is the case then its likely that the ip address will be changing (and client will need to open a new socket and pass the new ip address/socket info to the server). It also increases the chances that the server will fail to communicate with the client.
Sounds like an interesting project. Good luck!
Ages ago, the CF team built an application called the "Lunch Launcher" which was based on WCF store-and-forward messaging. David Kline did a nice series on it (here the last one, which has a TOC for all earlier articles).
There's an on-demand Webcast on MSDN given by Jim Wilson that gives an outline of store-and-forward and the code from that webcast is available here.
This might do what you want, though it got some dependencies (e.g. Exchange) and some inherent limitations (e.g. no built-in delivery confirmation).
Ok, further looking and I may be closer to what I want; which I think i a form of http long poll anyway.
This article here - http://www.codeproject.com/KB/IP/socketsincsharp.aspx - shows how to have a listener on a socket. So I do this on the server side.
Client side then opens a socket to the server at this port; sends it's device ID.
Server code first checks to see if there is a response for that device. If there is, it responds.
If not, it either polls itself or subscribes to some event; then returns when it's got data.
I could put in place time out code on the server side if needed.
Blocking on the client end i'm not worried about because it's a background thread and no data is the same as blocking at the app level; as to CPU & batter life, not sure.
I know what i've written is fairly broad, but is this a strategy worth exploring ?

Webservice for serial port devices

I want to create a remote webservice for an application that is now avaliable only localy. This application controlls three devices (each is controlled separately) connected on serial port. The problem is that I don't know how to take care of passing back information that a device return requested data. For example - I send move command to the motion device (which is very slow and can take a minute or more). Can I just set a big timeout on the client side (and server side) and return for example a true/false if operation is completed or is this a bad idea? Is SOAP with big timeouts ok?
And the other question is if Mono on Linux (Ubuntu 9.10, Mono 2.4) is stable enought for making a web service or should I chose Java or some other language?
I'm open for recommendations.
Thanks for your help!
Using big timeouts is not a good idea. It wastes resources on both the server and the client and you will not be able to detect a "true" timeout condition, when the server is unavailable for example, before the allocated timeout expires.
You really have two options. The first is to use polling. Return immediately from the motion request command, acknowledging the reception of the command (and not the completion of it). Then send requests in regular intervals, asking whether the command is completed or not.
The other alternative requires the client to be able to register a callback endpoint, which the server will call when the motion completes. This makes the whole process asynchronous, but requires the client to be able to operate in server mode. This is very easy to do with WCF - I don't know however if this functionality is available in Mono.
Not directly related to your question..., but consider com0com and its friends hub4com and com2tcp.

Getting a notification when my system freezes

I have a minor problem where my (new) computer tends to completely freeze up. Am not sure when it happens exactly but the 6 times that it did happen during the last 4 weeks, it could have been related to a very long rendering task that eats up lots of RAM. (Am actually pretty sure that this rendering engine is causing this problem.) Anyway, I don't really care about what causes the problem. I can repeat it by having the same image rendered again and waiting about 4 hours for it to finish. And I can avoid it by making a minor adjustment to the rendered image which somehow seems to solve it all. It's likely a bug in the rendering engine.
And when I say Freeze, I mean that everything stops responding. Keyboard, mouse, disks, they all just stop and the image on my screens are frozen. I don't get a BSOD or automated reboot.
I don't mind the freeze-up, but I would like to receive a warning when the system does freeze up. So I was thinking about a simple solution that should warn me when it does freeze up again. To do so, I want to use an old SmartPhone (HP IPAQ) which runs Windows Mobile 6 and connect it to my computer through one of the USB ports. It would just continue to communicate with my computer to check if it's still alive. When the computer doesn't respond for 5 minutes, it will assume the system is frozen and would have to send a signal to me. Basically, I want it to send me an SMS message to my other phone. Well, consider the SmartPhone to be a kind of lifeguard...
Anyways, I am quite familiar with software development, just don't know where to start with this application. I will be using the .NET Compact Framework and need some pointers in the right direction to do the following:
1) How to connect to a service on another PC using the USB connection and not some wireless Internet connection? (And definitely NOT any Internet over GSM options, since it's just a prepaid card that I'm using for this phone.)
2) How to send an SMS message from this phone to my other phone?
3) Are there already some existing solutions similar to this thing I just came up with, which could save me some time programming?
I used to have an iPaq pocket pc and based on what i remember when you hook them up to the pc they pick up an IP address.
That IP address is the key to your problem,
your computer could ping your pocket pc's ip as a heartbeat. that way you can be sure that you aren't going through GSM since the Desktop is calling the handheld. How to: Create a Socket Listener your socket listener would be listening on your pocket pc if it doesn't get any messages in a set period of time it would trigger the alert winch would send out your SMS.
You could also do the reverse, where your pocket pc would be pinging your desktop, just make sure that you are using the local IP to avoid traffic over GSM
Sending SMS using compact framework
Send SMS Sample
1) You can connect to a USB port as a COM port - many examples on how to do this especially around using GPS. Write an app for your pc to listen to USB for a message and respond. Write the app on the phone to periodically send a message to the PC and get a response.
2) There should be an API for the phone to send an SMS.
3) Not that I know of, the closest being anything that communicates on USB such as I mentioned with GPS-enabled devices.
Good luck - I know (since I have worked with all the technologies you are talking about) that I wouldn't have a problem making this, but for those without that experience it could get tricky.

Categories