Reputation: 125
I'm new to socket programming. I want to send a UDP package to a specific port on another PC in the network. When I analysie my network traffic with Wireshark I see a different port number in the outgoing packages from what I specified in my code. With port=10000 the actual port it gets send to is 4135. When I changed it to port=15000 (just to try something different) it got send to port 38970.
The port numbers wireshark shows must be true, as a receiving program set to listen on these ports (4135 or 38970) does react to sent packages, although the received data seems like garble (the console shows unknown characters, the debug console shows "1\355I\211\321^H\211...").
Any ideas why?
I'm running this on a Debian VM connected to other VMs in a virtual network. A very similar program using TCP worked just fine.
#include <sys/types.h> //Various types, including ssize_t
#include <sys/socket.h> //Types, macros and functions for sockets
#include <netinet/in.h> //Types, including sockaddr_in, macros
#include <arpa/inet.h> //Types and functions, including inet_aton()
#include <unistd.h> //Types, macros and functions for Unix/Posix
#include <stdlib.h> //GP types, macros and functions
#include <stdio.h> //IO operations (streams)
#include <string.h> //Functions for string operations
#define BC_ADDR "192.168.1.255"
int main(int argc, char** argv) {
int clientSocket;
const int setBroadcast = 1;
in_port_t port = 10000;
struct sockaddr_in broadcastAddr;
int broadcastAddrLen = sizeof(struct sockaddr_in);
const char* msg = "Hello World";
//Create a new UDP socket
clientSocket = socket(AF_INET, SOCK_DGRAM, 0);
if(clientSocket > 0) {
printf("Socket created successfully\n");
}
else {
printf("Failure during socket creation\n");
exit(EXIT_FAILURE);
}
//Set socket options to allow broadcasts
int setSockOptStatus = setsockopt(clientSocket, SOL_SOCKET,
SO_BROADCAST, &setBroadcast, sizeof(setBroadcast));
if(setSockOptStatus != 0) {
printf("Error setting socket options!");
close(clientSocket);
return EXIT_FAILURE;
}
//Form boradcast address structure
broadcastAddr.sin_family = AF_INET;
broadcastAddr.sin_port = port;
broadcastAddr.sin_addr.s_addr = inet_addr(BC_ADDR);
//Send broadcast message
sendto(clientSocket, msg, strlen(msg)+1, 0,
(struct sockaddr*) &broadcastAddr, broadcastAddrLen);
//Close socket and exit program
close(clientSocket);
return EXIT_SUCCESS;
}
Upvotes: 0
Views: 515
Reputation: 225227
The problem is how you're setting the port:
broadcastAddr.sin_port = port;
The IP address and port number stored in a struct sockaddr_in
must both be in network byte order which is big-endian byte ordering, i.e. most significant byte first. Your machine apparently uses little-endian byte ordering, i.e. least significant byte first, so by assigning the port number directly to the sin_port
member that conversion is not being done.
This is more apparent if you look at the hexadecimal representation of the expected and actual port numbers:
You need to call the htons()
function, which converts a 16-bit value from host byte order to network byte order:
broadcastAddr.sin_port = htons(port);
Upvotes: 3