Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations strongm on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Basic Winsock Problem.

Status
Not open for further replies.

Sebastiani

Programmer
Nov 3, 2002
38
US
Hi, all. I am having a problem getting connect() to complete successfully. I've tried to isolate the problem a bit, and in the below example simply use the manifest constant INADDR_LOOPBACK for simplicity. Any help would be greatly appreciated!

Code:
#include <iostream>
#include <winsock.h>

int main()
{
 WSADATA wsa;

  if(WSAStartup(0x0101, &wsa)!=0)
   cout << &quot;!WSAStartup()&quot; << endl;

  else
 {
  SOCKET handle = socket(AF_INET, SOCK_STREAM, 0);

    if(handle == INVALID_SOCKET)
     cout << &quot;!socket()&quot; << endl;

    else
   {
    sockaddr_in addr;
    memset(&addr, 0, sizeof(sockaddr_in));
    addr.sin_family = AF_INET;
    addr.sin_port = htons(80);
    addr.sin_addr.s_addr = INADDR_LOOPBACK;

       if(connect(handle, (sockaddr*)&addr, sizeof(sockaddr_in)) == SOCKET_ERROR)
        cout << &quot;!connect()&quot; << endl;

       else
      {
       cout << &quot;Yahoo!&quot; << endl;
      }

    shutdown(handle, SD_BOTH);
    closesocket(handle);
  }

  WSACleanup();
 }
 return cin.get();
}
 
I think, this would help.
////////////server////////////////
#include<conio.h>
#include<io.h>
#include<stdlib.h>
#include<stdio.h>
#include<winsock2.h>
#include<windows.h>
//WS2_32.Lib required
#define PORTNUM 888;
//server
bool run = true;
DWORD WINAPI ThreadProcCln(void* xx)
{
int ns = *(int*)xx;
char buf[80];
while(1)
{
gets(buf);
send(ns, buf, sizeof(buf), 0);
if(strcmp(&quot;exit&quot;, buf) == 0)break;
}
run = false;
return 0;
}
DWORD WINAPI ThreadProcSvr(void* xx)
{
int ns = *(int*)xx;
char buf[80];
HANDLE hThreadCln = 0;
ULONG th_id;
while(1)
{
int nbytes = recv(ns, buf, sizeof(buf), 0);
if(!hThreadCln)hThreadCln = CreateThread(0, 0, ThreadProcCln, (void*)&ns, 0, &th_id);
if(!hThreadCln){printf(&quot;error on creating thread\n&quot;);exit(1);}
printf(&quot;%s\n&quot;, buf);
if(strcmp(&quot;exit&quot;, buf) == 0)break;
}
run = false;
return 0;
}
int main()
{
WORD wVersionRequested = MAKEWORD( 2, 2 );
WSADATA wsd;
WSAStartup(wVersionRequested, &wsd);
int s, ns;
int nport;
nport = PORTNUM;
nport = htons((u_short)nport);
sockaddr_in svr_addr, cln_addr;
s = socket(AF_INET, SOCK_STREAM, 0);
if((s = socket(AF_INET, SOCK_STREAM, 0)) == INVALID_SOCKET)
{
printf(&quot;error on calling socket()\n&quot;);
exit(1);
}
svr_addr.sin_family = AF_INET;
svr_addr.sin_addr.S_un.S_addr = (u_long)INADDR_ANY;
svr_addr.sin_port = nport;
if(bind(s, (const sockaddr*)&svr_addr, sizeof(svr_addr)) == -1)
{
printf(&quot;error on calling bind()&quot;);
exit(1);
}
printf(&quot;server ready: %s\n&quot;, inet_ntoa(svr_addr.sin_addr));
if(listen(s, 5) == -1)
{
printf(&quot;error on calling listen()\n&quot;);
exit(1);
}

while(1)
{
int addrlen;
addrlen = sizeof(cln_addr);
if((ns = accept(s, (sockaddr*)&cln_addr, &addrlen)) == -1)
{
printf(&quot;error on calling accept\n&quot;);
exit(1);
}
printf(&quot;client: %s\n&quot;, inet_ntoa(cln_addr.sin_addr));
int nbytes;
char buf[80];
ULONG th_id;
HANDLE hThreadSvr = 0;
hThreadSvr = CreateThread(0, 0, ThreadProcSvr, (void*)&ns, 0, &th_id);
if(!hThreadSvr){printf(&quot;error on creating thread&quot;);exit(1);}
while(run);
close(ns);
close(s);
exit(0);
}
return 0;
}
////////////server////////////////
////////////client////////////////
#include<io.h>
#include<stdio.h>
#include<stdlib.h>
#include<winsock2.h>
#include<windows.h>
#define PORTNUM 888
#include<windows.h>
bool run = true;
DWORD WINAPI ThreadProcToSvr(void* xx)
{
int ns = *(int*)xx;
char buf[80];
while(1)
{
int nbytes = recv(ns, buf, sizeof(buf), 0);
printf(&quot;%s\n&quot;, buf);
if(strcmp(&quot;exit&quot;, buf) == 0)break;
}
run = false;
return 0;
}
DWORD WINAPI ThreadProcCln(void* xx)
{
int ns = *(int*)xx;
char buf[80];
HANDLE hThreadCln = 0;
ULONG th_id;
while(1)
{
gets(buf);
send(ns, buf, sizeof(buf), 0);
if(!hThreadCln)hThreadCln = CreateThread(0, 0, ThreadProcToSvr, (void*)&ns, 0, &th_id);
if(!hThreadCln){printf(&quot;error on creating thread\n&quot;);exit(1);}
if(strcmp(&quot;exit&quot;, buf) == 0)break;
}
run = false;
return 0;
}

