Click here to Skip to main content
Click here to Skip to main content

Fundamentals about data communication using socket with SocketPro

, 23 Feb 2002
Rate this:
Please Sign up or sign in to vote.
Socket, Data communication, internet/intranet, non-blocking


This short article is written for telling you fundamentals about SocketPro, which helps you quickly write super client and server applications based on internet/intranet socket. It also comments on other technologies such as DCOM, Corba and Java Bean/RIM. These comments will help you understand the design principles of SocketPro. It is expected that you are a professional with development of distributed applications across machines. If you have any doubts, concerns and comments, please send them to UDAParts at

Two data communication patterns using socket

To understand the design principle of SocketPro, you'd better understand and compare the following two data communication patterns between a client and a server. Once you understand the two patterns, it is highly recommended that what data communication patterns are used with other popular technologies, DCOM/MTS, Cobra and Java Bean/RIM. You could think the data movement efficiency over internet/intranet with these popular technologies rooted on socket. In order to better understand the two data communication patterns, you should be also familiar with socket. If not, please see the site.

Patterns.bmp (287910 bytes)
Figure 1. Two patterns of communication between a server and a client using socket.

Pattern 1
A client sends one request to a server, and stays still and waits (blocking/synchronous) for one returned result from the server. It is really easy for you to understand the communication mechanism.
Pattern 2
It is slightly more complicate. Basically, a client posts n (n=1, 2, 3, .... or more) requests into a buffer of the local client machine and is immediately released (non-blocking/asynchronous) for processing other user requests. Socket stack sends all of requests to a buffer of a remote server at a proper time, and later a server application uses the data inside the buffer to process all of requests by distributing/assigning all of requests into different threads/queues. All of threads/queues processes their assigned requests independently and in parallel. Whenever a request is finished, the returned result is posted into a buffer of the server machine. Once the buffer collects an enough number of binary data or at a specific time frame, the server socket sends the buffer containing multiple returned results using one full packet back to the client. The client is automatically singled when the returned results arrives at the client machine, and retrieves returned results. As you can see with pattern 2, if the network is considered as a water channel, the requests are continuously flowed to a server through one channel, the multiple requests are processed in parallel, and returned results are continuously flowed back to a client through the other channel. Sending and processing could happens concurrently at client and server sides if multiple requests are available.

Pattern 2 has following advantages over pattern 1:

  1. Efficient data movement over network:    

    In average, a client call just sends about a binary data with size of 50 bytes to a server for a request, and gets a returned binary result with size of 50 bytes too. On an Ethernet network, the MTU (Maximum Transmission Unit) for TCP is 1460 bytes. If the pattern 1 is used with your applications, each of round trip can't fully use one data packet. The net efficiency,  which is calculated from the size of transferred binary data divided by MTU, is less than 0.035, and most of packet is empty and wasted. The efficiency is just too low, and far way from 1! As you can see, if your server supports many clients, such a low net work efficiency will kill the whole network system. However, if your applications use pattern 2, the situation could be different. If a client sends multiple requests to a server, Nagle algorithm or your code is able to coalesce all of requests into a big one with one full package (1460), and the server assigns multiples requests into different threads/queues for processing. If all of requests are not lengthy actions, all of returned results can be also sent back to the client with one full package. The client sending, server processing and server sending could be happens at the same time and in parallel if enough requests originates from a client. As you can see, the net efficiency can be a data between 1 and 0.035 with pattern 2. The more requests from a client, the higher the net efficiency with pattern 2.

  2. Client graphic user interfaces never frozen:    

    Unlike in-process and in-machine calls, cross machine calls are much slower. The time of a round trip is 2.5 ms at the best for most of net hardware. Usually, it is around 30 ms per call. If your client has to send 30 calls to a server continuously, your client user interfaces could be frozen and be dead for about one second. If a request is a lengthy action, the server has to spend a long time to process. For example, your server application starts a MTS object, which typically costs you 2 seconds or more. Many more examples can be given with authentication, database accessing, email accessing, and others. As you can see, if you use the pattern 1 for moving data over internet, your client application runs badly. In order to solve this problem, you must design your project very carefully so that the number of round-trips must be minimized. If not, your whole network system runs slow if many client applications are connected to the server application. If your applications use the pattern 1, in many cases you must use threads to do background work and send requests to a server for processing in order to prevent graphic user interfaces from being frozen. It is a common way to do so with all of painful thread problems such as data synchronization, dead lock, and messy in coding logical. If your client applications have too many threads, these problems will certainly hurt you when an application becomes large and complicate. Right? In comparison to the pattern 1, Pattern 2 releases a client application immediately after the client posts a set of requests into a local buffer of the client machine. All of graphic user interfaces functions immediately and correctly because the pattern 2 uses non-blocking mode. There are no stay-still and waiting between a sending and a returning. The client application just picks up an event sent from a client socket if one or a set of returned results arrive in the buffer of the client machine. This feature is actually very important for your client application development. You don't have to use threads now. Actually, there is no necessity at all to use a threads for data communication over network if your application uses the pattern 2. As you can imagine, all of threads problems are avoided. The end result dramatically reduces the complexity of your client codes, data synchronization and dead lock etc.

  3. Coding logic

    Pattern 1 is better in coding logical sometimes, but not always. If your client applications are not windows, pattern 1 will give your better coding logical. However, if your clients are window applications, pattern 2 is more proper to you because pattern 2 is naturally in accordance with window events. 

