problem with recvfrom

O

Omega

I have a problem with recvfrom(). I get a message and no error occurs,
but the struct sockaddr* from is not filled with sender's data.

The client's source code:

#include "reversi.h"
-------------------------------------------------------------------
int main() {
int socket_id = socket(PF_INET,SOCK_DGRAM,0);
struct sockaddr_in adres;
adres.sin_family = PF_INET;
adres.sin_port = htons(PORT_NR);
adres.sin_addr.s_addr = inet_addr("127.0.0.1");
cli_msg msg;
msg.type = CMT_LOGIN;
sendto(socket_id,&msg,sizeof(cli_msg),0,(struct sockaddr*)&adres,sizeof
(struct sockaddr));
printf("wyslalem na 127.0.0.1\n");
ser_main_msg ser_msg;
unsigned int rozmiar;
recvfrom(socket_id,&ser_msg,sizeof(ser_main_msg),0,(struct sockaddr*)
&adres,&rozmiar);
printf("otrzymalem cos a adresu %s",inet_ntoa(adres.sin_addr));
printf("type = %d\n",ser_msg.type);
return 1;
}
-------------------------------------------------------------------
All needed header files are included in reversi.h

Server is rather long, but the inportant part is, the socket is datagram
socket:
-------------------------------------------------------------------
bzero(&klient1, sizeof(struct sockaddr_in));
int ret = recvfrom(sockid,&msg_kli1,sizeof(cli_msg),0,(struct sockaddr*)
&klient1,&rozmiar1);
printf("received %s, %d, %d\n",inet_ntoa(klient1.sin_addr), ret,
errno);
if (msg_kli1.type == CMT_LOGIN) {
msg.type = SMMT_WAIT;
sendto(sockid,&msg,sizeof(ser_main_msg),0,(struct sockaddr*)
&klient1,rozmiar1);
printf("send SMMT_WAIT to address %s\n",inet_ntoa
(klient1.sin_addr));
kli_nr++;
-------------------------------------------------------------------
serwer should print:
received 127.0.0.1, 16, 0
send SMMT_WAIT to addrress 127.0.0.1

but it prints:
reveived 0.0.0.0., 16, 0
send SMMT_WAIT to address 0.0.0.0

It happens only when I run the program on my computer, when I tried on
friends computer problem doesn't occur. Any ideas?

Omega
 
K

Keith Thompson

Omega said:
I have a problem with recvfrom(). I get a message and no error occurs,
but the struct sockaddr* from is not filled with sender's data.
[snip]

There is no recvfrom() function in standard C. Followups redirected.
 
D

David Schwartz

int main() {
int socket_id = socket(PF_INET,SOCK_DGRAM,0);
struct sockaddr_in adres;
adres.sin_family = PF_INET;
adres.sin_port = htons(PORT_NR);
adres.sin_addr.s_addr = inet_addr("127.0.0.1");
cli_msg msg;
msg.type = CMT_LOGIN;
sendto(socket_id,&msg,sizeof(cli_msg),0,(struct sockaddr*)&adres,sizeof
(struct sockaddr));
printf("wyslalem na 127.0.0.1\n");
ser_main_msg ser_msg;
unsigned int rozmiar;

Oops, your forgot to initialize 'rozmiar'.
recvfrom(socket_id,&ser_msg,sizeof(ser_main_msg),0,(struct sockaddr*)
&adres,&rozmiar);
printf("otrzymalem cos a adresu %s",inet_ntoa(adres.sin_addr));
printf("type = %d\n",ser_msg.type);
return 1;
Server is rather long, but the inportant part is, the socket is datagram
socket:

Did you remember to initialize "rozmiar1"?
printf("received %s, %d, %d\n",inet_ntoa(klient1.sin_addr), ret,
errno);
if (msg_kli1.type == CMT_LOGIN) {
msg.type = SMMT_WAIT;
sendto(sockid,&msg,sizeof(ser_main_msg),0,(struct sockaddr*)
&klient1,rozmiar1);
printf("send SMMT_WAIT to address %s\n",inet_ntoa
(klient1.sin_addr));
kli_nr++;
-------------------------------------------------------------------
serwer should print:
received 127.0.0.1, 16, 0
send SMMT_WAIT to addrress 127.0.0.1

but it prints:
reveived 0.0.0.0., 16, 0
send SMMT_WAIT to address 0.0.0.0

It happens only when I run the program on my computer, when I tried on
friends computer problem doesn't occur. Any ideas?

Passing an uninitalized value to 'recvfrom' results in unpredictable
behavior. Initialize it to the allocated length of the structure.

DS
 
C

clayne

Omega said:
I have a problem with recvfrom(). I get a message and no error occurs,
but the struct sockaddr* from is not filled with sender's data.

The client's source code:

ser_main_msg ser_msg;
unsigned int rozmiar;
recvfrom(socket_id,&ser_msg,sizeof(ser_main_msg),0,(struct sockaddr*)
&adres,&rozmiar);

You're not initializing 'rozmiar' to the length of 'adres'.

ssize_t recvfrom(int s, void *buf, size_t len, int flags,
struct sockaddr *from, int *fromlen);

'fromlen' is value-result parameter meaning that recvfrom() uses it's
passed value and before returning modifies the contents of 'fromlen' to
indicate the actual size of the address stored there.

What this means to you is:

unsigned int rozmiar;
rozmiar = sizeof(adres); /* or rozmiar = sizeof(struct sockaddr_in); */
recvfrom(socket_id, &ser_msg, sizeof(ser_main_msg), 0, (struct
sockaddr*)&adres, &rozmiar);

You have to initialize 'fromlen' (in your case rozmiar) to the proper
length before each call to recvfrom(). The reason it works sometimes is
because of any number of random possibilities as to what the contents
of 'rozmiar' are (since it's an auto variable) without you explicitly
initializing it.
 
C

clayne

Omega said:
I have a problem with recvfrom(). I get a message and no error occurs,
but the struct sockaddr* from is not filled with sender's data.

The client's source code:

ser_main_msg ser_msg;
unsigned int rozmiar;
recvfrom(socket_id,&ser_msg,sizeof(ser_main_msg),0,(struct sockaddr*)
&adres,&rozmiar);

You're not initializing 'rozmiar' to the length of 'adres'.

ssize_t recvfrom(int s, void *buf, size_t len, int flags,
struct sockaddr *from, int *fromlen);

'fromlen' is value-result parameter meaning that recvfrom() uses it's
passed value and before returning modifies the contents of 'fromlen' to
indicate the actual size of the address stored there.

What this means to you is:

unsigned int rozmiar;
rozmiar = sizeof(adres); /* or rozmiar = sizeof(struct sockaddr_in); */
recvfrom(socket_id, &ser_msg, sizeof(ser_main_msg), 0, (struct
sockaddr*)&adres, &rozmiar);

You have to initialize 'fromlen' (in your case rozmiar) to the proper
length before each call to recvfrom(). The reason it works sometimes is
because of any number of random possibilities as to what the contents
of 'rozmiar' are (since it's an auto variable) without you explicitly
initializing it.
 
M

Maxim Yegorushkin

Omega said:
I have a problem with recvfrom(). I get a message and no error occurs,
but the struct sockaddr* from is not filled with sender's data.
[]

unsigned int rozmiar;
recvfrom(socket_id,&ser_msg,sizeof(ser_main_msg),0,(struct sockaddr*)
&adres,&rozmiar);

rozmiar must be of type socklen_t and have to be initialized with the
length of your address structure prior the call to recvfrom

socklen_t rozmiar = sizeof adres;

see
http://www.opengroup.org/onlinepubs/009695399/functions/recvfrom.html
 
C

clayne

Maxim said:
rozmiar must be of type socklen_t and have to be initialized with the
length of your address structure prior the call to recvfrom

socklen_t rozmiar = sizeof adres;

To be 100% portable it should be socklen_t - but of course that's not
why it's failing here.
 
L

loic-dev

Hi,
I have a problem with recvfrom(). I get a message and no error occurs,
but the struct sockaddr* from is not filled with sender's data.

ssize_t recvfrom(int socket, void *restrict buffer, size_t length,
int flags, struct sockaddr *restrict address,
socklen_t *restrict address_len);


The 6th parameter /addrlen_len/ is an IN/OUT argument. It should be
initialized to the size of the structure pointed by the /address/
argument prior to calling recvfrom().

HTH,
Loic.

The client's source code:

#include "reversi.h"
-------------------------------------------------------------------
int main() {
int socket_id = socket(PF_INET,SOCK_DGRAM,0);
struct sockaddr_in adres; [snip]
unsigned int rozmiar;

this line should be:
| unsigned int rozmiar = sizeof (adres);

Similarly in the server:
the following line is missing:
| rozmiar1 = sizeof (klient1);
int ret = recvfrom(sockid,&msg_kli1,sizeof(cli_msg),0,(struct sockaddr*)
&klient1,&rozmiar1);
[...]
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,579
Members
45,053
Latest member
BrodieSola

Latest Threads

Top