From b2c2e5c5b1eefa07a3aff95930cae6c9d1b6bc52 Mon Sep 17 00:00:00 2001 From: MikalaiR Date: Sun, 23 Aug 2015 12:41:40 +0000 Subject: SkypeWeb: more login fixes. git-svn-id: http://svn.miranda-ng.org/main/trunk@15017 1316c22d-e87f-b044-9b9b-93d7a3e3ba9c --- protocols/SkypeWeb/src/skype_login.cpp | 18 +++++-- protocols/SkypeWeb/src/skype_polling.cpp | 88 +++++++++++++++++--------------- protocols/SkypeWeb/src/skype_proto.cpp | 46 +++++++++++++---- protocols/SkypeWeb/src/skype_proto.h | 17 +++--- protocols/SkypeWeb/src/skype_timers.cpp | 4 +- protocols/SkypeWeb/src/skype_trouter.cpp | 61 +++++++++++----------- 6 files changed, 139 insertions(+), 95 deletions(-) (limited to 'protocols/SkypeWeb/src') diff --git a/protocols/SkypeWeb/src/skype_login.cpp b/protocols/SkypeWeb/src/skype_login.cpp index 3db5b33aaf..13b6e605fe 100644 --- a/protocols/SkypeWeb/src/skype_login.cpp +++ b/protocols/SkypeWeb/src/skype_login.cpp @@ -34,7 +34,7 @@ void CSkypeProto::Login() ProtoBroadcastAck(NULL, ACKTYPE_LOGIN, ACKRESULT_FAILED, NULL, LOGIN_ERROR_UNKNOWN); return; } - HistorySynced = isTerminated = false; + HistorySynced = m_bThreadsTerminated = false; if ((tokenExpires - 1800) > time(NULL)) OnLoginSuccess(); else @@ -48,6 +48,8 @@ void CSkypeProto::Login() void CSkypeProto::OnLoginOAuth(const NETLIBHTTPREQUEST *response) { + if (!IsStatusConnecting(m_iStatus)) return; + if (response == NULL || response->pData == NULL) { ProtoBroadcastAck(NULL, ACKTYPE_LOGIN, ACKRESULT_FAILED, NULL, LOGIN_ERROR_UNKNOWN); @@ -121,7 +123,9 @@ void CSkypeProto::OnLoginOAuth(const NETLIBHTTPREQUEST *response) } void CSkypeProto::OnLoginSuccess() { - isTerminated = false; + if (!IsStatusConnecting(m_iStatus)) return; + + m_bThreadsTerminated = false; ProtoBroadcastAck(NULL, ACKTYPE_LOGIN, ACKRESULT_SUCCESS, NULL, 0); li.api.szToken = getStringA("TokenSecret"); @@ -133,6 +137,8 @@ void CSkypeProto::OnLoginSuccess() void CSkypeProto::OnEndpointCreated(const NETLIBHTTPREQUEST *response) { + if (!IsStatusConnecting(m_iStatus)) return; + m_iStatus++; if (response == NULL) @@ -171,7 +177,7 @@ void CSkypeProto::OnEndpointCreated(const NETLIBHTTPREQUEST *response) if (m_iStatus++ > SKYPE_MAX_CONNECT_RETRIES) { - debugLogA(__FUNCTION__ ": failed to get create endpoint"); + debugLogA(__FUNCTION__ ": failed to create endpoint (too many connect retries)"); ProtoBroadcastAck(NULL, ACKTYPE_LOGIN, ACKRESULT_FAILED, NULL, LOGIN_ERROR_UNKNOWN); SetStatus(ID_STATUS_OFFLINE); return; @@ -200,7 +206,7 @@ void CSkypeProto::OnEndpointCreated(const NETLIBHTTPREQUEST *response) void CSkypeProto::OnSubscriptionsCreated(const NETLIBHTTPREQUEST *response) { - m_iStatus++; + if (!IsStatusConnecting(m_iStatus)) return; if (response == NULL) { @@ -236,6 +242,8 @@ void CSkypeProto::SendPresence(bool isLogin) void CSkypeProto::OnCapabilitiesSended(const NETLIBHTTPREQUEST *response) { + if (!IsStatusConnecting(m_iStatus)) return; + if (response == NULL || response->pData == NULL) { ProtoBroadcastAck(NULL, ACKTYPE_LOGIN, ACKRESULT_FAILED, NULL, LOGIN_ERROR_UNKNOWN); @@ -255,7 +263,7 @@ void CSkypeProto::OnCapabilitiesSended(const NETLIBHTTPREQUEST *response) FreeList(skypenames); skypenames.destroy(); - m_hPollingThread = ForkThreadEx(&CSkypeProto::PollingThread, 0, NULL); + SetEvent(m_hPollingEvent); SendRequest(new LoadChatsRequest(li), &CSkypeProto::OnLoadChats); SendRequest(new CreateTrouterRequest(), &CSkypeProto::OnCreateTrouter); diff --git a/protocols/SkypeWeb/src/skype_polling.cpp b/protocols/SkypeWeb/src/skype_polling.cpp index e4f503cd08..cec5055c66 100644 --- a/protocols/SkypeWeb/src/skype_polling.cpp +++ b/protocols/SkypeWeb/src/skype_polling.cpp @@ -21,64 +21,68 @@ void CSkypeProto::PollingThread(void*) { debugLogA(__FUNCTION__ ": entering"); - int errors = 0; - isTerminated = false; - while (!isTerminated && errors < POLLING_ERRORS_LIMIT) + int nErrors = 0; + while (!m_bThreadsTerminated) { - PollRequest *request = new PollRequest(li); - request->nlc = m_pollingConnection; - NLHR_PTR response(request->Send(m_hNetlibUser)); - delete request; + WaitForSingleObject(m_hPollingEvent, INFINITE); - if (response == NULL) + while ((nErrors < POLLING_ERRORS_LIMIT) && (m_iStatus > ID_STATUS_OFFLINE || IsStatusConnecting(m_iStatus))) { - errors++; - continue; - } + PollRequest *request = new PollRequest(li); + request->nlc = m_pollingConnection; + NLHR_PTR response(request->Send(m_hNetlibUser)); + delete request; - if (response->resultCode == 200) - { - if (response->pData) + if (response == NULL) { - char *pData = mir_strdup(response->pData); - if (pData != NULL) - { - ForkThread(&CSkypeProto::ParsePollData, pData); - } - else - { - debugLogA(__FUNCTION__ ": memory overflow !!!"); - break; - } + nErrors++; + continue; } - } - else - { - errors++; - if (response->pData) + if (response->resultCode == 200) { - JSONNode root = JSONNode::parse(response->pData); - const JSONNode &error = root["errorCode"]; - if (error != NULL) + if (response->pData) { - int errorCode = error.as_int(); - if (errorCode == 729) + char *pData = mir_strdup(response->pData); + if (pData != NULL) + { + ForkThread(&CSkypeProto::ParsePollData, pData); + } + else { + debugLogA(__FUNCTION__ ": memory overflow !!!"); break; } } } - } + else + { + nErrors++; - m_pollingConnection = response->nlc; - - } + if (response->pData) + { + JSONNode root = JSONNode::parse(response->pData); + const JSONNode &error = root["errorCode"]; + if (error != NULL) + { + int errorCode = error.as_int(); + if (errorCode == 729) + { + break; + } + } + } + } - if (!isTerminated) - { - debugLogA(__FUNCTION__ ": unexpected termination; switching protocol to offline"); - SetStatus(ID_STATUS_OFFLINE); + m_pollingConnection = response->nlc; + + } + + if (m_iStatus > ID_STATUS_OFFLINE) + { + debugLogA(__FUNCTION__ ": unexpected termination; switching protocol to offline"); + SetStatus(ID_STATUS_OFFLINE); + } } m_hPollingThread = NULL; m_pollingConnection = NULL; diff --git a/protocols/SkypeWeb/src/skype_proto.cpp b/protocols/SkypeWeb/src/skype_proto.cpp index 24b1cf110a..0b66f02421 100644 --- a/protocols/SkypeWeb/src/skype_proto.cpp +++ b/protocols/SkypeWeb/src/skype_proto.cpp @@ -49,8 +49,13 @@ CSkypeProto::CSkypeProto(const char* protoName, const TCHAR* userName) : SkinAddNewSoundEx("skype_call_canceled", "SkypeWeb", LPGEN("Incoming call canceled sound")); m_hTrouterEvent = CreateEvent(NULL, FALSE, FALSE, NULL); + m_hPollingEvent = CreateEvent(NULL, FALSE, FALSE, NULL); + m_hTrouterHealthEvent = CreateEvent(NULL, FALSE, FALSE, NULL); SkypeSetTimer(); + + m_hPollingThread = ForkThreadEx(&CSkypeProto::PollingThread, NULL, NULL); + m_hTrouterThread = ForkThreadEx(&CSkypeProto::TRouterThread, NULL, NULL); } CSkypeProto::~CSkypeProto() @@ -61,11 +66,40 @@ CSkypeProto::~CSkypeProto() UnInitNetwork(); UninitPopups(); + if (m_hPollingThread) + { + TerminateThread(m_hPollingThread, NULL); + m_hPollingThread = NULL; + } + CloseHandle(m_hPollingEvent); m_hPollingEvent = NULL; + + if (m_hTrouterThread) + { + TerminateThread(m_hTrouterThread, NULL); + m_hTrouterThread = NULL; + } CloseHandle(m_hTrouterEvent); m_hTrouterEvent = NULL; + CloseHandle(m_hTrouterHealthEvent); + SkypeUnsetTimer(); } +int CSkypeProto::OnPreShutdown(WPARAM, LPARAM) +{ + debugLogA(__FUNCTION__); + + requestQueue->Stop(); + + m_bThreadsTerminated = true; + + ShutdownConnections(); + + SetEvent(m_hPollingEvent); + + return 0; +} + DWORD_PTR CSkypeProto::GetCaps(int type, MCONTACT) { switch (type) @@ -216,7 +250,6 @@ int CSkypeProto::SetStatus(int iNewStatus) delSetting("expires"); } // logout - isTerminated = true; requestQueue->Stop(); ShutdownConnections(); @@ -271,13 +304,4 @@ int CSkypeProto::OnEvent(PROTOEVENTTYPE iEventType, WPARAM wParam, LPARAM lParam } return 1; -} - -int CSkypeProto::OnPreShutdown(WPARAM, LPARAM) -{ - debugLogA(__FUNCTION__); - isTerminated = true; - requestQueue->Stop(); - ShutdownConnections(); - return 0; -} +} \ No newline at end of file diff --git a/protocols/SkypeWeb/src/skype_proto.h b/protocols/SkypeWeb/src/skype_proto.h index 1b3a9d9d38..5aee7df862 100644 --- a/protocols/SkypeWeb/src/skype_proto.h +++ b/protocols/SkypeWeb/src/skype_proto.h @@ -95,8 +95,7 @@ private: RequestQueue *requestQueue; - bool isTerminated, - HistorySynced; + bool HistorySynced; std::map m_mpOutMessages; @@ -104,10 +103,9 @@ private: static std::map languages; HANDLE m_pollingConnection, - m_hPollingThread, - m_hTrouterThread, - m_TrouterConnection, - m_hTrouterEvent; + m_hPollingThread, + m_hTrouterThread, + m_TrouterConnection; TRInfo TRouter; @@ -127,6 +125,13 @@ private: static mir_cs accountsLock; static mir_cs timerLock; + bool m_bThreadsTerminated; + + HANDLE m_hPollingEvent; + HANDLE m_hTrouterEvent; + + HANDLE m_hTrouterHealthEvent; + static CSkypeProto* GetContactAccount(MCONTACT hContact); int __cdecl OnAccountLoaded(WPARAM, LPARAM); diff --git a/protocols/SkypeWeb/src/skype_timers.cpp b/protocols/SkypeWeb/src/skype_timers.cpp index 4ab560cd2f..4ff57975b9 100644 --- a/protocols/SkypeWeb/src/skype_timers.cpp +++ b/protocols/SkypeWeb/src/skype_timers.cpp @@ -26,8 +26,8 @@ void CSkypeProto::ProcessTimer() { PushRequest(new GetContactListRequest(li, NULL), &CSkypeProto::LoadContactList); SendPresence(false); - if (!m_hTrouterThread) - SendRequest(new CreateTrouterRequest(), &CSkypeProto::OnCreateTrouter); + //if (!m_hTrouterThread) + // SendRequest(new CreateTrouterRequest(), &CSkypeProto::OnCreateTrouter); } } diff --git a/protocols/SkypeWeb/src/skype_trouter.cpp b/protocols/SkypeWeb/src/skype_trouter.cpp index e3ee811fa3..1525b6b19a 100644 --- a/protocols/SkypeWeb/src/skype_trouter.cpp +++ b/protocols/SkypeWeb/src/skype_trouter.cpp @@ -103,10 +103,9 @@ void CSkypeProto::OnGetTrouter(const NETLIBHTTPREQUEST *response) int iStart = 0; CMStringA szToken = data.Tokenize(":", iStart).Trim(); TRouter.sessId = szToken.GetString(); - if (!m_hTrouterThread) - m_hTrouterThread = ForkThreadEx(&CSkypeProto::TRouterThread, 0, NULL); - else - SetEvent(m_hTrouterEvent); + + SetEvent(m_hTrouterEvent); + SetEvent(m_hTrouterHealthEvent); if ((time(NULL) - TRouter.lastRegistrationTime) >= 3600) { @@ -134,41 +133,45 @@ void CSkypeProto::TRouterThread(void*) int errors = 0; - while (!isTerminated && errors < POLLING_ERRORS_LIMIT) + while (!m_bThreadsTerminated) { - TrouterPollRequest *request = new TrouterPollRequest(TRouter.socketIo, TRouter.connId, TRouter.st, TRouter.se, TRouter.sig, TRouter.instance, TRouter.ccid, TRouter.sessId); - request->nlc = m_TrouterConnection; - NLHR_PTR response(request->Send(m_hNetlibUser)); - if (response == NULL) + WaitForSingleObject(m_hTrouterEvent, INFINITE); + + while (errors < POLLING_ERRORS_LIMIT && m_iStatus > ID_STATUS_OFFLINE) { - errors++; + TrouterPollRequest *request = new TrouterPollRequest(TRouter.socketIo, TRouter.connId, TRouter.st, TRouter.se, TRouter.sig, TRouter.instance, TRouter.ccid, TRouter.sessId); + request->nlc = m_TrouterConnection; + NLHR_PTR response(request->Send(m_hNetlibUser)); delete request; - continue; - } + if (response == NULL) + { + errors++; + continue; + } - if (response->resultCode == 200) - { - if (response->pData) + if (response->resultCode == 200) { - char *json = strstr(response->pData, "{"); - if (json != NULL) + if (response->pData) { - JSONNode root = JSONNode::parse(json); - std::string szBody = root["body"].as_string(); - const JSONNode &headers = root["headers"]; - const JSONNode body = JSONNode::parse(szBody.c_str()); - OnTrouterEvent(body, headers); + char *json = strstr(response->pData, "{"); + if (json != NULL) + { + JSONNode root = JSONNode::parse(json); + std::string szBody = root["body"].as_string(); + const JSONNode &headers = root["headers"]; + const JSONNode body = JSONNode::parse(szBody.c_str()); + OnTrouterEvent(body, headers); + } } } + else + { + SendRequest(new HealthTrouterRequest(TRouter.ccid.c_str()), &CSkypeProto::OnHealth); + WaitForSingleObject(m_hTrouterHealthEvent, INFINITE); + } + m_TrouterConnection = response->nlc; } - else - { - SendRequest(new HealthTrouterRequest(TRouter.ccid.c_str()), &CSkypeProto::OnHealth); - WaitForSingleObject(m_hTrouterEvent, INFINITE); - } - m_TrouterConnection = response->nlc; - delete request; } m_hTrouterThread = NULL; m_TrouterConnection = NULL; -- cgit v1.2.3