By default, SocketPro uses the pattern 2 for fast moving data on intranet and internet. It guarantees that data movement over internet or intranet is the most efficient. Additionally, SocketPro also guarantees that your client applications can reduce or completely avoid use of any worker threads in window development environment for exchanging data between a client and a server. Besides, SocketPro enables your applications to have multiple socket instances and connections from a client to a server, and all of instances and connections run independently and in parallel from ONE THREAD ONLY without blocking graphic user interfaces. The focus here is words, multiple, parallel and one thread. At the last, all of client function calls, which lead to data movement over internet, can be switched between blocking and non-blocking modes at your will. This is another particular advantage. It is hard to get this feature from other technologies, MS DCOM/COM+, Java Bean/RMI, and Corba.

It is time to comment on other technologies. Do you know what pattern is used with DCOM/MTS/COM+, Corba and Java Bean/RMI? DCOM/MTS/COM+ definitely uses the pattern 1 to move data over network. It is estimated that all of other technologies use the pattern 1 too. If you have network tools, you could verify it. Our test results show that under all cases SocketPro runs much faster than DCOM. If lots of requests need to be sent to a server, SocketPro could be easily 30 or more times faster than DCOM. All of these technologies highly recommend three-tier distribution systems, and push all (or as many as possible) of logical operations in the middle tier. The essence is to avoid bad data traffic between a client and a server over internet/intranet, and pattern 1 just can't use a network system efficiently. If you push all of logical operations into middle tier, you must deeply understand all of details of your projects. If you are really able to do so, your client applications will lack flexibility and extensibility. Whenever you want to add a feature to a client, you'd better reconsider the design of middle tier components. If your applications follow the pattern 2, the design of your project is less important, and adding more requests doesn't necessarily add extra data trips over expensive network, because pattern 2 coalesces all of requests into one whenever possible by default with non-blocking mode. 

Server side development with SocketPro

Even though your client applications send a set of requests into a server with pattern 2, your client applications may take too long time to get expected results. To get returned results fast, the server application must be carefully designed. Traditionally, the server applications are multithreaded with a thread pool. SocketPro has a multithreaded server component (NetBaseR.dll) running with multiple message queues for fast processing multiple requests in parallel. It is designed according to the following two fundamental points.

  1. How much time a server application needs to process a request from a client.

    No matter what a request is, it is always either slow or fast to be processed. Usually, when you write a server side function, you already know if the request needs a long time to be processed. At an extreme case, you know if the processing is lengthy or quick action at run time only.

  2. What dependency relationships among different requests

    Considering two requests from a client with lengthy actions, the two requests can be processed using two threads/queues if they are totally independent on each other. Here is an example. A client sends two requests to a server for resolving host name and ip address. There are two functions, gethostbyaddr and gethostbyname to be used for processing. You can use two threads/message queues to process them in parallel because there is no dependency between the two function calls. In many cases, one request must be processed after or before the other. For such cases, the two requests must be processed sequentially using one thread only. Here is an example. When you want to access a database, you send two requests to a server with one big stream. The first request is to open a session to the database, the second one is to open a query for records. Both the two requests could be lengthy actions. They must be processed using one thread/queue only, because the second request can be processed only after the first one is successfully processed.

How does SocketPro create and manage threads/queues? What functions and roles do they have? How many threads/queues are created? Basically, SocketPro creates them automatically according to your defined data structures, which describe method ids (requests) and method dependency relationships. Your code doesn't have to create any thread/queue. SocketPro has one main thread/message queue having the following roles:

  1. Main thread/message queue is responsible to listen all of connection requests from different clients, dynamically create and destroy various socket class objects, and close socket connections.
  2. Main thread/message queue is responsible to get all of socket events, and routes these events to different socket class objects, corresponding to different client socket sessions. Main thread/message queue also accepts all of messages from other threads/message queues.
  3. All of requests, which can be quickly processed no matter whether they are from either same or different clients, are processed with the main thread/message queue.
  4. Main thread/message queue creates and kills all of worker threads/message queues, and posts related messages (requests) from the main thread/queue to each of worker threads/message queues for processing.
  5. Main thread/message does decryption and authentication for internet/intranet security.

