- Domain: Specifies the protocol family. For internet-based communication, we use
AF_INETfor IPv4. - Type: Specifies the communication semantics. We use
SOCK_STREAMfor TCP (Transmission Control Protocol), which provides a reliable, connection-oriented byte stream. - Protocol: Specifies the protocol. Setting it to
0usually selects the appropriate default protocol based on the domain and type.
Let's dive into creating a daytime client server program in C. In this comprehensive guide, we'll walk through building a simple client-server application where the server provides the current date and time to any connected client. This project is fantastic for understanding basic network programming concepts like sockets, binding, listening, and accepting connections. So, grab your favorite code editor, and let's get started!
Understanding the Basics
Before we jump into the code, it's essential to understand the fundamental concepts that make our client-server program work. Networking involves processes running on different machines communicating with each other. In our case, the server will listen for incoming connections, and the client will initiate the connection to request the current date and time.
Sockets
At the heart of network communication are sockets. Think of sockets as endpoints for sending and receiving data. In C, we use the socket() function to create a socket. This function requires three arguments:
Binding
Once we create a socket for the server, we need to associate it with a specific address and port. This is done using the bind() function. The address is an IP address, and the port is a number that identifies the service on the server. When binding, we typically use INADDR_ANY to allow the server to listen on all available network interfaces. Choosing the right port number is also crucial; ports below 1024 are reserved for system services and require special permissions, so it's better to use a port number above 1024.
Listening
After binding, the server needs to listen for incoming connections. The listen() function puts the socket into a passive mode, where it waits for client connections. This function takes two arguments: the socket and the backlog, which specifies the maximum number of queued connections.
Accepting Connections
When a client tries to connect, the server uses the accept() function to accept the connection. This function creates a new socket that is connected to the client. The original socket remains listening for more connections, while the new socket is used to communicate with the connected client. The accept() function returns a new socket descriptor, which is used for sending and receiving data with the client.
Server-Side Code
The server-side code is responsible for listening for incoming client connections, accepting those connections, and sending the current date and time back to the client. Here's a breakdown of the steps and the corresponding C code.
Setting Up the Server Socket
First, we include the necessary header files and define the port number.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netinet/in.h>
#define PORT 5000 // You can change this
Next, we create the socket, bind it to an address and port, and start listening for connections.
int main() {
int server_fd, new_socket;
struct sockaddr_in address;
int addrlen = sizeof(address);
// Creating socket file descriptor
if ((server_fd = socket(AF_INET, SOCK_STREAM, 0)) == 0) {
perror("socket failed");
exit(EXIT_FAILURE);
}
address.sin_family = AF_INET;
address.sin_addr.s_addr = INADDR_ANY;
address.sin_port = htons( PORT );
// Binding the socket to the specified address and port
if (bind(server_fd, (struct sockaddr *)&address, sizeof(address)) < 0) {
perror("bind failed");
exit(EXIT_FAILURE);
}
// Listening for incoming connections
if (listen(server_fd, 3) < 0) {
perror("listen failed");
exit(EXIT_FAILURE);
}
Handling Client Connections
Now, we accept incoming connections in a loop and send the current date and time to the client.
while(1) {
printf("Waiting for a connection...");
if ((new_socket = accept(server_fd, (struct sockaddr *)&address, (socklen_t*)&addrlen)) < 0) {
perror("accept failed");
exit(EXIT_FAILURE);
}
// Get current date and time
time_t rawtime;
struct tm * timeinfo;
time(&rawtime);
timeinfo = localtime(&rawtime);
char *time_str = asctime(timeinfo);
// Sending the time to the client
send(new_socket, time_str, strlen(time_str), 0);
printf("Message sent to client\n");
close(new_socket); // Close the connection after sending
}
return 0;
}
This code snippet first waits for a connection using accept(). Once a connection is established, it retrieves the current date and time using time(), localtime(), and asctime(). Then, it sends the formatted time string to the client using send(). Finally, it closes the socket using close() to terminate the connection with the client. It is crucial to close the socket; otherwise, you might encounter resource leaks.
Client-Side Code
The client-side code is simpler than the server-side code. It creates a socket, connects to the server, receives the date and time, and prints it to the console.
Setting Up the Client Socket
First, we include the necessary header files and define the server's IP address and port number.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#define PORT 5000 // Must match the server's port
#define SERVER_IP "127.0.0.1" // Localhost
Here, we define the PORT and SERVER_IP. Make sure the SERVER_IP is set to the correct IP address of the server. If the server is running on the same machine as the client, you can use 127.0.0.1 (localhost).
Connecting to the Server and Receiving Data
Next, we create a socket, connect to the server, receive the date and time, and print it.
int main() {
int sock = 0;
struct sockaddr_in serv_addr;
char buffer[1024] = {0};
// Creating socket file descriptor
if ((sock = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
printf("Socket creation error \n");
return -1;
}
serv_addr.sin_family = AF_INET;
serv_addr.sin_port = htons(PORT);
// Convert IPv4 and IPv6 addresses from text to binary form
if(inet_pton(AF_INET, SERVER_IP, &serv_addr.sin_addr)<=0) {
printf("Invalid address/ Address not supported \n");
return -1;
}
// Connecting to the server
if (connect(sock, (struct sockaddr *)&serv_addr, sizeof(serv_addr)) < 0) {
printf("Connection Failed \n");
return -1;
}
// Receiving the time from the server
read(sock, buffer, 1024);
printf("Time from server: %s\n", buffer);
close(sock); // Closing the socket
return 0;
}
In this code, we create a socket using socket(), specify the server address using serv_addr, and connect to the server using connect(). Once connected, we read the data sent by the server using read() and store it in the buffer. Finally, we print the received time and close the socket using close(). Always ensure you close the socket to free up resources.
Compiling and Running the Code
To compile the server and client code, you can use a C compiler like GCC. Save the server code in a file named server.c and the client code in a file named client.c. Then, open a terminal and navigate to the directory where you saved the files.
Compiling
Compile the server code using the following command:
gcc server.c -o server
Compile the client code using the following command:
gcc client.c -o client
Running
First, run the server:
./server
In another terminal, run the client:
./client
The client should display the current date and time received from the server. If you encounter any issues, make sure the server is running before the client and that the port numbers and IP addresses match.
Error Handling
Error handling is crucial in network programming. The code examples above include basic error checking, but you can enhance it by adding more robust error handling. For example, you can use perror() to print more descriptive error messages and handle specific error codes returned by system calls.
Common Errors
- Socket Creation Error: Occurs when the
socket()function fails. - Bind Error: Occurs when the
bind()function fails, usually because the port is already in use. - Listen Error: Occurs when the
listen()function fails, possibly due to insufficient permissions. - Accept Error: Occurs when the
accept()function fails, often due to system resource issues. - Connection Refused: Occurs when the client tries to connect to a server that is not running or is not listening on the specified port.
- Invalid Address: Occurs when the client provides an incorrect IP address.
Best Practices for Error Handling
- Check Return Values: Always check the return values of system calls for errors.
- Use
perror(): Useperror()to print descriptive error messages. - Handle Specific Error Codes: Check specific error codes (e.g., using
errno) to handle different types of errors differently. - Cleanup Resources: Ensure that you close sockets and free allocated memory in case of errors to prevent resource leaks.
Conclusion
Creating a daytime client server program in C is an excellent way to understand the basics of network programming. This guide walked you through the essential steps, from setting up sockets to handling client connections and sending data. With this knowledge, you can start building more complex network applications. Remember to handle errors properly and always close sockets to prevent resource leaks. Happy coding, and may your network programs always connect successfully! Understanding the concepts and code provided here will give you a solid foundation for further exploration into network programming and distributed systems. By practicing and experimenting with these examples, you’ll be well on your way to mastering network programming in C.
Lastest News
-
-
Related News
Ministry Of Finance Portal: Your Easy Access Guide
Alex Braham - Nov 13, 2025 50 Views -
Related News
IDotnet Aspire Community Toolkit: Enhance Your Apps
Alex Braham - Nov 13, 2025 51 Views -
Related News
Greatest Lakers Team Of All Time: A Look Back
Alex Braham - Nov 9, 2025 45 Views -
Related News
Unveiling 'Inna Fii Khalqi Samawati Wal Ard': Deep Meaning
Alex Braham - Nov 12, 2025 58 Views -
Related News
Ipseiautotechse Perkasa Mandiri: Your Go-To Automotive Partner
Alex Braham - Nov 14, 2025 62 Views