Hoj ahoj lidi, obracím se na lidi tady protože mi zatím vždy někdo poradil a pomohl mi :)
můj "dotaz" má tři části,
první by byla kontrola kódu a co by jste v něm udělali jinak - lépe..
void CServerDlg::IsBanned(char a[], int nClientId, CPlayerInfo *pPlayerInfo)
{
bool BANNED=false;
FILE *fh = NULL;
fh=fopen(g_LogName,"a+");
SYSTEMTIME now;
GetLocalTime(&now);
fprintf(fh, "\n\n{Incoming Player - START}");
fprintf(fh, "\n %02d:%02d:%02d - %02d.%02d.%d : ", now.wHour, now.wMinute, now.wSecond, now.wDay, now.wMonth, now.wYear);
fprintf(fh, "\n Incoming Player: %s, IP: %s, ", pPlayerInfo->m_szPlayerHandle, m_JoinData[nClientId-1].m_szIP);
FILE *HN = NULL;
HN=fopen("Rommie_Logs/HN_DEBUG.txt","a+");
bool damn=false;
WORD wVersionRequested=MAKEWORD(1,1);
WSADATA wsaData;
long res=WSAStartup(wVersionRequested, &wsaData);
unsigned long inaddr = inet_addr (m_JoinData[nClientId-1].m_szIP);
hostent *myhostent;
if(res!=0)
{
damn=true;
fprintf(HN, "\n{HN - Debug}: WSAStartup!=0");
}
if((myhostent = gethostbyaddr((const char FAR *)&inaddr,sizeof(in_addr),AF_INET)) && damn==false)
{
fprintf(HN, "\n{HN}: Got HN");
if(strlen(myhostent->h_name)>5){
fprintf(HN, "\n{HN - Debug}: HN right - %s", myhostent->h_name);
sprintf(m_JoinData[nClientId-1].HNAME,"%s", myhostent->h_name);
}
else{
fprintf(HN, "\n{HN - Debug}: HN is shorter than 5 chars - %s - using IP - %s", myhostent->h_name, m_JoinData[nClientId-1].m_szIP);
sprintf(m_JoinData[nClientId-1].HNAME,"%s", m_JoinData[nClientId-1].m_szIP);
}
}
else
{
fprintf(HN, "\n{HN - Debug}: GetHostByAddr() return no value, using IP - %s", m_JoinData[nClientId-1].m_szIP);
sprintf(m_JoinData[nClientId-1].HNAME,"%s", m_JoinData[nClientId-1].m_szIP);
}
WSACleanup();
for(int l = 0; l < count; l++)
{
int iLen=0;
iLen=strlen(HNBan[l]);
fprintf(HN, "\n{HN - Check}: iLen %d", iLen);
fprintf(HN, "\n{HN - Compare}: Client's HN %s, HNBan[%d]=%s", m_JoinData[nClientId-1].HNAME, l, HNBan[l]);
if(iLen>5)
{
if(strstr(m_JoinData[nClientId-1].HNAME, HNBan[l]))
{
fprintf(HN, "\n{HN - FoundBannedHN}: Client's HN %s, HNBan[%d]=%s DING, BANNED HN!", m_JoinData[nClientId-1].HNAME, l, HNBan[l]);
BANNED=true;
}
}
}
if(BANNED==true)
{
fprintf(fh, "\n HN: %s -> HN or his part is BLACKLISTED, kicking player out of game...", m_JoinData[nClientId-1].HNAME);
fprintf(fh, "\n{Incoming Player - END}");
char szMsg[512];
sprintf(szMsg, "Player: %s - HN: %s - KICKED - (BLACKLISTED).", pPlayerInfo->m_szPlayerHandle, m_JoinData[nClientId-1].HNAME);
m_lstShellMsgs_Shell.AddTail( szMsg );
char szBuf[512];
ostrstream memStream( szBuf, sizeof( szBuf ));
memStream << (( BYTE )SERVERSHELL_MESSAGE ) << szMsg << ends;
EnterCriticalSection( &m_CS );
m_pServerMgr->SendToServerShell( szBuf, sizeof( szBuf ));
LeaveCriticalSection( &m_CS );
EnterCriticalSection( &m_CS );
if(m_pServerMgr->BootClient(nClientId))
LeaveCriticalSection( &m_CS );
}
else
{
fprintf(fh, "\n HN: %s -> Allow to join, HN is not blacklisted.", m_JoinData[nClientId-1].HNAME);
fprintf(fh, "\n{Incoming Player - END}");
char szMsg[512];
sprintf(szMsg, "Player: %s - HN: %s - (if you see plain IP, DNS lookup was failed.).", pPlayerInfo->m_szPlayerHandle, m_JoinData[nClientId-1].HNAME);
m_lstShellMsgs_Shell.AddTail( szMsg );
char szBuf[512];
ostrstream memStream( szBuf, sizeof( szBuf ));
memStream << (( BYTE )SERVERSHELL_MESSAGE ) << szMsg << ends;
EnterCriticalSection( &m_CS );
m_pServerMgr->SendToServerShell( szBuf, sizeof( szBuf ));
LeaveCriticalSection( &m_CS );
}
fclose(HN);
fclose(fh);
}
kód mi fuguje fajn, ALE je tu jeden problém a to:
myhostent = gethostbyaddr((const char FAR *)&inaddr,sizeof(in_addr),AF_INET)
konkrétně v "if((myhostent = gethostbyaddr((const char FAR *)&inaddr,sizeof(in_addr),AF_INET)) && damn==false)"
když se mi připojuje hráč s IP která z nějakého důvodu nejde přeložit na hostname pomocí toho gethostbyaddr tak mi celá aplikace (dedikovaný server po hru) lagne.. prostě se vlákno na 2-4 sekundy zastaví a ve hře všichni brečí že jsou lagy.. celá ta funkce kterou jsem sem pastl se volá v hlavním voidu Update()
if(m_JoinData[nClientId-1].m_bLog==true)
{
m_JoinData[nClientId-1].m_bLog=false;
IsBanned(m_JoinData[nClientId-1].m_szIP, nClientId, pPlayerInfo);
}
kde m_szIP je char ip adresa.., nClientID je vnitřní ID klienta, a pPlayerInfo je struktura ze které se tahá jméno
napadlo Mně to vyřešit "jednoduše" a to proste "IsBanned(m_JoinData[nClientId-1].m_szIP, nClientId, pPlayerInfo);" zavolat jako jiný thread pomocí "_beginthreadex( 0,0, &IsBanned, this, 0, 0 );"
ale to má dva problémy.. první je že _beginthreadex ?neumí? zavolat funkce s těma třema parametrama, nebo jsem hloupej a nepřišel jsem na to jak, a druhý problém že ta funkce by musela být unsigned int __stdcall což mi způsobí ten problém že by neměla přístup k těm datům co potřebuje..
a třetí část dotazu je zda je možné nahradit "gethostbyaddr" nějakou vyspělejší funkcí na získáni hostname z IP.. prolezl jsem pár fór někde nadávají že je ta funkce zastaralá a pomalá, ale nikde není srozumitelně napsáno jak ji nahradit jinou.
podotknu že projekt je dělaný jako MFC aplikace, Microsoft Visual C++ 6.0 (1998, hodně pravěké, ale bohužel ty originální zdrojáky té hry v jiném - novějším VS nejdou zkompilovat)
Budu velmi rád za každou pomoc, a kdyby se třeba našel někdo kdo by byl ochotný občas na Mé přiblblé dotazy odpovědět na emailu nebo ICQ, vůůůůbec bych se nezlobil :)