In regards to worker threads/message queues, they are created for processing one request (one method) or different requests (different methods). All of these requests are lengthy actions. In regards to how many threads/message queues are created, it depends on if a lengthy action request is already called and how your code defines dependency relationships among different lengthy action requests. If no lengthy action requests are called, no thread/message queue is created by the main thread/message. If all of lengthy action requests are dependent on each other, one thread/message queue is created only at most. If some of these lengthy actions are grouped according to dependency, the number of threads/queues are created according to your defined structures at most. Besides, SocketPro has a feature to automatically kill idle threads/message queues for releasing resources and reducing thread context switch. This short article just gives you basic ideas. For details, UDAParts will show you how to code with tutorial samples. However, these basic rules are very important. From the view of clients, all of requests from one socket or different socket connections can be processed in parallel.

Usually, a server application is difficult to be created because of using threads. Data synchronization and dead lock must be considered and carefully planned. SocketPro solves these problems for you. In most cases, you will not have to create any thread/message queue at all. Additionally, SocketPro uses the main thread/message queue to route various messages to different threads/queues, and your code uses these messages to process and return results to clients.

How does SocketPro handle synchronization of socket? A socket has two channels (sending and receiving) as show in the figure 1. Receiving and sending channels can run independently. There must be some ways to synchronize them separately. Otherwise, receiving and sending data could be damaged because of multiple threads or not efficient. SocketPro handles this problem very well. Simply you just can't damage receiving and sending data with SocketPro.

What work do you need to do? Your code just needs to do following kind of jobs.

  1. Define class and method ids, and tell SocketPro what requests are lengthy actions and what requests are quick actions, and set up one (at most cases) or more (at extreme cases) structures.
  2. Code functions to process your requests.

That is all! No more!

In short, SocketPro is able to process multiple requests in batch from a client and send multiple results in batch back to the client for efficient use of network, while the client is sending another batch of requests. In order to speed up processing, all of requests are assigned into different threads/message queues for parallel processing according to SocketPro specific rules. SocketPro provides mechanism to eliminate side effects with threads, such as data synchronization, dead lock and messy coding logical, for reducing the complexity of developing various server side services. In comparison with other technologies, SocketPro doesn't have any intermediate object, which benefits SocketPro somewhat in performance. However, the most important fact is that SocketPro is written on pattern 2 but other technologies on pattern 1. 

Client side development with C/C++, Java, DotNet, VB, Perl and others

Currently, SocketPro is written from winsock 2 using its specific socket functions. By default, a client socket runs in non-blocking mode using pattern2. A window client application can easily create multiple socket connections to a server, and all of these connections run in parallel for obtaining different services from a server without creating one thread. If possible, you should use this feature to speed up your client application. Here is an example. Suppose that your client application needs to process file exchange and also to update data into a backend database through a SocketPro-based server, you could open two socket connections to the middle tier, use one connection for handling accessing file, and the other for updating data with non-blocking mode. If necessary, you could switch socket to blocking mode for simple coding logical. However, it is highly recommended that your window application use non-blocking mode for the best performance as much as possible. It is very simple to use non-blocking/asynchronous mode in window platforms (not Win CE), as shown from samples with SocketPro package. Particularly, SocketPro also lets a client socket configure its server peer socket like enabling/disabling Nagle algorithm, setting socket receiving and sending buffers and setting other socket optional parameters, etc. This feature can further improves your network computation.

Socket is created for moving a stream of binary data across machines with different platforms. Both client and server can run with any platforms, such as Window, UNIX, Macintosh, Linux, and others. Additionally, the development tools can be any language like C/C++, Java, DotNet, VB, Perl and others able to handle binary data. The independence of socket application is excellent in comparison with other technologies.


