Reputation: 788
My code is currently making use of INADDR_ANY, I am testing to see if I am able to send packets from a VM client through a Ubuntu router, [using IPTables] to my host machine.
I am able to ping the Host machine from the client behind the Linux router and the client from the host machine, but when I send a UDP packet it never arrives at the host machine.
The problem is either in one of these two places, the IPTables I set up for routing are not working properly, or in my server code where I am binding to INADDR_ANY, INADDR_ANY does not include VMware Interfaces.
I have looked around, but I could not find specific information. From what I understand there is not reason why it should not work.
Extending Question:
According to this If I run the commands I would be able to replicated the respective NAT, but were it says public ip goes here and private ip goes here is it referring to the destination IP or the public and private interface IP; i.e the IP addresses of eth0 and eth1 ?
Solved
I was setting the iptable rules on the wrong eth card ! So make sure that you are applying the commands on the correct eth.
Upvotes: 0
Views: 189
Reputation: 16540
The following code is the client side of a UDP connection.
This worked with ubuntu linux, over VM, over windows XP.
Note: code statements on the left margin are (generally) for debug
Note: system functions 'sendto()' and 'recvfrom()' are the correct calls for UDP communications.
Note: the function capitalization, etc are per the local the coding style being used.
Note: as with any 'real life' project, the majority of the code is to handle errors.
You will probably be most interested in the create_UDP_socket()
function.
/* *************** Included files************************************* */
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h> // for system() and itoa() utilities
#include <stdarg.h> // for va_list(), etc
#include <string.h> // string handling utilities
#include <semaphore.h> // semaphores handling utilities
#include <fcntl.h> // symbolic definitions for flags bits
#include <sys/types.h> // contains definitions of data types used in system calls
#include <sys/socket.h>// type definitions (I.E. struct sockaddr_in)
#include <sys/stat.h> // symbolic definitions for permission bits and open()
#include <sys/ipc.h> // ipc interface utilities
#include <sys/shm.h> // shared memory utilities
#include <arpa/inet.h> // defines INADDR_ANY, etc
#include <errno.h> // for accessing errno and related functions
#include <stdbool.h> // define true, false, bool
#include <time.h>
// contains common data type definitions
#include "localTypes.h"
// contains data definitions for ON and OFF, enum enumReturnStatus
#include "Defines.h"
// contains prototypes for writing to Log file
#include "CommonWriteLog.h"
// contains prototypes, and data type definitions
#include "CommonConfiguration.h"
//contains prototypes for globally visible functions in this file
#include "Common_UDP_Utilities.h"
/* *************** Global variables *********************************** */
/* *************** File Static Variables ****************************** */
/* *************** Code *********************************************** */
enum enumReturnStatus create_UDP_socket( INT32 taskSelector, INT32 *pUDPsocket_FD )
{
enum enumReturnStatus returnStatus = eRS_Success; // indicate success
INT32 LocalPort;
INT32 socket_FD;
struct sockaddr_in *pLocal_sockaddr;
char *txtAddress;
if( is_taskSelector_Valid( taskSelector ) )
{ // then parameters valid
socket_FD = get_UDPsocket_FD( eTask_Retrieve_GPS );
if( 0 >= socket_FD )
{ // then socket not yet opened
pLocal_sockaddr = get_pUDPsocket_sockaddr( taskSelector );
txtAddress = inet_ntoa((*pLocal_sockaddr).sin_addr);
fprintf(stdout, "OPENING SOCKET on socket addresss: %s \n", txtAddress );
if( NULL != pLocal_sockaddr )
{ // then, sockaddr configured
LocalPort = get_UDPsocket_LocalPort( taskSelector );
fprintf(stdout, "OPENING SOCKET on PORT: %d \n", LocalPort );
if( 0 <= LocalPort )
{ // then port configured
socket_FD = socket( AF_INET, SOCK_DGRAM, IPPROTO_UDP );
if( -1 != socket_FD )
{ // then, socket creation successful
int TurnOn = 1;
returnStatus = setsockopt( socket_FD, SOL_SOCKET, SO_REUSEADDR, &TurnOn, sizeof( TurnOn ) );
if ( eRS_Success == returnStatus )
{ // then setsockopt() successful
bzero((char *) pLocal_sockaddr, sizeof(struct sockaddr_in) );
pLocal_sockaddr->sin_family = AF_INET;
pLocal_sockaddr->sin_port = htons( LocalPort );
pLocal_sockaddr->sin_addr.s_addr = htonl(INADDR_ANY); // todo: change to specific GPS IP address
CommonWriteLog( eLL_Info,
"INFO:File:%s: Line:%d:\n\t%s 0X%08X %d\n\n",
__FILE__, __LINE__,
"addr.sin_port =",
pLocal_sockaddr->sin_port,
pLocal_sockaddr->sin_port );
returnStatus = bind( socket_FD, (struct sockaddr *)pLocal_sockaddr, sizeof(struct sockaddr) );
if( eRS_Success == returnStatus )
{ // then bind successful
returnStatus = set_UDPsocket_FD( taskSelector, socket_FD );
if( eRS_Success != returnStatus )
{ // then set_UDPsocket_FD failed
CommonWriteLog( eLL_Error,
get_pFormatString( eFormat_EFFL_string ),
__FILE__, __LINE__,
"Function:set_UDPsocket_FD() failed" );
returnStatus = eRS_UDP_Create_Failure; // indicate error occurred
close( socket_FD );
socket_FD = -1;
}
// set callers data
*pUDPsocket_FD = socket_FD;
}
else
{ // else, bind() failed
CommonWriteLog( eLL_Error,
get_pFormatString( eFormat_EFFL_taskSelector_dataIndex_string_string ),
__FILE__, __LINE__,
taskSelector, 0,
"LibFunc:bind() failed",
strerror(errno) );
} // endif( bind )
}
else
{ // else setsockopt() failed
CommonWriteLog( eLL_Error,
get_pFormatString( eFormat_EFFL_taskSelector_dataIndex_string_string ),
__FILE__, __LINE__,
taskSelector, 0,
"LibFunc:setsockopt( SO_REUSEADDR ) failed",
strerror(errno) );
} // endif( SO_REUSEADDR )
}
else
{ // else failed to create socket
fprintf(stdout, "FAILED TO OPEN SOCKET: \n" );
fflush(stdout);
system("sync;sync;");
exit(EXIT_FAILURE);
CommonWriteLog( eLL_Error,
get_pFormatString( eFormat_EFFL_taskSelector_dataIndex_string_string ),
__FILE__, __LINE__,
taskSelector, 0,
"LibFunc:socket() failed",
strerror(errno) );
returnStatus = eRS_SystemCall_Failure; // indicate error occured
} // endif( socket )
}
else
{ // else port not configured
CommonWriteLog( eLL_Error,
get_pFormatString( eFormat_EFFL_taskSelector_dataIndex_string ),
__FILE__, __LINE__,
taskSelector, 0,
"port not configured" );
returnStatus = eRS_Configuration_Failure; // indicate error occurred
}
}
else
{ // else get pUDP sockaddr failed
CommonWriteLog( eLL_Error,
get_pFormatString( eFormat_EFFL_taskSelector_dataIndex_string ),
__FILE__, __LINE__,
taskSelector, 0,
"Function:get_pUDPsocket_sockaddr() failed" );
returnStatus = eRS_UDP_Create_Failure; // indicate error occurred
} // endif( get_pUDPsocket_sockaddr() successful )
} // endif( socket already open )
}
else
{ // else, bad parameters
returnStatus = eRS_UDP_Create_Failure;
CommonWriteLog( eLL_Error,
get_pFormatString( eFormat_EFFL_digit_string ),
__FILE__, __LINE__,
taskSelector,
"Parameter:taskSelector out of range" );
}
return( returnStatus );
} // end create_UDP_socket()
enum enumReturnStatus write_UDP_socket( INT32 Socket_FD, char *pSocket_OutBuffer, INT32 Size, struct sockaddr *pTo_sockaddr, INT32 *pWriteCount )
{
enum enumReturnStatus returnStatus = eRS_Success; // indicate success
INT32 flags = 0;
INT32 sendtoStatus;
// do not call CommonWriteLog() to help avoid extranious 'recursion' messages in logs
// and to avoid recrusive operation
sendtoStatus =
sendto( Socket_FD, pSocket_OutBuffer, Size, flags,pTo_sockaddr, sizeof(struct sockaddr) );
if( 0 <= sendtoStatus )
{ // then, sendto() successful
*pWriteCount = sendtoStatus;
if( sendtoStatus != Size )
{ // then not all char sent
CommonWriteLog( eLL_Error,
"ERROR:File:%s: Line:%d:\n\t%s:num2Send:%d, numSent:%d\n\n",
__FILE__, __LINE__,
"LibFunc:sendto() failed",
Size, sendtoStatus );
returnStatus = eRS_UDP_Write_Failure; // indicate error occurred
}
}
else
{
CommonWriteLog( eLL_Error,
get_pFormatString( eFormat_EFFL_string_string ),
__FILE__, __LINE__,
"LibFunc:sendto() failed",
strerror(errno) );
returnStatus = eRS_SystemCall_Failure; // indicate error occurred
*pWriteCount = 0;
}
return( returnStatus );
} // end write_UDP_socket()
enum enumReturnStatus read_UDP_socket( INT32 Socket_FD, char *pSocket_InBuffer, INT32 Size, INT32 *pReadCount )
{
enum enumReturnStatus returnStatus = eRS_Success;
INT32 readStatus = 0; // result of call to recvfrom()
INT32 flags = 0; // option parameter for call to recvfrom()
struct sockaddr_in from_sockaddr;
UINT32 slen = 0; // sizeof struct sockaddr_in
memset( &from_sockaddr, 0x00, sizeof(from_sockaddr) );
slen = sizeof( struct sockaddr_in );
readStatus = recvfrom( Socket_FD, pSocket_InBuffer,Size, flags,(struct sockaddr*)&from_sockaddr, &slen ); // filled during call
if( 0 > readStatus )
{ // then, an I/O error occurred
CommonWriteLog( eLL_Error,
get_pFormatString( eFormat_EFFL_string_string ),
__FILE__, __LINE__,
"LibFunc:recvfrom() failed",
strerror(errno) );
*pReadCount = 0;
returnStatus = eRS_SystemCall_Failure; // indicate error occurred
}
else
{ //else 0 or more bytes read
// update callers' info
*pReadCount = readStatus;
}
return( returnStatus );
} // end read_UDP_socket()
/* ******************************************************************** **
** End of source file: Common_UDP_Utilities.c
** ******************************************************************** */
Upvotes: 1