Witam
Otóż na bazie różnych źródeł w internecie, napisałem program, który łączy się z jakimś serwerem i wyświetla nam odpowiedź. Programik jest konsolowy, ale ogólnie działa, jeśli połączy się z serwerem to wyświetli ramkę zwrotną (nagłówek + plik np index.html).
Problem polega na tym, iż podczas gdy funkcje z biblioteki WinSocket łączą się z serwerem, program się zamraża na chwilę, w ogóle nie odpowiada. Jak np nie ma w sieci urządzenia o podanym adresie IP to program potrafi się zamrozić na ok 20 sekund. Gdy urządzenie jest, podczas odpytywania, program się zamraża na ćwierć lub pół sekundy (tak na oko ;P ), chociaż zdarzały się sytuację, iż program się zamrażał nawet na 2, 3 sekundy, mimo iż urządzenie było w sieci (brak problemów sprzętowych).
Sęk w tym, że jak będę potrzebował odpytywać układ np co 3 sekundy, to to może być dość uciążliwe (tutaj jest tylko program łączący się z serwerem raz, w innym programie wywołuję funkcję "main" ok. raz na 3 sek). Czy jest jakiś sposób, a w zasadzie inna metoda, by uniknąć takich zgrzytów? A może akurat wykorzystywany przeze mnie sposób jest jednym z najgorszych jakie mogłem znaleźć w sieci?
Z góry dziękuję za wszelką pomoc :)
PS: gdy będę chciał przenieść program do wersji okienkowej (korzystając z WinForms + MVS C++ 2005), to chyba implementowanie tego nie będzie najlepszym pomysłem, i wydaje mi się że WinForms mają już wbudowane coś tego typu? Oczywiście nie chodzi mi o to, by forumowicze od razu mi podali cały kod na tacy, ale wystarczy słowo klucz, z jakich funkcji, bibliotek czy coś w tym stylu skorzystać pisząc program w WinForms. Później mogę sobie sam poszukać :)
Tutaj jest kod źródłowy jakby ktoś chciał zobaczyć:
(Jakby ktoś chciał sprawdzić, to musi do zmiennej hostname wpisać jakiś adres ip (sam adres ip), 192.168.1.1 niekoniecznie musi działać u każdego :] )
#include <iostream>
#include <string>
#include <stdlib.h>
#include <assert.h>
#include <Winsock2.h>
#define SEND_RQ(MSG) send(sock,MSG,strlen(MSG),0);
using namespace std;
int Result(int result);
int main()
{
int iResult;
string message;
char *hostname = "192.168.1.1";
WSADATA WsaData;
WSAStartup (0x0101, &WsaData);
sockaddr_in sin;
int sock = socket(AF_INET, SOCK_STREAM, 0);
if (sock == -1)
Result( -100);
sin.sin_family = AF_INET;
sin.sin_port = htons( (unsigned short)80);
struct hostent * host_addr = gethostbyname(hostname);
if(host_addr==NULL)
{
cout<<"Unable to locate host"<<endl;
Result( -103);
}
sin.sin_addr.s_addr = *((int*)*host_addr->h_addr_list);
cout<<"Port :"<<sin.sin_port<<", Address : "<< sin.sin_addr.s_addr<<endl;
if( connect (sock,(const struct sockaddr *)&sin, sizeof(sockaddr_in) ) == -1 )
{
cout<<"connect failed"<<endl;
Result( -101);
}
SEND_RQ("POST /test.html HTTP/1.0\n\rHost:");
SEND_RQ(hostname); //192.168.1.1
SEND_RQ("\n\rUser-Agent: Mozilla/4.0\n\r\n\r");
char c1[1];
int l,line_length;
bool loop = true;
bool bHeader = false;
while(loop)
{
l = recv(sock, c1, 1, 0);
if(l<0)
loop = false;
if(c1[0]=='\n')
{
if(line_length == 0)
loop = false;
line_length = 0;
if(message.find("200") != string::npos) //lub samo "200"
bHeader = true;
}
else if(c1[0]!='\r')
line_length++;
cout<<c1[0];
message += c1[0];
}
message="";
if(bHeader)
{
char p[1024];
while((l = recv(sock,p,1023,0)) > 0)
{
cout.write(p,l) ;
p[l] = '\0';
message += p;
}
}
else
Result( -102);
WSACleanup( );
printf("\t\n%s\n", message.c_str()); //zawartość pobranego pliku
system("pause");
return 0;
}
//=================================
// Result
//=================================
int Result(int result)
{
printf("%d\n", result);
system("pause");
exit(result);
}