A socket-based software component, SocketPro, is created for helping software developers quickly and easily create super client and server applications. All of these application will have following HUGE advantages:

  • Fast:

    Your client software components should ALWAYS and absolutely beat all of components written from COM, Corba and Java Bean/RMI in speed. The focus here is the words "ALWAYS" and "speed".

  • Non-blocking (asynchronous):

    Your client software components make it possible that all of client graphic user interfaces could be NEVER, NEVER, ...... blocked and frozen with no need of threads no matter what calls are sent from a client to a server. If you use the common technologies, COM, Corba and Java Bean/RMI, for a real project, you may have to use threads for preventing client graphic user interfaces from being dead because of long time delay of an internet/intranet call. The problems such as data synchronization and mess in coding logical, which naturally come with use of threads, could be avoided if you use SocketPro.

  • Switchable between non-blocking and blocking mode:

    All of client function calls, which lead to data movement over internet, can be switched between blocking and non-blocking modes at your will. This advantage dramatically simplifies the client side development.

  • Multiple sessions to a server:

    Your client applications are able to create multiple sessions to a server. Each of sessions does its own job, runs independently and in parallel, and doesn't block others without help of threads.

  • Cross-platform development:

    Your client applications can communicate with all of socket-based server applications running on all of platforms, Windows, UNIX, Linux, windows, Mac, and others. The server applications don't have to be written from SocketPro.
Other advantages includes:
  • Fast connection to a server,
  • Quick initialization of a class object,
  • Simple installation and security setup,
  • Simple to learn and use, and no complicatedconcepts are involved,
  • Stable if you understand socket and follow its rule.


This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here


About the Author

Yuancai (Charlie) Ye
Web Developer
United States United States
Yuancai (Charlie) Ye, an experienced software engineer, lives in Atlanta, Georgia. He is an expert at OLEDB consumer and created a powerful data accessing libarary at the site He has been working at SocketPro written from batching, asynchrony and parallel computation for more than three years. Visual C++, C# and ASP.NET are his favorite development environments.

Comments and Discussions

