BSD Socket Easy Incoming Manual
Translation: Wilbur Lang
Introduction
Capital ratio (What is Socket?)
Patch your new phone (how to listen?)
Dial (How to call Socket)
Talk (how to talk through Sockets)
Hang (end)
Chinese language (the language of communication is important)
The future is in your master (next step?)
Introduction
When you enter UNIX's mysterious world, it will immediately find that more and more things are difficult to understand. For most people, BSD Socket
The concept is one of them. This is a very short tutorial to explain what they are, how do they work and give some simple code to explain how to make
Use them.
Capital ratio (What is Socket?)
Socket is a BSD method for program communication (IPC). This means that the socket is used to interwork information and other processes, just like us.
Use a phone to communicate with other people.
It is very appropriate to use the phone to metaphor, we will always describe the concept of the phone.
Patch your new phone (how to listen?)
One person must be able to receive the call to him, first of all, he wants to install a phone. Similarly, you must first create Socket to listen to the line. This pass
Cheng includes several steps. First, you have to build a new one.
Socket, just install the phone first. The Socket () command completes this job.
Because Sockets has several types, you have to indicate what type you want to build. You have to make a choice is the address format of the socket. Like the phone
Different forms of frequency and pulses, Socket
There are two most important options that are AF_UNIX and IAF_INET. AF_UNIX identifies Sockets like UNIX path names. This form is in the same
IPC on a machine
Very useful. AF_INET uses the four decimal numbers of the four decimal numbers such as 192.9.200.10. In addition to the machine address,
You can use port numbers to allow multiple parts of each machine.
AF_INET SOCKET. We will focus on the AF_INET method here because he is useful and widely used.
Another parameter you must provide is the type of socket. Two important types are SOCK_STREAM and SOCK_DGRAM. Sock_Stream
Indicates that the data is like a symbol stream through Socket. Sock_DGRAM indicates that the data will be in the form of a datagrams. We will explain
Sock_Stream
Sockets, he is very common and easy to use.
After building Socket, we will provide the address of the socket listening. Just like you have to answer the phone number. Bind () function
This matter.
SOCK_STREAM Sockets allows the connection request to form a queue. If you are busy with a connection, other connection requests will always wait until the connection
It is complete. Listen ()
The function is used to set the number of requests (generally 5) that is not rejected. Generally do not use the listen () function.
The following code shows how to connect to the socket (), bind (), and listen () functions and accept data.
/ * code to establish a socket; Originally from bzs@bu-cs.bu.edu
* /
INT Establish (unsigned short portnum)
{Char MyName [MaxHostName 1];
Int S;
Struct sockaddr_in sa;
Struct hostent * hp;
MEMSET (& SA, 0, SIZEOF (Struct SockAddr_in); / * Clear Our Address * /
GethostName (MyName, MaxHostName); / * Who Are We? * /
HP = gethostByname (MyName); / * Get outress info * / if (hp == null) / * We don't exist!? * /
Return (-1);
sa.sin_family = hp-> h_addrtype; / * this is io host address * /
sa.sin_port = htons (portnum); / * this is our port number * /
IF ((S = Socket, Sock_Stream, 0)) <0) / * CREATE SOCKET * /
Return (-1);
IF (Bind (S, & SA, SIZEOF (Struct SockAddr_in) <0) {
Close (s);
Return (-1); / * bind address to socket * /
}
Listen (s, 3); / * max # of queued connects * /
Return (s);
}
After you have established Socket, you have to wait for the call to the socket. The accept () function comes to this purpose. Calling accept ()
Like the phone after the phone is ringing. Accept () returns a new Socket connected to the caller.
The following code demo is a presentation.
/ * WAIT for a connection to occur on a socket created with establish ()
* /
INT GET_CONNECTION (INT S)
{INT T; / * Socket of connection * /
IF ((t = accept (s, null, null) <0) / * accept connection if there is one * /
Return (-1);
Return (T);
}
Unlike the phone, you can also accept call when you handle the previous connection. To this end, it is generally used to handle each connection. Below
How to demonstrate how to use Establish () and
Get_connection () to handle multiple connections.
#include
#include
#include
#include
#include
#include
#include
#include
#include
#define portnum 5000 / * Random Port Number, WE NEED SOMETHING * /
Void Fireman (void);
Void do_something (int);
Main ()
{INT S, T;
IF ((s = establish (portnum)) <0) {/ * plug in the phone * /
PERROR ("Establish");
Exit (1);
}
Signal (SIGCHLD, FIREMAN); / * This Eliminates Zombies * /
For (;;) {/ * loop for phone calls * /
IF ((t = get_connection (s)) <0) {/ * Get a connection * /
IF (errno == eintr) / * Eintr might happen on accept (), * / continue; / * try again * /
PERROR ("accept"); / * bad * /
Exit (1);
}
Switch (fork ()) {/ * try to handle connection * /
Case -1: / * bad news. Scream and die * /
PERROR ("fork");
Close (s);
Close (T);
Exit (1);
Case 0: / * We're the child, do something * /
Close (s);
Do_something (t);
exit (0);
Default: / * We're The Parent So Look for * /
Close (T); / * another connection * /
CONTINUE;
}
}
}
/ * as children die we shop get catch their return or or We get
* Zombies, a bad thing. Fireman () Catches Falling Children.
* /
Void Fireman (void)
{
While (Waitpid (-1, null, wnohang> 0)
;
}
/ * this is the function That Plays with the socket. IT Will Be Called
* after getting a connection.
* /
Void do_something (int S)
{
/ * Do Your Thing with the socket here
:
:
* /
}
Dial (How to call Socket)
Now you should know how to build Socket to accept call. So how do you call? Like the phone, you have to have a call. Socket ()
The function is to complete this matter, just like the establishment of listening
Socket.
After giving the socket address, you can use the connect () function to connect the listen Socket. Here is a code.
Int call_socket (char * hostname, unsigned short portnum)
{struct sockaddr_in sa;
Struct hostent * hp;
Int a, s;
IF ((hp = gethostbyname) == null) {/ * do we know the host's * /
Errno = ECONNREFUSED; / * Address? * /
Return (-1); / * no * /
}
MEMSET (& SA, 0, SIZEOF (SA);
Memcpy ((char *) & sa.sin_addr, hp-> h_addr, hp-> h_length; / * set address * /
Sa.sin_family = hp-> h_addrtype;
sa.sin_port = HTONS ((u_short) portnum);
IF ((S = Socket (hp-> h_addrtype, sock_stream, 0)) <0) / * get socket * /
Return (-1);
IF (Connect (S, & SA, SIZEOF SA <0) {/ * connection * /
Close (s);
Return (-1);
}
Return (s);
}
This function returns a Socket that can flow through data. Talk (how to talk through Sockets)
Ok, you have established a connection between the two sides to transfer data, and now it is transmitted. The read () and write () functions are processed. In addition to Socket
Like a difference in reading and writing and document reading and writing, the same as the general file. The difference is that you usually do not get the number of data you want. So you want
Always circulating to the data you need. A simple example: read certain data to the cache.
INT read_data (int S, / * connection socket * /
Char * BUF, / * Pointer to the buffer * /
INT N / * NUMBER OF CHARACTERS (BYTES) WA WANT * /
)
{Int bcount; / * counts bytes read * /
INT Br; / * bytes read this pass * /
BCOUNT = 0;
Br = 0;
While (BCOUNT IF ((br = read (s, buf, n-bcount)> 0) { BCOUNT = Br; / * increment Byte Counter * / BUF = Br; / * Move Buffer Ptr for Next Read * / } ELSE IF (br <0) / * Signal An Error to the Caller * / Return (-1); } Return (BCOUNT); } The same function can also write data, leave our reader. Hang (end) Like you through the phone and someone, you have to close the connection between the socket. General close () function is used to close Socket on each side connection. If you have closed it, and the other side is written to him, an error code is returned. Chinese language (the language of communication is important) Now you can contact between machines, but be careful about what you said. Many machines have their own dialects, such as ASCII and Ebcdic. More common problems are byte order issues. Unless you are transferring, you must pay attention to this problem. Fortunately, people We found a solution. A long time ago, what kind of order is more "correct". Now there is a corresponding function to switch now. Among them, Htons (), NTOHS (), HTONL () and NTOHL (). Convert it first before transmitting a integer data. i = HTONL (i); Write_Data (S, & I, SIZEOF (i)); After reading the data, change again. READ_DATA (S, & I, SIZEOF (i)); I = NTOHL (i); If you have been insisting on this habit, you will be more wrong than others. The future is in your master (next step?) Just use what we just discussed, you can write your own communication program. Like all new things, it is best to see others already do What is it. There are many about BSD Socket here. Things can be referred to. Please note that there is no error check in the example, which is very important in "real" programs.