![]() |
|
|
#1 |
![]() |
C/C++ Sockets FAQ and How-To Win+Linux
Ok so many many programs these days make use of networking and the internet. Ever wondered how simple it would be to connect two programs together over such? Wonder no further
What are sockets? Well sockets are used as an interface to access a network through your operating system. Imagine your system to be contained inside of a locked room, with the only point of entry being a wall totally plastered in wall plugs. You create a socket, bind it to the plug and you've got access outside on the network. Also whilst we're at it, you can think of your firewall as a dude that stands about watching the wall plugs, pulling out ones that it doesn't like XD Getting Started Ok first you'll need to include the appropriate header files for sockets. Windows Code:
#include <winsock.h> winsock as in Windows Socket ![]() Linux Code:
#include <sys/types.h> #include <sys/socket.h> #include <netinet/in.h> #include <arpa/inet.h> The headers for Unix are split up more so you don't get the overhead of a huge amount of stuff you just don't need! Extra stuff for Windows... You'll need a load of extra stuff for Windows: Code:
WSADATA wsaData; WSAStartup(0x0202, &wsaData); ![]() Creating your first socket First you need to define some information about the type of connection you want to establish. Here i'm after a two-way socket (SOCK_STREAM) that uses IPv4 (AF_INET) and uses TCP (IPPROTO_TCP) for reliable data transfer. Thankfully both ways are interoperable between OS's ![]() Code:
int thisSocket;
struct sockaddr_in destination;
destination.sin_family = AF_INET;
thisSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (thisSocket < 0)
{
printf("\nSocket Creation FAILED!");
return 0;
}
![]() The differences here come from the way both OS's handle networking... Windows Code:
closesocket(thisSocket) WSACleanup(); Code:
close(thisSocket) Hosting a connection with your socket There are three stages to host and establish a connection:
Binding to a socket Before you can bind to a socket you want to know what port you want to listen on. In this example i'll be listening on port "13374" because it's 1337-er than the others ![]() The htons(int) function basically converts a port number to the type that sockets prefer. Code:
destination.sin_port = htons (13374);
destination.sin_addr.s_addr = INADDR_ANY;
if (bind(thisSocket, (struct sockaddr *)&destination, sizeof(destination))<0){
printf("\nBinding Socket FAILED!\n");
if (thisSocket) close(thisSocket);
return 0;
}
This function will BLOCK until someone tries to connect , so if your program hangs on this line and you're wondering why, it's because nobodies connected yet. The 5 refers to how many people can be trying to connect at once, not entirely sure about it tbh.Code:
printf("\nListening on 13374...");
if (listen(thisSocket, 5)<0){
printf("\nListening on Socket FAILED!\n");
if (thisSocket) close(thisSocket);
return 0;
}
The last stage . You'll need an object to get information about who you are connecting to, whose information you can read out of the struct to find out more about them after the function returns.Code:
struct sockaddr_in clientAddress;
int clientSize = sizeof(clientAddress);
thisSocket= accept(thisSocket, (struct sockaddr *)&clientAddress, (int *) &clientSize);
if (thisSocket<0)
{
printf("\nSocket Connection FAILED!\n");
if (thisSocket) close(thisSocket);
return 0;
}
printf("\nConnection Established!");
Connecting to a host Thankfully connecting to a host is blissfully simple This will be connecting to port 13374, the same port that we should be listening on above and it'll connect to the local host (aka you) so you can try this stuff out ![]() Code:
destination.sin_port = htons(13374);
destination.sin_addr.s_addr = inet_addr("127.0.0.1");
if (connect(thisSocket,(struct sockaddr *)&destination,sizeof(destination))!=0){
printf("\nSocket Connection FAILED!\n");
if (thisSocket) close(thisSocket);
return 0;
}
printf("\nConnected!");
Sending data over a socket So you've got a socket set up at last, how do you send data over it? The send() function takes the following:
Code:
send(thisSocket, buffer, BUFFERSIZE, 0); Receiving data over a socket The revc() function takes the following:
Code:
int newData; newData = recv(thisSocket, buffer, BUFFERSIZE, 0); My ways for writing for both Windows and Unix At the top of every file I start with two lines: Code:
#define __WINDOWS #define __LINUX This lets me do things like this: Code:
#ifdef __WINDOWS
#include <winsock.h>
#endif
#ifdef __LINUX
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
void closesocket(int socket) { close(socket); }
#endif
Code:
#ifdef __WINDOWS WSADATA wsaData; #endif Code:
#ifdef __WINDOWS WSAStartup(0x0202, &wsaData); #endif Code:
#ifdef __WINDOWS
WSACleanup();
#endif
Last edited by Oliver_FF; Apr 8, 2008 at 04:49 PM. |
|
|
|
| The Following User Says Thank You to Oliver_FF For This Useful Post: |
|
|
#2 |
|
Hardcore Monkey Moderator
Join Date: Feb 2007
Location: Cheeseland (Wisconsin, USA)
Posts: 12,254 (5.27/day)
Thanks: 591
Thanked 5,510 Times in 2,948 Posts
|
Great post !!!!
The last time I did any socket programming was when I was using Unix machines. That was about 15 years ago. Brings back memories. Not necessarily fond memories, but memories. Keep 'em coming Oliver_FF ... we need to boost the P&W section !!! PS. I see you've mastered the [code] tags
__________________
Cloud (noun, singular): A dynamic arrangement of multiple potential single points of failure, with a user at one end and their data at the other. Get more tech news on a wide variety of topics at NextPowerUp
|
|
|
|
|
|
#3 |
![]() |
Bump for the follow-up http://forums.techpowerup.com/showthread.php?p=818797
|
|
|
|
|
|
#4 |
![]() Join Date: Jan 2009
Posts: 6 (0.00/day)
Thanks: 0
Thanked 0 Times in 0 Posts
|
Thanks alot!
|
|
|
|
![]() |
| Currently Active Users Viewing This Thread: 1 (0 members and 1 guests) | |
| Thread Tools | |
|
|