QuestionCAn you help me? Pinmemberdonperry19-Mar-09 13:32 
GeneralDCOM statements from Microsoft PinmemberYuancai (Charlie) Ye17-Apr-02 6:39 
GeneralSocketPro updated with doc and more samples PinmemberYuancai (Charlie) Ye5-Apr-02 6:29 
GeneralNice but not professional PinmemberAnonymous24-Feb-02 14:33 
GeneralRe: Nice but not professional PinmemberYuancai (Charlie) Ye25-Feb-02 6:04 
Hi, Andrew:
After reading through your comments, here are my answers. If you are not clear about what I said, please give your concerns here.
Anonymous wrote:
I read your article and it might be nice for beginners and maybe also for medium skilled developers.
Every professional program (as Web Server or Databases e.g.) uses a system that
works similar (without message collection on high level) as what you described as Pattern 2 (so not very unique).
I assume you are using WSA with Events (I haven't seen the source code so I can actually not judge).
And you seem to use unique Threads waiting for the WSA Events with something like WaitForSingleObject / WaitForMultipleObjects and some sort of Queues (maybe STL queues or another suitable collection class.
For this task IO Completion Ports are the more professional (and more efficient)
method (though it requires a professional OS like NT, 2000, XP).

In short, SocketPro doesn't use any pre collections and message collections at all at either server or client sides! This is against what you imagined about SocketPro. SocketPro fully takes advantage of Nagle Algorithm.
I bet most of programs don't use pattern 2 for data communications between 2 machines. For all of DCOM/MTS based programs, I am sure them are not. Although I am not professional with Corba and Java RMI/bean, I think that those professional programs based on these techniques would n't use pattern 2 for data communication either.
In regards to IOCP, SocketPro doesn't use it at this time. I will maybe use it in the next version of SocketPro release if it really works very well for me and has a considerable improvement. At this time, I tested SocketPro with exchanging big files (40 mbytes) between two computers. It is found that SocketPro can match to OS operation (window explorer).
Anonymous wrote:
Next what you describe as problem of Pattern 1 (but not really the problem of pattern 1):
It is never a problem to send 50 Bytes Messages over a network with much higher MTU.
You are right, that MTU size is maybe not used, but this makes transmission faster if a frame (with less than MTU size) is transferred, because less Bytes are transferred, there will be never a waste in transmission power anyway.
Your calculation is simply wrong because MTU is Maximum Transfer Unit size and not Transfer unit size !
Your program simply collects requests using less (and bigger) frame sizes causing unnecessary time gaps (collecting phase) and longer transmission between them, so there is still a part of what you describe as pattern 1 inside your program.
In addition Maximum Transfer Unit size can vary on different systems and in addition Windows (at least 2000, XP) optimizes these values dynamically for the network environment of each attached network device (POTS-Modem, DSL, cable, E1, ATM, Ethernet, Token Ring, ...).
Using high MTU values only makes sense for really big data (over slow responding networks) like sending 1 MegaByte, but if you send 1 MegaByte at once, the MTU size would be used anyway. For small messages like the 50 Bytes messages it is unimportant. So eg for HTTP or FTP a high MTU is recommended. For Message Transfer it does not matter if maximum Message size is less than MTU.
If your test program would be faster you would see, that the operating system is doing
automatically (Nagle Algorithm, which you have described) concatenation of messages if maximum Througput is not reached with lower TU size, what will happen eg at about a througput of more than about 7 000 Messages / s for a 100 MBit Ethernet network.
So it is useless to implement this a second time on a higher level.
Even more: because OS is doing this anyway and you seem to not use this your program could get trouble on higher speeds,
if your SocketPro would be able to reach these speed, because packets will be wrapped on Frame/Buffer sizes no matter it is optimized for a certain MTU size and then the receiver in SocketPro will have problems to puzzle them together again.

The simplest way to judge if SocketPro is really able to improve moving data speed over internet is to use the tool NetStat (netstat -i -p IP) with sending a number of arbitituary requests to a server. If the number of IP packets is reduced, the net efficiency is improved. At this time, see the attached speed test sample(..\SocketPro\Samples\Client\SpeedTest) at the site Additionally, I also give you a very simple DCOM server to test. The test result can speak out, and approve it.
Anonymous wrote:
The problem of Pattern 1 exists mainly on the Client Side, and the real problem is that
if a client does not send a lot of requests, the server cannot process a lot of requests.
You simply found the explanation why Multitasking exists and why it makes sense for Clients.

Your point here is correct if blocking/synchronous running mode is used with Socket and a client is expecting a returned result. But, when a socket is running in the non-blocking/asynchrounous mode or with no expecting returned result, a client may send two or more requests with one bigger stream data to a server through Nagle algorithm or client packing although this is not guranteed to happen.
Anonymous wrote:
Okay, let's get back to the sockets:
A disadvantage of your SocketPro (other than it does not deliver maximum throughput)
is that you collect requests on the client and not send immediatly, this can result in
starvation of clients with little request amount and in any case increased network round trips.

The SocketPro doesn't have this disadvantage at all, because SocketPro doesn't use your metioned mechanism to manage data.
Anonymous wrote:
I wonder how many Requests your SocketPro can process, the Socket system we use can deliver on a standard
PC a throughput that cannot be managed by a 100 MBit network card (can deliver more than 15 000 Messages/s)
and it does not matter if the requests are 50 or 5000 Bytes long. We are currently optimizing this software to reach
a value of 25 000 to 50 000 100-5120 Bytes Messages / s / CPU, so I am interested in every method to queech out some
more performance but your message precollection is reducing performance in my opinion (s.a.).
You also mentioned DCOM etc. as a performance comparison, but whatever number you measured, what you report can be a result
of the DCOM logic itself and you haven't measured or compared the actual throughput anyway. You measured only the network round trip delay time which is not important for almost all applications and low for DCOM in any case. If you have 0.5, 2.5 or 30 ms that does not matter in case of internet anyway with delay times of >100 to 1000 ms, and in case of intranet anything below 50 ms is so fast that the user cannot detect any difference in application performance. So the measured throughput in Messages / second is the important number, e.g. for a server that means how many clients can be handled.
I am very interested in your performance measures.
Depending on this you and I could proof my criticism as true or false.

According to my test data with my supporting hardwares, my results show that
1. SocketPro with non-blocking can be much faster than DCOM, and easily 30 or more times faster.
2. Under any cases, SocketPro is never slower than DCOM no matter if a socket running mode is blocking or non-blocking, or if a request is lengthy or short action.

You could use the above SpeedTest sample to measure the speed of SocketPro, which contains all of source code available.
Please test it, and give me your comments here.

GeneralRe: Nice but not professional PinmemberAnonymous2-Apr-02 22:49 
GeneralRe: Nice but not professional PinmemberYuancai (Charlie) Ye9-Apr-02 6:01 
QuestionWhat/where is it? PinmemberChoppa28-Jan-02 23:37 
AnswerRe: What/where is it? PinmemberYuancai (Charlie) Ye29-Jan-02 3:25 
AnswerRe: What/where is it? PinmemberYuancai (Charlie) Ye30-Jan-02 3:05 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

| Advertise | Privacy | Terms of Use | Mobile
Web03 | 2.8.150327.1 | Last Updated 24 Feb 2002
Article Copyright 2002 by Yuancai (Charlie) Ye
Everything else Copyright © CodeProject, 1999-2015
Layout: fixed | fluid