CN Practical File
CN Practical File
OF
COMPUTER
NETWORKING
SESSION 2022-23
Ans.
**Ethernet Cables:**
- **Description:** These are the most common type of cables used to
connect devices in a LAN. They come in different categories such as Cat5e,
Cat6, Cat6a, and Cat7, offering varying levels of speed and performance.
- **Use:** Connecting devices like computers, printers, and switches within
a local network.
2. **Switches:**
- **Description:** Switches are networking devices that operate at the data
link layer (Layer 2) of the OSI model. They forward data to specific devices
on the network based on their MAC addresses.
- **Use:** Connecting multiple devices in a LAN, facilitating communication
between them.
3. **Routers:**
- **Description:** Routers operate at the network layer (Layer 3) of the OSI
model. They forward data between different networks, such as connecting a
local network to the internet.
- **Use:** Routing data between different networks and providing access to
the internet
. 4. **Access Points:**
- **Description:** Access points (APs) are devices that allow wireless
devices to connect to a wired network using Wi-Fi. They often integrate with
routers or switches.
- **Use:** Enabling wireless connectivity within a LAN.
6. **Hub:**
- **Description:** Hubs are basic networking devices that operate at the
physical layer (Layer 1). They simply broadcast data to all connected
devices without any intelligence for addressing.
- **Use:** Less common today due to switches, but may still be found in
older networks.
7. **Firewalls:**
- **Description:** Firewalls are security devices that monitor and control
incoming and outgoing network traffic based on predetermined security
rules. - **Use:** Protecting a LAN from unauthorized access and potential
security threats.
8. **Modems:**
- **Description:** Modems (modulator-demodulator) convert digital data
from a computer into the analog signal needed for communication over
telephone lines or cable systems.
- **Use:** Connecting to the internet via DSL, cable, or other broadband
services.
9. **Proxy Servers:**
- **Description:** Proxy servers act as intermediaries between clients and
the internet. They can be used for various purposes, including content
filtering and improving performance.
- **Use:** Enhancing security, managing bandwidth, and caching frequently
accessed content.
10. **Bridge:**
- **Description:** A bridge connects two or more network segments and
operates at the data link layer. It filters and forwards traffic based on MAC
addresses.
- **Use:** Extending a LAN or connecting different LAN segments.
Ans.
Network topologies refer to the physical or logical layout of a network,
determining how devices are connected and how data is transmitted
between them.
1. **Star Topology:**
- **Description:** In a star topology, all devices are connected to a central
hub or switch. The central hub serves as a repeater and facilitates
communication between devices.
- **Advantages:** - Easy to install and manage. - Fault isolation – if one
connection fails, it doesn't affect others.
- **Disadvantages:** - Dependency on the central hub – if it fails, the whole
network is affected. - Requires more cabling than some other topologies.
2. **Bus Topology:**
- **Description:** In a bus topology, all devices share a single
communication line (bus). Data is broadcasted to all devices, and each
device has a unique address to determine if the data is intended for it.
- **Advantages:** - Simple and easy to implement. - Requires less cabling
compared to a star topology.
- **Disadvantages:** - Limited scalability. - Performance can degrade as
more devices are added.
3. **Ring Topology:**
- **Description:** In a ring topology, each device is connected to exactly two
other devices, forming a closed loop or ring. Data circulates around the ring
until it reaches its destination.
- **Advantages:** - Equal access to the network for all devices. - No central
point of failure.
- **Disadvantages:** - Difficult to install and reconfigure. - Adding or
removing devices can disrupt the entire network.
4. **Mesh Topology:**
- **Description:** In a mesh topology, every device is connected to every
other device, creating multiple paths for data to travel. There are full mesh
and partial mesh configurations.
- **Advantages:** - High redundancy and reliability. - Fault tolerance – if one
connection fails, alternative paths are available.
- **Disadvantages:** - Expensive to implement due to the number of
connections. - Complex to manage and configure.
5. **Tree Topology:**
- **Description:** Tree topology combines characteristics of star and bus
topologies. Devices are grouped into star-configured clusters, and these
clusters are then connected in a bus configuration.
- **Advantages:** - Scalable and can support larger networks. - Provides
some fault tolerance.
- **Disadvantages:** - If the central hub (root) fails, the entire network may
be affected. - More complex than star or bus topologies.
6. **Hybrid Topology:**
- **Description:** Hybrid topology is a combination of two or more different
types of topologies. For example, a network might combine elements of
both star and ring topologies.
- **Advantages:** - Offers flexibility and customization. - Allows optimization
for specific needs within different parts of the network.
- **Disadvantages:** - Complexity increases with the combination of
different topologies. - May require more resources and planning.
Ans.
1. **Planning:**
- **Define Requirements:** - Identify the number of users and devices
that will be part of the LAN. - Determine the types of applications and
services the network will support.
- **Physical Layout:** - Plan the physical layout of the network,
considering factors like the location of network equipment and cable routes.
- Choose the appropriate network topology (e.g., star, bus, or ring).
- **Security Considerations:** - Determine security measures, such as
firewalls, access control, and encryption. - Plan for regular updates and
patches to ensure network security.
8. **Documentation:**
- Maintain detailed documentation of the LAN configuration, including
IP addresses, device settings, and security configurations.
- Keep an updated network diagram for reference.
Ans.
**Hamming Code**
def hamming_encode(data):
# Calculate the number of redundant bits needed
r = 0
while 2 ** r < len(data) + r + 1:
r += 1
# Initialize the encoded data with parity bits
encoded_data = [0] * (len(data) + r)
j = 0
# Fill in data bits in the encoded data, leaving spaces for parity
bits
for i in range(1, len(encoded_data) + 1):
if i & (i - 1) == 0:
continue # Skip powers of 2 (parity bit positions)
encoded_data[i - 1] = int(data[j])
j += 1
# Calculate parity bits
for i in range(r):
parity_pos = 2 ** i
parity = 0
for j in range(1, len(encoded_data) + 1):
if j & parity_pos == parity_pos:
parity ^= encoded_data[j - 1]
encoded_data[parity_pos - 1] = parity
return encoded_data
def hamming_decode(received_data):
# Calculate the number of redundant bits needed
r = 0
while 2 ** r < len(received_data):
r += 1
# Initialize syndrome bits
syndrome = [0] * r
# Calculate syndrome bits
for i in range(r):
parity_pos = 2 ** i
for j in range(1, len(received_data) + 1):
if j & parity_pos == parity_pos:
syndrome[i] ^= received_data[j - 1]
# Check for errors and correct if possible
error_pos = sum([2 ** i if bit == 1 else 0 for i, bit in
enumerate(syndrome)])
if error_pos > 0:
print(f"Error detected at position {error_pos}")
received_data[error_pos - 1] ^= 1 # Correct the bit
# Remove parity bits and return the decoded data
decoded_data = [received_data[i] for i in range(len(received_data)) if
i & (i + 1) !=
0]
return decoded_data
def main():
# Example usage
original_data = "1011101"
print(f"Original Data: {original_data}")
encoded_data = hamming_encode(original_data)
print(f"Encoded Data: {encoded_data}")
# Simulate an error by flipping a bit
error_position = 3
encoded_data[error_position - 1] ^= 1
print(f"Received Data with Error: {encoded_data}")
decoded_data = hamming_decode(encoded_data)
print(f"Decoded Data: {decoded_data}")
if __name__ == "__main__":
main()
Ans.
Framing is a technique used in data communication to delineate the
boundaries of frames (packets) within the transmitted data. Below is an
example of a Python program that implements two common framing
methods: Character Count and Byte Stuffing.
def character_count_framing(data):
frame = str(len(data)) + '/' + data
return frame
def byte_stuffing(data):
FLAG = b'\x7E' # Flag sequence to indicate the start and end of a
frame
ESCAPE = b'\x7D' # Escape character to escape special characters
XOR_MASK = 0x20 # XOR mask for escaping characters
# Byte stuffing procedure
stuffed_frame = bytearray([FLAG[0]])
for byte in data:
if byte == FLAG[0] or byte == ESCAPE[0]:
stuffed_frame.extend([ESCAPE[0], byte ^ XOR_MASK])
else:
stuffed_frame.append(byte)
stuffed_frame.extend([FLAG[0]])
return stuffed_frame
def byte_destuffing(data):
FLAG = b'\x7E'
ESCAPE = b'\x7D'
XOR_MASK = 0x20
destuffed_frame = bytearray()
i = 1 # Start from the second byte to skip the initial FLAG
while i < len(data) - 1: # Stop before the final FLAG
if data[i] == ESCAPE[0]:
destuffed_frame.append(data[i + 1] ^ XOR_MASK)
i += 2
else:
destuffed_frame.append(data[i])
i += 1
return bytes(destuffed_frame)
def main():
original_data = b'Hello, World!'
# Character Count Framing
cc_frame = character_count_framing(original_data.decode())
print(f"Character Count Frame: {cc_frame}")
# Byte Stuffing
bs_frame = byte_stuffing(original_data)
print(f"Byte Stuffed Frame: {bs_frame}")
# Byte Destuffing
destuffed_data = byte_destuffing(bs_frame)
print(f"Destuffed Data: {destuffed_data.decode()}")
if __name__ == "__main__":
main()
In this program:
- `character_count_framing` adds a count of characters to the
beginning of the data, followed by a delimiter ("/").
- `byte_stuffing` escapes special characters (e.g., FLAG and ESCAPE)
by adding an escape character before them and XORing with a mask.
- `byte_destuffing` reverses the byte stuffing process to retrieve the
original data.
Ans.
a.)
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#define PORT 8080
#define BUFFER_SIZE 1024
int main() {
int server_fd, new_socket;
struct sockaddr_in server_addr, client_addr;
int addrlen = sizeof(server_addr);
char buffer[BUFFER_SIZE] = {0};
// Create socket
if ((server_fd = socket(AF_INET, SOCK_STREAM, 0)) == 0) {
perror("Socket creation failed");
exit(EXIT_FAILURE);
}
// Setup server address structure
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr = INADDR_ANY;
server_addr.sin_port = htons(PORT);
// Bind the socket
if (bind(server_fd, (struct sockaddr *)&server_addr,
sizeof(server_addr)) < 0) {
perror("Bind failed");
exit(EXIT_FAILURE);
}
struct sockaddr_in server_addr;
char message[] = "Hello, Server!";
// Create socket
if ((client_socket = socket(AF_INET, SOCK_STREAM, 0)) == 0) {
perror("Socket creation failed");
exit(EXIT_FAILURE);
}
// Setup server address structure
server_addr.sin_family = AF_INET;
server_addr.sin_port = htons(PORT);
// Convert IPv4 and IPv6 addresses from text to binary form
if (inet_pton(AF_INET, SERVER_IP, &server_addr.sin_addr) <= 0) {
perror("Invalid address/ Address not supported");
exit(EXIT_FAILURE);
}
// Connect to the server
if (connect(client_socket, (struct sockaddr *)&server_addr,
sizeof(server_addr)) <
0) {
perror("Connection failed");
exit(EXIT_FAILURE);
}
// Send data to the server
send(client_socket, message, strlen(message), 0);
// Close the connection
close(client_socket);
return 0;
}
b.)
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#define PORT 8080
#define BUFFER_SIZE 1024
int main() {
int server_fd, new_socket;
struct sockaddr_in server_addr, client_addr;
int addrlen = sizeof(server_addr);
char buffer[BUFFER_SIZE] = {0};
// Create socket
if ((server_fd = socket(AF_INET, SOCK_STREAM, 0)) == 0) {
perror("Socket creation failed");
exit(EXIT_FAILURE);
}
// Setup server address structure
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr = INADDR_ANY;
server_addr.sin_port = htons(PORT);
// Bind the socket
if (bind(server_fd, (struct sockaddr *)&server_addr,
sizeof(server_addr)) < 0) {
perror("Bind failed");
exit(EXIT_FAILURE);
}
// Listen for incoming connections
if (listen(server_fd, 1) < 0) {
perror("Listen failed");
exit(EXIT_FAILURE);
}
printf("Server listening on port %d...\n", PORT);
// Accept a connection
if ((new_socket = accept(server_fd, (struct sockaddr
*)&client_addr,
(socklen_t*)&addrlen)) < 0) {
perror("Accept failed");
exit(EXIT_FAILURE);
}
// Read data from the client
ssize_t valread = read(new_socket, buffer, BUFFER_SIZE);
printf("Received from client: %s\n", buffer);
// Close the connection
close(new_socket);
close(server_fd);
return 0;
}
```
### Hello Client (client.c):
```c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#define PORT 8080
#define SERVER_IP "127.0.0.1"
#define MESSAGE "Hello, world!"
int main() {
int client_socket;
struct sockaddr_in server_addr;
// Create socket
if ((client_socket = socket(AF_INET, SOCK_STREAM, 0)) == 0) {
perror("Socket creation failed");
exit(EXIT_FAILURE);
}
// Setup server address structure
server_addr.sin_family = AF_INET;
server_addr.sin_port = htons(PORT);
// Convert IPv4 and IPv6 addresses from text to binary form
if (inet_pton(AF_INET, SERVER_IP, &server_addr.sin_addr) <= 0)
{
perror("Invalid address/ Address not supported");
exit(EXIT_FAILURE);
}
// Connect to the server
if (connect(client_socket, (struct sockaddr *)&server_addr,
sizeof(server_addr)) <
0) {
perror("Connection failed");
exit(EXIT_FAILURE);
}
// Send data to the server
send(client_socket, MESSAGE, strlen(MESSAGE), 0);
// Close the connection
close(client_socket);
return 0;
}
Ans.
Below are simple examples of an Echo server and an Echo client written in
C for estimating the round trip time from the client to the server. The server
is designed to accept multiple connections simultaneously.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/socket.h>
#include <pthread.h>
#define PORT 8080
#define BUFFER_SIZE 1024
void *handle_client(void *arg) {
int client_socket = *((int *)arg);
char buffer[BUFFER_SIZE];
ssize_t bytes_received;
// Receive data from the client
while ((bytes_received = recv(client_socket, buffer, sizeof(buffer),
0)) > 0) {
// Send the received data back to the client
send(client_socket, buffer, bytes_received, 0);
memset(buffer, 0, sizeof(buffer)); // Clear the buffer for the next
iteration
}
// Close the client socket
close(client_socket);
pthread_exit(NULL);
}
int main() {
int server_fd, client_socket;
struct sockaddr_in server_addr, client_addr;
Ans.
### Echo Server (udp_echo_server.c):
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#define PORT 8080
#define BUFFER_SIZE 1024
int main() {
int server_fd;
struct sockaddr_in server_addr, client_addr;
socklen_t addrlen = sizeof(server_addr);
char buffer[BUFFER_SIZE];
// Create socket
if ((server_fd = socket(AF_INET, SOCK_DGRAM, 0)) == 0) {
perror("Socket creation failed");
exit(EXIT_FAILURE);
}
// Setup server address structure
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr = INADDR_ANY;
server_addr.sin_port = htons(PORT);
// Bind the socket
if (bind(server_fd, (struct sockaddr *)&server_addr,
sizeof(server_addr)) < 0) {
perror("Bind failed");
exit(EXIT_FAILURE);
}
printf("UDP Server listening on port %d...\n", PORT);
while (1) {
perror("Invalid address/ Address not supported");
exit(EXIT_FAILURE);
}
// Send data to the server
sendto(client_socket, MESSAGE, strlen(MESSAGE), 0, (struct sockaddr
*)&server_addr, sizeof(server_addr));
// Receive and print the echoed message
char buffer[1024] = {0};
socklen_t addrlen = sizeof(server_addr);
ssize_t bytes_received = recvfrom(client_socket, buffer,
sizeof(buffer), 0, (struct
sockaddr *)&server_addr, &addrlen);
printf("Echoed message from server: %.*s\n", (int)bytes_received,
buffer);
// Close the connection
close(client_socket);
return 0;
}
Compile and run the server in one terminal window:
```bash
gcc udp_echo_server.c -o udp_echo_server
./udp_echo_server
```
Compile and run the client in another terminal window:
```bash
gcc udp_echo_client.c -o udp_echo_client
./udp_echo_client
```
9.] Write an Echo Client and Echo server using UDP to
estimate the round trip time from client to the server. The
server should be such that it can accept multiple connections
at any given time with multiplexed I/O operations.
Ans.
Echo Server
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/time.h>
#include <sys/types.h>
#define PORT 8080
#define BUFFER_SIZE 1024
#define MAX_CLIENTS 10
int main() {
int server_fd;
struct sockaddr_in server_addr, client_addr;
socklen_t addrlen = sizeof(server_addr);
char buffer[BUFFER_SIZE];
int client_sockets[MAX_CLIENTS];
fd_set readfds;
// Create socket
if ((server_fd = socket(AF_INET, SOCK_DGRAM, 0)) == 0) {
perror("Socket creation failed");
exit(EXIT_FAILURE);
}
// Setup server address structure
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr = INADDR_ANY;
server_addr.sin_port = htons(PORT);
// Bind the socket
if (bind(server_fd, (struct sockaddr *)&server_addr,
sizeof(server_addr)) < 0) {
perror("Bind failed");
exit(EXIT_FAILURE);
}
printf("Multiplexed UDP Server listening on port %d...\n", PORT);
for (int i = 0; i < MAX_CLIENTS; ++i) {
client_sockets[i] = -1;
}
while (1) {
FD_ZERO(&readfds);
FD_SET(server_fd, &readfds);
for (int i = 0; i < MAX_CLIENTS; ++i) {
if (client_sockets[i] != -1) {
FD_SET(client_sockets[i], &readfds);
}
}
// Use select to wait for activity on any of the sockets
if (select(FD_SETSIZE, &readfds, NULL, NULL, NULL) < 0) {
perror("Select failed");
exit(EXIT_FAILURE);
}
// Check for activity on the server socket (new connection)
if (FD_ISSET(server_fd, &readfds)) {
ssize_t bytes_received = recvfrom(server_fd, buffer, BUFFER_SIZE,
0,
(struct sockaddr *)&client_addr, &addrlen);
// Find an empty slot in the client_sockets array
int empty_slot = -1;
for (int i = 0; i < MAX_CLIENTS; ++i) {
if (client_sockets[i] == -1) {
empty_slot = i;
break;
}
}
// If an empty slot is found, store the new client socket
if (empty_slot != -1) {
client_sockets[empty_slot] = socket(AF_INET, SOCK_DGRAM, 0);
connect(client_sockets[empty_slot], (struct sockaddr
*)&client_addr,
addrlen);
}
// Echo the received data back to the client
for (int i = 0; i < MAX_CLIENTS; ++i) {
if (client_sockets[i] != -1) {
send(client_sockets[i], buffer, bytes_received, 0);
}
}
memset(buffer, 0, sizeof(buffer)); // Clear the buffer for the
next iteration
}
// Check for activity on the client sockets (received data)
for (int i = 0; i < MAX_CLIENTS; ++i) {
if (client_sockets[i] != -1 && FD_ISSET(client_sockets[i],
&readfds)) {
ssize_t bytes_received = recv(client_sockets[i], buffer,
BUFFER_SIZE, 0);
if (bytes_received <= 0) {
// Client closed the connection, remove from the array
close(client_sockets[i]);
client_sockets[i] = -1;
} else {
// Echo the received data back to the client
send(client_sockets[i], buffer, bytes_received, 0);
memset(buffer, 0, sizeof(buffer)); // Clear the buffer for the
next iteration
}
}
}
}
// Close the server socket (this won't be reached in this
example)
close(server_fd);
return 0;
}
Echo Client
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#define PORT 8080
#define SERVER_IP "127.0.0.1"
#define MESSAGE "Hello, server! This is an echo message."
int main() {
int client_socket;
struct sockaddr_in server_addr;
// Create socket
if ((client_socket = socket(AF_INET, SOCK_DGRAM, 0)) == 0) {
perror("Socket creation failed");
exit(EXIT_FAILURE);
}
// Setup server address structure
server_addr.sin_family = AF_INET;
server_addr.sin_port = htons(PORT);
// Convert IPv4 and IPv6 addresses from text to binary form
if (inet_pton(AF_INET, SERVER_IP, &server_addr.sin_addr) <= 0) {
perror("Invalid address/ Address not supported");
exit(EXIT_FAILURE);
}
// Send data to the server
sendto(client_socket, MESSAGE, strlen(MESSAGE), 0, (struct sockaddr
*)&server_addr, sizeof(server_addr));
// Receive and print the echoed message
char buffer[1024] = {0};
socklen_t addrlen = sizeof(server_addr);
ssize_t bytes_received = recvfrom(client_socket, buffer,
sizeof(buffer), 0, (struct
sockaddr *)&server_addr, &addrlen);
printf("Echoed message from server: %.*s\n", (int)bytes_received,
buffer);
// Close the connection
close(client_socket);
return 0;
}
Compile and run the server in one terminal window:
```bash
gcc udp_echo_server_multiplexed.c -o udp_echo_server_multiplexed
./udp_echo_server_multiplexed
```
Compile and run the client in another terminal window:
```bash
gcc udp_echo_client_multiplexed.c -o udp_echo_client_multiplexed
./udp_echo_client_multiplexed
```
These programs use UDP for communication and `select` for
multiplexed I/O operations. The server can handle multiple clients
simultaneously and echoes messages back to each client.
```tcl
# Bellman-Ford Routing Algorithm Simulation in NS2
# Create a new simulator instance
set ns [new Simulator]
Keep in mind that this is a simplified example, and you may need to adjust
the script based on your specific requirements. You can explore additional
NS2 functionalities and parameters to customize the simulation further.
11.] Analysis of packets using Wireshark, Network simulations
Ans.
Wireshark is a widely-used network protocol analyzer that allows you to
capture and analyze the traffic on a network. Network simulations, on the
other hand, involve using tools like Network Simulator 2 (NS2) or other
simulation environments to model and study network behavior in a
controlled, virtual environment.
Let's discuss how you can analyze packets using Wireshark in the context
of network simulations:
1. **Capture Packets:**
- Start Wireshark and select the network interface through which you
want to capture packets.
- Click on the "Start" or "Capture" button to begin capturing packets.
2. **Filter Packets:**
- Use display filters to focus on specific types of packets or traffic. For
example, you can filter by IP address, protocol, port, etc.
6. **Apply Colorization:**
- Wireshark uses colorization to highlight different types of packets.
Understanding the color scheme can help you quickly identify issues or
patterns in the network traffic.
6. **Protocol-Specific Analysis:**
- Depending on the protocols used in your simulation, Wireshark allows
for in-depth analysis of specific protocol behaviors.