Check IP before accepting asio::IP::TCP socket - c++

Is it possible to check the IP of the remote host on the server/acceptor side before accepting the connection?
The reason behind it: I have n clients regularly trying to connect to a server, and I do not want to constantly have n open connections. Instead I would like to be able to choose which clients I want to connect with and only accept these connections when I need them.
Unfortunately, the connect needs to be initiated from the client, so in a reverse kind of way, due to firewall and policies.
Is this even possible from a TCP perspective and how can this be done in asio?

There are two approach:
You accept the connection and get peer address, check and close it. You can also take the opportunity to tell the client that server is busy. This however on the cons side might open up attack vector for massive connection request.
You modify the firewall in run time, using something like fail2ban.
By the way, what make you not willing to hold N open connection? Modern system can handle hundreds of thousand, even millions of connection without issue.

Related

Pinging by creating new sockets per each peer

I created a small cross-platform app using Qt sockets in C++ (although this is not a C++ or Qt specific question).
The app has a small "ping" feature that tries to connect to a peer and asks for a small challenge (i.e. some custom data sent and some custom data replied) to see if it's alive.
I'm opening one socket per each peer so as soon as the ping starts we have several sockets in SYN_SENT.
Is this a proper way to implement a ping-like protocol with challenge? Am I wasting sockets? Is there a better way I should be doing this?
I'd say your options are:
An actual ping (using ICMP echo packets). This has low overhead, but only tells you whether the host is up. And it requires you to handle lost packets, timeouts, and retransmits.
A UDP-based protocol. This also has lower kernel overhead, but again you'll be responsible for setting up timeouts, handling lost packets, and retransmits. It has the advantage of allowing you to positively affirm that your program is running on the peer. It can be implemented with only a single socket endpoint no matter how many peers you add. (It is also possible that you could send to multiple peers at once with a broadcast if all are on a local network, or a multicast [complicated set-up required for that].)
TCP socket as you're doing now. This is much easier to code, extremely reliable and will automatically provide a timeout (i.e. your connect will eventually fail if the peer doesn't respond). It lets you know positively that your peer is there and running your program. Although there is more kernel overhead to this, and you will use one socket endpoint on your host per peer system, I wouldn't call it a significant issue unless you think you'll be having thousands of peers.
So, in the end, you have to judge: If thousands of hosts will be participating and this pinging is going to happen frequently, you may be better off coding up a UDP solution. If the pinging is rare or you don't expect so many peers, I would go the TCP route. (And I wouldn't consider that a "waste of sockets" -- those advantages are why TCP is so commonly used.)
The technique described in the question doesn't really implement ping for the connection and doesn't test if the connection itself is alive. The technique only checks that the peer is listening for (and is responsive to) new connections...
What you're describing is more of an "is the server up?" test than a "keep-alive" ping.
If we're discussing "keep-alive" pings, than this technique will fail.
For example, if just the read or the write aspect of the connection is closed, you wouldn't know. Also, if the connection was closed improperly (i.e., due to an intermediary dropping the connection), this ping will not expose the issue.
Most importantly, for some network connections and protocols, you wouldn't be resetting the connection's timeout... so if your peer is checking for connection timeouts, this ping won't help.
For a "keep-alive" ping, I would recommend that you implement a protocol specific ping.
Make sure that the ping is performed within the existing (same) connection and never requires you to open a new connection.

Routing sockets to another port

I have a system where I want to listen to a socket and wait to client connect and then pass the connection to another application that I'll start as soon as the connection is established.
I do not have control on this other application and can only set the port where it will listen, but I want to have one process for each new client.
This is what I'm trying to do:
I've been searching for a solution, but I thing I don't have the right terminology, but I managed to find on Richard Stevens' "Unix Network Programming" something about the AF_ROUTE family of sockets that may be combined with a SOCK_RAW to route a connection to another IP and port. But there's too little documentation about how to use this flag and seems to require superuser privileges (that I want to avoid).
Maybe there's an easier solution but I'm probably using the wrong terms. Is it clear what I want to do?
I don't think you'll be able to just "pass" the socket like you want to, especially if you can't change and recompile "APP". Sockets include various administrative overhead (resource management, etc) that are linked to the process they are owned by. In addition, if you can't recompile APP, there is no way to make it bypass the steps involved with accepting a connection and simple have an already open connected "handed" to it by your router.
However, have you considered simply using router as a pass-through? Basically, have your "Router" process connect via sockets to the each "APP" process it spawns, and simply echo whatever it recieves from the appropriate client to the appropriate APP, and visa versa for APP to client?
This does add overhead, and you will have to manage a small mapping to keep track of which clients go to which apps, but it might work (assuming the APP or client aren't basing any behavior off of the IP address they are connected to, etc). Assuming you can't recompile APP, there might not be too many other options.
The code for this is relatively simple. Your handler for data recieved from APP just looks up the socket for the appropriate app from your mapping, and then does a non blocking send of this data out on it. Likewise the handler for data recieved from client. Depending on how exactly the clients and app behave, you may have to handle a bit of synchronization (if you recieve from both simultaneously).

How to get the client IP address before accepting the connection in C++

I'm studing c++ socket programming...
The server program binds to a socket and starts listening for connection requests...ok now how can I list the IP addreses of the listened requests?
I know I can get the IP addresses after accepting the connections but lets say I don't wanna accept a connection from an specific IP address...
On Windows only, you can use the conditional callback feature of WinSock2's WSAAccept() function to access client information before accepting a connection, and to even reject the connection before it is accepted.
This can't be done in terms of the standard socket API. On all platforms I know, the system actually accepts the connection (i.e. responds with SYN+ACK TCP datagram) before the application has a chance to monitor the pending request.
For optimum performance, this would be solved by filtering in the network stack, but the details of doing that will depend on the operating system (this is not part of the socket interface and your application may generally not even have the rights to configure your network stack this way.)
The other opportunity is after the accept, by which time the connection is already accepted (CONNECT ACK) on TCP level.
I don't think you can do it in the middle phase where you would prefer that. That however would not be very different from doing it after accept anyway.

Avira Antivirus detects the listen function as backdoor model

The function
listen( ListenSocket, SOMAXCONN )
is detected by avira antivirus as a backdoor model.
How can I write small client/server applications without a listen function?
Is there a way to do it?
If you need to accept connections then no, you can't do that without calling listen.
If you can make your application just a client and have an server running somewhere else then your client can connect to the server and the server can act as a broker for other clients to connect to...
I wouldn't worry about this anyway. If you're running a server that you want to be able to connect to from a machine other than the one it's running on then your documentation will have to explain how to open up firewall ports and whatever so just add details of how to exclude the app from the antivirus applications that it confuses.
Also, your application IS accepting connections from external sources and so the antivirus app is correct to warn the user. You need to educate the user that it's OK for your app to do this because it's doing it for whatever valid reason you have. If you don't want to explain it to the user then, IMHO, you are writing a backdoor ;)
Uninstall Avira Antivirus ;-)
Server, by definition, listens for incoming connections, and clients initiate connections to the server. In TCP/IP networking, the server achieves this by bind()ing and listen() ing to a socket.
Avira is filled with all sorts of false-positives that are trivially easy to work around. Try storing listen into a function pointer and calling it. It'll probably work.
If you're dealing with TCP connections and you know who/where the connection is coming from, and have a third party that can tell you when the connection is going to be attempted, it's valid for both sides to connect to each other at the same time. Doing this can negotiate a connection without either side listening. It's not a good solution and needs a much more complex implementation if a NAT is involved, but it is a possibility if the client and server are on a LAN.