int main(HINSTANCE, HINSTANCE, LPSTR, int)
{
WORD wVersionRequested = MAKEWORD( 2, 2 );
WSADATA wsd;
WSAStartup(wVersionRequested, &wsd);

int s;//SOCKET

sockaddr_in svr_addr;//sei-filipski
hostent *hp;
char buf[80] = &quot;salut la toti&quot;;
if((hp = gethostbyname(&quot;icurici&quot;)) == 0)
{
printf(&quot;error on calling gethostbyname()\n&quot;);
exit(1);
}
strncpy((char*)&svr_addr.sin_addr.S_un.S_un_b, hp->h_addr_list[0], hp->h_length);


svr_addr.sin_family = hp->h_addrtype;
svr_addr.sin_port = htons((u_short)PORTNUM);
if((s = socket(AF_INET, SOCK_STREAM, 0)) == -1)
{
printf(&quot;error on creating socket\n&quot;);
exit(1);
}
if(connect(s, (const sockaddr*)&svr_addr, sizeof(svr_addr)) == -1)
{
printf(&quot;error on calling connect()\n&quot;);
exit(1);
}
ULONG th_id;
HANDLE hThreadSvr = 0;
hThreadSvr = CreateThread(0, 0, ThreadProcCln, (void*)&s, 0, &th_id);
if(!hThreadSvr){printf(&quot;error on creating thread&quot;);exit(1);}
while(run);
close(s);
return 0;
}
////////////client////////////////

Ion Filipski
1c.bmp

ICQ: 95034075
AIM: IonFilipski
filipski@excite.com
 
Thanks for the reply. Unfortunately, it still fails to connect, though I don't know why. The most frustrating thing is that I did this a year or so ago without any problems. :-/

And yes, in the actual program I was using something like:

Code:
hostent * host = gethostbyname(&quot;[URL unfurl="true"]www.google.com&quot;);[/URL]

if(!host) 
 cout << &quot;!gethostbyname()&quot; << endl;
else
{ 
 memcpy(&addr.sin_addr.s_addr, host->h_addr_list[0], sizeof(unsigned long));  
}
Still, no go. Any ideas?
 
memcpy(&addr.sin_addr.s_addr, host->h_addr_list[0], sizeof(addr.sin_addr.s_addr));

Ion Filipski
1c.bmp

ICQ: 95034075
AIM: IonFilipski
filipski@excite.com
 
>> IonFilipski

Actually, the two are identical since S_addr is an unsigned long...

Take a look:

struct in_addr {
union {
struct { u_char s_b1,s_b2,s_b3,s_b4; } S_un_b;
struct { u_short s_w1,s_w2; } S_un_w;
u_long S_addr; <<
} S_un;

But after looking at my code, I saw what I had inadvertantly done:

address = (unsigned long)host->h_addr_list[0];

In other words, I had cast the first element of
h_addr_list[0] to an unsigned long instead of copying a sizeof(unsigned long) amount of bytes from the array.

Anyway, here is the function that I am using now. First it tries to resolve a dotted-decimal string to an address. If that fails, it assumes a hostname was provided.


Code:
unsigned long ip(const char * addr)
{
 unsigned long address = inet_addr(addr);

  if(address == INADDR_NONE)
 {
  hostent * host = gethostbyname(addr);

   if(host)
  {
   memcpy(&address, host->h_addr_list[0], sizeof(unsigned long));
  }
 }
 return address;
}

As to why my connection to INADDR_LOOPBACK failed was simple. I wasn't running a server on my machine to accept it! Major brain-fart there. :)

Thanks for all of the input guys...
 
It does not matter. You must put the correct type of data, even you could put someshing else.

Ion Filipski
1c.bmp

ICQ: 95034075
AIM: IonFilipski
filipski@excite.com
 
No, you're still off.

The struct member S_addr is an unsigned long. It makes no difference.

Look:

struct foo {
unsigned long var;
};

foo bar;

int sz = sizeof(bar.var);

or...

int sz = sizeof(unsigned long);

Do you see why?

 
is a S_addr, not a long. You can use S_addr for mathematical operation or learn to count, but for that is long, not socket address. It does not matter what originally socket address was a long.

Ion Filipski
1c.bmp

ICQ: 95034075
AIM: IonFilipski
filipski@excite.com
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top