TCP/IP and designing networking application

i'm reading about way to implemnt client-server in the most efficient manner, and i bumped into that link :
http://msdn.microsoft.com/en-us/library/ms740550(VS.85).aspx
saying :
"Concurrent connections should not exceed two, except in special purpose applications. Exceeding two concurrent connections results in wasted resources. A good rule is to have up to four short lived connections, or two persistent connections per destination "
i can't quite get what they mean by 2... and what do they mean by persistent?
let's say i have a server who listens to many clients , whom suppose to do some work with the server, how can i keep just 2 connections open ?
what's the best way to implement it anyway ? i read a little about completion port , but couldn't find a good examples of code, or at least a decent explanation.
thanks
Did you read the last sentence:
A good rule is to have up to four
short lived connections, or two
persistent connections per
destination.
Hard to say from the article, but by destination I think they mean client. This isn't a very good article.
A persistent connection is where a client connects to the server and then performs all its actions without ever dropping the connection. Even if the client has periods of time when it does not need the server, it maintains its connection to the server ready for when it might need it again.
A short lived connection would be one where the client connects, performs its action and then disconnects. If it needs more help from the server it would re-connect to the server and perform another single action.
As the server implementing the listening end of the connection, you can set options in the listening TCP/IP socket to limit the number of connections that will be held at the socket level and decide how many of those connections you wish to accept - this would allow you to accept 2 persistent connections or 4 short lived connections as required.
What they mean by, "persistent," is a connection that is opened, and then held open. It's pretty common problem to determine whether it's more expensive to tie up resources with an "always on" connection, or suffer the overhead of opening and closing a connection every time you need it.
It may be worth taking a step back, though.
If you have a server that has to listen for requests from a bunch of clients, you may have a perfect use case for a message-based architecture. If you use tightly-coupled connections like those made with TCP/IP, your clients and servers are going to have to know a lot about each other, and you're going to have to write a lot of low-level connection code.
Under a message-based architecture, your clients could place messages on a queue. The server could then monitor that queue. It could take messages off the queue, perform work, and place the responses back on the queue, where the clients could pick them up.
With such a design, the clients and servers wouldn't have to know anything about each other. As long as they could place properly-formed messages on the queue, and connect to the queue, they could be implemented in totally different languages, and run on different OS's.
Messaging-oriented-middleware like Apache ActiveMQ and Weblogic offer API's you could use from C++ to manage and use queues, and other messaging objects. ActiveMQ is open source, and Weblogic is sold by Oracle (who bought BEA). There are many other great messaging servers out there, so use these as examples, to get you started, if messaging sounds like it's worth exploring.
I think key words are "per destination". Single tcp connection tries to accelerate up to available bandwidth. So if you allow more connections to same destination, they have to share same bandwidth.
This means that each transfer will be slower than it could be and server has to allocate more resources for longer time - data structures for each connection.
Because establishing tcp connection is "time consuming", it makes sense to allow establish second connection in time when you are serving first one, so they are overlapping each other. for short connections setup time could be same as for serving the connection itself (see poor performance example), so more connections are needed for filling all bandwidth effectively.
(sorry I cannot post hyperlinks yet)
here msdn.microsoft.com/en-us/library/ms738559%28VS.85%29.aspx you can see, what is poor performance.
here msdn.microsoft.com/en-us/magazine/cc300760.aspx is some example of threaded server what performs reasonably well.
you can limit number of open connections by limiting number of accept() calls. you can limit number of connections from same source just by canceling connection when you find out, that you allready have more then two connections from this location (just count them).
For example SMTP works in similar way. When there are too many connections, it returns 4xx code and closes your connection.
Also see this question:
What is the best epoll/kqueue/select equvalient on Windows?