diff options
-rw-r--r-- | protocols/Steam/Steam.vcxproj | 1 | ||||
-rw-r--r-- | protocols/Steam/Steam.vcxproj.filters | 3 | ||||
-rw-r--r-- | protocols/Steam/src/main.cpp | 5 | ||||
-rw-r--r-- | protocols/Steam/src/stdafx.h | 1 | ||||
-rw-r--r-- | protocols/Steam/src/steam_chats.cpp | 300 | ||||
-rw-r--r-- | protocols/Steam/src/steam_login.cpp | 10 | ||||
-rw-r--r-- | protocols/Steam/src/steam_messages.cpp | 28 | ||||
-rw-r--r-- | protocols/Steam/src/steam_proto.cpp | 18 | ||||
-rw-r--r-- | protocols/Steam/src/steam_proto.h | 37 | ||||
-rw-r--r-- | protocols/Steam/src/steam_server.cpp | 3 | ||||
-rw-r--r-- | protocols/Steam/src/steam_ws.cpp | 41 |
11 files changed, 406 insertions, 41 deletions
diff --git a/protocols/Steam/Steam.vcxproj b/protocols/Steam/Steam.vcxproj index 0f29dd2747..445cb17cd3 100644 --- a/protocols/Steam/Steam.vcxproj +++ b/protocols/Steam/Steam.vcxproj @@ -79,6 +79,7 @@ <PrecompiledHeader>Create</PrecompiledHeader>
</ClCompile>
<ClCompile Include="src\steam_avatars.cpp" />
+ <ClCompile Include="src\steam_chats.cpp" />
<ClCompile Include="src\steam_contacts.cpp" />
<ClCompile Include="src\steam_crypt.cpp" />
<ClCompile Include="src\steam_dialogs.cpp" />
diff --git a/protocols/Steam/Steam.vcxproj.filters b/protocols/Steam/Steam.vcxproj.filters index 3bd5e7610d..c1d24742be 100644 --- a/protocols/Steam/Steam.vcxproj.filters +++ b/protocols/Steam/Steam.vcxproj.filters @@ -111,6 +111,9 @@ <ClCompile Include="src\protobuf-c\steammessages_deviceauth.steamclient.pb-c.cpp">
<Filter>Source Files\protobuf</Filter>
</ClCompile>
+ <ClCompile Include="src\steam_chats.cpp">
+ <Filter>Source Files</Filter>
+ </ClCompile>
</ItemGroup>
<ItemGroup>
<ClInclude Include="src\resource.h">
diff --git a/protocols/Steam/src/main.cpp b/protocols/Steam/src/main.cpp index 920345a2e5..828311e40f 100644 --- a/protocols/Steam/src/main.cpp +++ b/protocols/Steam/src/main.cpp @@ -171,6 +171,11 @@ void CMPlugin::InitSteamServices() serviceHandlers[FriendGetRecentMessages] = ServiceResponseHandler(&CSteamProto::OnGotRecentMessages);
serviceHandlers[FriendGetIncomingMessage] = ServiceResponseHandler(&CSteamProto::OnGotIncomingMessage);
+ serviceHandlers[GetMyChatRoomGroups] = ServiceResponseHandler(&CSteamProto::OnGetMyChats);
+ serviceHandlers[GetChatHistory] = ServiceResponseHandler(&CSteamProto::OnGetChatHistory);
+ serviceHandlers[NotifyIncomingChatMessage] = ServiceResponseHandler(&CSteamProto::OnGetChatMessage);
+ serviceHandlers[LeaveChatGroup] = ServiceResponseHandler(&CSteamProto::OnLeftChat);
+
serviceHandlers[GetOwnAuthorizedDevices] = ServiceResponseHandler(&CSteamProto::OnGotDeviceList);
serviceHandlers[NotificationReceived] = ServiceResponseHandler(&CSteamProto::OnGotNotification);
diff --git a/protocols/Steam/src/stdafx.h b/protocols/Steam/src/stdafx.h index 56b6647f22..37c008b5b1 100644 --- a/protocols/Steam/src/stdafx.h +++ b/protocols/Steam/src/stdafx.h @@ -13,6 +13,7 @@ #include <algorithm>
#include <newpluginapi.h>
+#include <m_chat_int.h>
#include <m_contacts.h>
#include <m_database.h>
#include <m_langpack.h>
diff --git a/protocols/Steam/src/steam_chats.cpp b/protocols/Steam/src/steam_chats.cpp new file mode 100644 index 0000000000..7d25507bde --- /dev/null +++ b/protocols/Steam/src/steam_chats.cpp @@ -0,0 +1,300 @@ +/* +Copyright (C) 2012-25 Miranda NG team (https://miranda-ng.org) + +This program is free software; you can redistribute it and/or +modify it under the terms of the GNU General Public License +as published by the Free Software Foundation version 2 +of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program. If not, see <http://www.gnu.org/licenses/>. +*/ + +#include "stdafx.h" + +void CSteamProto::SendGetChatsRequest() +{ + CChatRoomGetMyChatRoomGroupsRequest request; + WSSendService(GetMyChatRoomGroups, request); +} + +void CSteamProto::OnGetMyChats(const CChatRoomGetMyChatRoomGroupsResponse &reply, const CMsgProtoBufHeader &hdr) +{ + if (hdr.failed()) + return; + + for (int i = 0; i < reply.n_chat_room_groups; i++) { + auto *pGroup = reply.chat_room_groups[i]->group_summary; + + SESSION_INFO *pOwner = 0; + + for (int k = 0; k < pGroup->n_chat_rooms; k++) { + auto *pChat = pGroup->chat_rooms[k]; + CMStringW wszId(FORMAT, L"%lld_%d", pGroup->chat_group_id, pChat->chat_id); + + CMStringW wszTitle(Utf2T(pChat->chat_name)); + if (wszTitle.IsEmpty()) + wszTitle = Utf2T(pGroup->chat_group_name); + + auto *si = Chat_NewSession(GCW_CHATROOM, m_szModuleName, wszId, wszTitle); + Chat_AddGroup(si, TranslateT("Owner")); + Chat_AddGroup(si, TranslateT("Participant")); + + if (pOwner == 0) { + for (int j = 0; j < pGroup->n_top_members; j++) { + uint64_t iSteamId = AccountIdToSteamId(pGroup->top_members[j]); + CMStringW wszUserId(FORMAT, L"%lld", iSteamId), wszNick; + + GCEVENT gce = { si, GC_EVENT_JOIN }; + gce.pszUID.w = wszUserId; + + if (iSteamId == m_iSteamId) { + gce.bIsMe = true; + wszNick = getMStringW("Nick"); + } + else if (MCONTACT hContact = GetContact(iSteamId)) + wszNick = Clist_GetContactDisplayName(hContact); + else + wszNick = L"@" + wszUserId; + + gce.pszNick.w = wszNick; + gce.pszStatus.w = (pGroup->top_members[j] == pGroup->accountid_owner) ? TranslateT("Owner") : TranslateT("Participant"); + Chat_Event(&gce); + } + } + else si->pParent = pOwner; + + setDword(si->hContact, "ChatId", pChat->chat_id); + + if (mir_strlen(pGroup->chat_group_tagline)) { + Utf2T wszTopic(pGroup->chat_group_tagline); + Chat_SetStatusbarText(si, wszTopic); + + GCEVENT gce = { si, GC_EVENT_TOPIC }; + gce.pszText.w = wszTopic; + gce.time = time(0); + Chat_Event(&gce); + } + + Chat_Control(si, WINDOW_HIDDEN); + Chat_Control(si, SESSION_ONLINE); + + uint32_t dwLastMsgId = getDword(si->hContact, DBKEY_LASTMSG); + if (pChat->time_last_message > dwLastMsgId) + SendGetChatHistory(si->hContact, dwLastMsgId); + } + } +} + +///////////////////////////////////////////////////////////////////////////////////////// + +void CSteamProto::SendGetChatHistory(MCONTACT hContact, uint32_t iLastMsgId) +{ + CChatRoomGetMessageHistoryRequest request; + request.chat_group_id = GetId(hContact, DBKEY_STEAM_ID); request.has_chat_group_id = true; + request.chat_id = getDword(hContact, "ChatId"); request.has_chat_id = true; + request.last_time = iLastMsgId; request.has_last_time = true; + WSSendService(GetChatHistory, request, (void*)hContact); +} + +void CSteamProto::OnGetChatHistory(const CChatRoomGetMessageHistoryResponse &reply, const CMsgProtoBufHeader &hdr) +{ + if (hdr.failed()) + return; + + if (auto *si = Chat_Find(UINT_PTR(GetRequestInfo(hdr.jobid_target)), m_szModuleName)) { + uint32_t iLastMsg = getDword(si->hContact, DBKEY_LASTMSG); + uint32_t iChatId = getDword(si->hContact, "ChatId"); + + for (int i = (int)reply.n_messages - 1; i >= 0; i--) { + auto *pMsg = reply.messages[i]; + if (pMsg->server_timestamp > iLastMsg) + iLastMsg = pMsg->server_timestamp; + + // some slack, skip it + if (pMsg->server_message) + continue; + + char szMsgId[100], szUserId[100]; + mir_snprintf(szMsgId, "%d_%d", iChatId, pMsg->server_timestamp); + _i64toa(AccountIdToSteamId(pMsg->sender), szUserId, 10); + + DB::EventInfo dbei(db_event_getById(m_szModuleName, szMsgId)); + dbei.flags |= DBEF_UTF; + dbei.eventType = EVENTTYPE_MESSAGE; + dbei.szModule = m_szModuleName; + replaceStr(dbei.pBlob, mir_strdup(pMsg->message)); + dbei.cbBlob = (int)mir_strlen(dbei.pBlob); + dbei.timestamp = pMsg->server_timestamp; + dbei.szId = szMsgId; + dbei.szUserId = szUserId; + + if (dbei.getEvent()) + db_event_edit(dbei.getEvent(), &dbei, true); + else + db_event_add(si->hContact, &dbei); + } + + setDword(si->hContact, DBKEY_LASTMSG, iLastMsg); + } +} + +///////////////////////////////////////////////////////////////////////////////////////// + +void CSteamProto::OnGetChatMessage(const CChatRoomIncomingChatMessageNotification &reply, const CMsgProtoBufHeader &hdr) +{ + if (hdr.failed()) + return; + + CMStringW wszId(FORMAT, L"%lld_%lld", reply.chat_group_id, reply.chat_id); + if (auto *si = Chat_Find(wszId, m_szModuleName)) { + char szMsgId[100], szUserId[100]; + mir_snprintf(szMsgId, "%lld_%d", reply.chat_id, reply.timestamp); + _i64toa(reply.steamid_sender, szUserId, 10); + + DB::EventInfo dbei(db_event_getById(m_szModuleName, szMsgId)); + dbei.flags |= DBEF_UTF; + dbei.eventType = EVENTTYPE_MESSAGE; + dbei.szModule = m_szModuleName; + replaceStr(dbei.pBlob, mir_strdup(reply.message)); + dbei.cbBlob = (int)mir_strlen(dbei.pBlob); + dbei.timestamp = reply.timestamp; + dbei.szId = szMsgId; + dbei.szUserId = szUserId; + + if (dbei.getEvent()) + db_event_edit(dbei.getEvent(), &dbei, true); + else + db_event_add(si->hContact, &dbei); + } +} + +///////////////////////////////////////////////////////////////////////////////////////// + +INT_PTR CSteamProto::SvcLeaveChat(WPARAM hContact, LPARAM) +{ + CChatRoomLeaveChatRoomGroupRequest request; + request.chat_group_id = GetId(hContact, DBKEY_STEAM_ID); request.has_chat_group_id = true; + WSSendService(LeaveChatGroup, request, new uint64_t(request.chat_group_id)); + return 0; +} + +void CSteamProto::OnLeftChat(const CChatRoomLeaveChatRoomGroupResponse&, const CMsgProtoBufHeader &hdr) +{ + if (auto *pGroupId = (int64_t *)GetRequestInfo(hdr.jobid_target)) { + for (auto &cc : AccContacts()) { + if (!Contact::IsGroupChat(cc) || GetId(cc, DBKEY_STEAM_ID) != *pGroupId) + continue; + + CMStringW wszId(FORMAT, L"%lld_%lld", *pGroupId, getDword(cc, "ChatId")); + if (auto *si = Chat_Find(wszId, m_szModuleName)) + Chat_Terminate(si); + + db_delete_contact(cc); + } + } +} + +///////////////////////////////////////////////////////////////////////////////////////// + +enum +{ + IDM_LEAVE = 1, +}; + +int CSteamProto::GcEventHook(WPARAM, LPARAM lParam) +{ + GCHOOK *gch = (GCHOOK *)lParam; + if (gch == nullptr) + return 0; + + if (mir_strcmpi(gch->si->pszModule, m_szModuleName)) + return 0; + + switch (gch->iType) { + case GC_USER_MESSAGE: + if (gch->ptszText && mir_wstrlen(gch->ptszText) > 0) { + rtrimw(gch->ptszText); + T2Utf szMessage(gch->ptszText); + + CChatRoomSendChatMessageRequest request; + request.chat_group_id = _wtoi64(gch->si->ptszID); request.has_chat_group_id = true; + request.chat_id = getDword(gch->si->hContact, "ChatId"); request.has_chat_id = true; + request.echo_to_sender = request.has_echo_to_sender = true; + request.message = szMessage; + WSSendService(SendChatMessage, request); + } + break; + + case GC_USER_PRIVMESS: + Chat_SendPrivateMessage(gch); + break; + + case GC_USER_LOGMENU: + Chat_LogMenu(gch); + break; + + case GC_USER_NICKLISTMENU: + break; + } + return 0; +} + +void CSteamProto::Chat_SendPrivateMessage(GCHOOK *gch) +{ + uint64_t iSteamId = _wtoi64(gch->ptszUID); + MCONTACT hContact = GetContact(iSteamId); + if (!hContact) { + PROTOSEARCHRESULT psr = { sizeof(psr) }; + psr.id.w = (wchar_t *)gch->ptszUID; + psr.firstName.w = (wchar_t *)gch->ptszNick; + + hContact = AddToList(PALF_TEMPORARY, &psr); + if (hContact == 0) + return; + + setWString(hContact, "Nick", gch->ptszNick); + Contact::Hide(hContact); + db_set_dw(hContact, "Ignore", "Mask1", 0); + } + + CallService(MS_MSG_SENDMESSAGE, hContact, 0); +} + +void CSteamProto::Chat_LogMenu(GCHOOK *gch) +{ + switch (gch->dwData) { + case IDM_LEAVE: + SvcLeaveChat(gch->si->hContact, 0); + break; + } +} + +///////////////////////////////////////////////////////////////////////////////////////// + +static gc_item sttLogListItems[] = +{ + { LPGENW("&Leave chat session"), IDM_LEAVE, MENU_ITEM } +}; + +int CSteamProto::GcMenuHook(WPARAM, LPARAM lParam) +{ + GCMENUITEMS *gcmi = (GCMENUITEMS *)lParam; + if (gcmi == nullptr) + return 0; + + if (mir_strcmpi(gcmi->pszModule, m_szModuleName)) + return 0; + + if (gcmi->Type == MENU_ON_LOG) { + Chat_AddMenuItems(gcmi->hMenu, _countof(sttLogListItems), sttLogListItems, &g_plugin); + } + else if (gcmi->Type == MENU_ON_NICKLIST) { + } + return 0; +} diff --git a/protocols/Steam/src/steam_login.cpp b/protocols/Steam/src/steam_login.cpp index 1c2c130287..1235130542 100644 --- a/protocols/Steam/src/steam_login.cpp +++ b/protocols/Steam/src/steam_login.cpp @@ -57,7 +57,7 @@ void CSteamProto::Login() CAuthenticationGetPasswordRSAPublicKeyRequest request; request.account_name = username.get(); - WSSendService(GetPasswordRSAPublicKey, request, true); + WSSendAnon(GetPasswordRSAPublicKey, request); } void CSteamProto::OnGotRsaKey(const CAuthenticationGetPasswordRSAPublicKeyResponse &reply, const CMsgProtoBufHeader &hdr) @@ -98,7 +98,7 @@ void CSteamProto::OnGotRsaKey(const CAuthenticationGetPasswordRSAPublicKeyRespon request.platform_type = details.platform_type; request.has_platform_type = true; request.guard_data = machineId; - WSSendService(BeginAuthSessionViaCredentials, request, true); + WSSendAnon(BeginAuthSessionViaCredentials, request); } void CSteamProto::OnBeginSession(const CAuthenticationBeginAuthSessionViaCredentialsResponse &reply, const CMsgProtoBufHeader &hdr) @@ -191,7 +191,7 @@ void CSteamProto::SendConfirmationCode(bool isEmail, const char *pszCode) request.code_type = EAUTH_SESSION_GUARD_TYPE__k_EAuthSessionGuardType_DeviceCode; request.has_code_type = true; request.code = (char*)pszCode; - WSSendService(UpdateAuthSessionWithSteamGuardCode, request, true); + WSSendAnon(UpdateAuthSessionWithSteamGuardCode, request); } void CSteamProto::OnGotConfirmationCode(const CAuthenticationUpdateAuthSessionWithSteamGuardCodeResponse &, const CMsgProtoBufHeader &hdr) @@ -209,7 +209,7 @@ void CSteamProto::SendPollRequest() CAuthenticationPollAuthSessionStatusRequest request; request.client_id = GetId(DBKEY_CLIENT_ID); request.has_client_id = true; request.request_id.data = m_requestId.data(); request.request_id.len = m_requestId.length(); request.has_request_id = true; - WSSendService(PollAuthSessionStatus, request, true); + WSSendAnon(PollAuthSessionStatus, request); } void CSteamProto::OnPollSession(const CAuthenticationPollAuthSessionStatusResponse &reply, const CMsgProtoBufHeader &) @@ -262,7 +262,7 @@ void CSteamProto::OnClientLogon(const CMsgClientLogonResponse &reply, const CMsg ProtoBroadcastAck(NULL, ACKTYPE_STATUS, ACKRESULT_SUCCESS, (HANDLE)ID_STATUS_CONNECTING, m_iStatus = m_iDesiredStatus); SendPersonaStatus(m_iStatus); - SendDeviceListRequest(); + SendGetChatsRequest(); WSSend(EMsg::ClientChatGetFriendMessageHistoryForOfflineMessages, NoResponse()); } diff --git a/protocols/Steam/src/steam_messages.cpp b/protocols/Steam/src/steam_messages.cpp index 8c8cfab442..da65a5b424 100644 --- a/protocols/Steam/src/steam_messages.cpp +++ b/protocols/Steam/src/steam_messages.cpp @@ -1,42 +1,32 @@ #include "stdafx.h"
-int64_t CSteamProto::SendFriendMessage(EChatEntryType entry_type, int64_t steamId, const char *pszMessage)
+void CSteamProto::SendFriendMessage(EChatEntryType entry_type, int64_t steamId, const char *pszMessage, void *pInfo)
{
CFriendMessagesSendMessageRequest request;
request.chat_entry_type = (int)entry_type; request.has_chat_entry_type = true;
request.contains_bbcode = request.has_contains_bbcode = true;
request.steamid = steamId; request.has_steamid = true;
request.message = (char *)pszMessage;
- return WSSendService(FriendSendMessage, request);
+ WSSendService(FriendSendMessage, request, pInfo);
}
void CSteamProto::OnMessageSent(const CFriendMessagesSendMessageResponse &reply, const CMsgProtoBufHeader &hdr)
{
- COwnMessage tmp(0, 0);
- {
- mir_cslock lck(m_csOwnMessages);
- for (auto &it : m_arOwnMessages)
- if (it->iSourceId == hdr.jobid_target) {
- tmp = *it;
- m_arOwnMessages.remove(m_arOwnMessages.indexOf(&it));
- break;
- }
- }
-
- if (!tmp.hContact)
+ auto *pOwn = (COwnMessage*)GetRequestInfo(hdr.jobid_target);
+ if (pOwn == nullptr)
return;
if (hdr.failed()) {
CMStringW wszMessage(FORMAT, TranslateT("Message sending has failed with error %d"), hdr.eresult);
- ProtoBroadcastAck(tmp.hContact, ACKTYPE_MESSAGE, ACKRESULT_FAILED, (HANDLE)tmp.iMessageId, (LPARAM)wszMessage.c_str());
+ ProtoBroadcastAck(pOwn->hContact, ACKTYPE_MESSAGE, ACKRESULT_FAILED, (HANDLE)pOwn->iMessageId, (LPARAM)wszMessage.c_str());
}
else {
uint32_t timestamp = (reply.has_server_timestamp) ? reply.server_timestamp : 0;
- if (timestamp > getDword(tmp.hContact, DBKEY_LASTMSG))
- setDword(tmp.hContact, DBKEY_LASTMSG, timestamp);
+ if (timestamp > getDword(pOwn->hContact, DBKEY_LASTMSG))
+ setDword(pOwn->hContact, DBKEY_LASTMSG, timestamp);
- tmp.timestamp = timestamp;
- ProtoBroadcastAck(tmp.hContact, ACKTYPE_MESSAGE, ACKRESULT_SUCCESS, (HANDLE)tmp.iMessageId, 0);
+ pOwn->timestamp = timestamp;
+ ProtoBroadcastAck(pOwn->hContact, ACKTYPE_MESSAGE, ACKRESULT_SUCCESS, (HANDLE)pOwn->iMessageId, 0);
}
}
diff --git a/protocols/Steam/src/steam_proto.cpp b/protocols/Steam/src/steam_proto.cpp index a21247bf90..f8cee175d0 100644 --- a/protocols/Steam/src/steam_proto.cpp +++ b/protocols/Steam/src/steam_proto.cpp @@ -46,13 +46,17 @@ CSteamProto::CSteamProto(const char *protoName, const wchar_t *userName) : nlu.szSettingsModule = m_szModuleName;
m_hNetlibUser = Netlib_RegisterUser(&nlu);
- debugLogA(__FUNCTION__":Setting protocol / module name to '%s'", m_szModuleName);
+ // groupchat initialization
+ GCREGISTER gcr = {};
+ gcr.dwFlags = GC_TYPNOTIF | GC_DATABASE;
+ gcr.ptszDispName = m_tszUserName;
+ gcr.pszModule = m_szModuleName;
+ Chat_Register(&gcr);
- if (uint32_t iGlobalValue = getDword(DBKEY_LASTMSG)) {
- for (auto &cc : AccContacts())
- setDword(cc, DBKEY_LASTMSG, iGlobalValue);
- delSetting(DBKEY_LASTMSG);
- }
+ CreateProtoService(PS_LEAVECHAT, &CSteamProto::SvcLeaveChat);
+
+ HookProtoEvent(ME_GC_EVENT, &CSteamProto::GcEventHook);
+ HookProtoEvent(ME_GC_BUILDMENU, &CSteamProto::GcMenuHook);
}
CSteamProto::~CSteamProto()
@@ -194,7 +198,7 @@ int CSteamProto::SendMsg(MCONTACT hContact, MEVENT, const char *message) m_arOwnMessages.insert(pOwn);
}
- pOwn->iSourceId = SendFriendMessage(EChatEntryType::ChatMsg, GetId(hContact, DBKEY_STEAM_ID), message);
+ SendFriendMessage(EChatEntryType::ChatMsg, GetId(hContact, DBKEY_STEAM_ID), message, pOwn);
return hMessage;
}
diff --git a/protocols/Steam/src/steam_proto.h b/protocols/Steam/src/steam_proto.h index 446680db43..63473ecb9b 100644 --- a/protocols/Steam/src/steam_proto.h +++ b/protocols/Steam/src/steam_proto.h @@ -29,6 +29,13 @@ #define FriendGetRecentMessages "FriendMessages.GetRecentMessages#1"
#define FriendGetIncomingMessage "FriendMessagesClient.IncomingMessage#1"
+#define GetMyChatRoomGroups "ChatRoom.GetMyChatRoomGroups#1"
+#define GetChatHistory "ChatRoom.GetMessageHistory#1"
+#define SendChatMessage "ChatRoom.SendChatMessage#1"
+#define LeaveChatGroup "ChatRoom.LeaveChatRoomGroup#1"
+
+#define NotifyIncomingChatMessage "ChatRoomClient.NotifyIncomingChatMessage#1"
+
#define NotificationReceived "SteamNotificationClient.NotificationsReceived#1"
struct SendAuthParam
@@ -82,7 +89,6 @@ struct COwnMessage int iMessageId, timestamp = 0;
MCONTACT hContact;
- uint64_t iSourceId = -1;
};
class CSteamProto : public PROTO<CSteamProto>
@@ -137,6 +143,12 @@ class CSteamProto : public PROTO<CSteamProto> // connection
WebSocket<CSteamProto> *m_ws;
+
+ mir_cs m_csRequestLock;
+ std::map<uint64_t, void *> m_requestInfo;
+
+ void SetRequestInfo(uint64_t, void *);
+ void* GetRequestInfo(uint64_t);
void __cdecl ServerThread(void *);
bool ServerThreadStub(const char *szHost);
@@ -147,8 +159,9 @@ class CSteamProto : public PROTO<CSteamProto> void WSSend(EMsg msgType, const ProtobufCppMessage &msg);
void WSSendRaw(EMsg msgType, const MBinBuffer &buf);
+ void WSSendAnon(const char *pszServiceName, const ProtobufCppMessage &msg);
void WSSendHeader(EMsg msgType, const CMsgProtoBufHeader &hdr, const ProtobufCppMessage &msg);
- int64_t WSSendService(const char *pszServiceName, const ProtobufCppMessage &msg, bool bAnon = false);
+ void WSSendService(const char *pszServiceName, const ProtobufCppMessage &msg, void *pInfo = nullptr);
// requests
bool SendRequest(HttpRequest *request);
@@ -194,6 +207,24 @@ class CSteamProto : public PROTO<CSteamProto> INT_PTR __cdecl GetAvatarCaps(WPARAM, LPARAM);
INT_PTR __cdecl GetMyAvatar(WPARAM, LPARAM);
+ // chats
+ void SendGetChatsRequest();
+ void OnGetMyChats(const CChatRoomGetMyChatRoomGroupsResponse &pResponse, const CMsgProtoBufHeader &hdr);
+
+ void SendGetChatHistory(MCONTACT hContact, uint32_t iLastMsgId);
+ void OnGetChatHistory(const CChatRoomGetMessageHistoryResponse &reply, const CMsgProtoBufHeader &hdr);
+
+ void OnGetChatMessage(const CChatRoomIncomingChatMessageNotification &reply, const CMsgProtoBufHeader &hdr);
+ void OnLeftChat(const CChatRoomLeaveChatRoomGroupResponse &reply, const CMsgProtoBufHeader &hdr);
+
+ INT_PTR __cdecl SvcLeaveChat(WPARAM, LPARAM);
+
+ int __cdecl GcMenuHook(WPARAM, LPARAM);
+ int __cdecl GcEventHook(WPARAM, LPARAM);
+
+ void Chat_LogMenu(GCHOOK *gch);
+ void Chat_SendPrivateMessage(GCHOOK *gch);
+
// contacts
void SetAllContactStatuses(int status);
void SetContactStatus(MCONTACT hContact, uint16_t status);
@@ -262,7 +293,7 @@ class CSteamProto : public PROTO<CSteamProto> mir_cs m_csOwnMessages;
OBJLIST<COwnMessage> m_arOwnMessages;
- int64_t SendFriendMessage(EChatEntryType, int64_t steamId, const char *pszMessage);
+ void SendFriendMessage(EChatEntryType, int64_t steamId, const char *pszMessage, void *pInfo = nullptr);
void OnGotIncomingMessage(const CFriendMessagesIncomingMessageNotification &reply, const CMsgProtoBufHeader &hdr);
void OnMessageSent(const CFriendMessagesSendMessageResponse &reply, const CMsgProtoBufHeader &hdr);
int __cdecl OnPreCreateMessage(WPARAM, LPARAM lParam);
diff --git a/protocols/Steam/src/steam_server.cpp b/protocols/Steam/src/steam_server.cpp index 41a9ca550e..0714e10e78 100644 --- a/protocols/Steam/src/steam_server.cpp +++ b/protocols/Steam/src/steam_server.cpp @@ -73,9 +73,8 @@ void CSteamProto::SendDeviceListRequest() WSSendService(GetOwnAuthorizedDevices, request); } -void CSteamProto::OnGotDeviceList(const CDeviceAuthGetOwnAuthorizedDevicesResponse &pResponse, const CMsgProtoBufHeader &hdr) +void CSteamProto::OnGotDeviceList(const CDeviceAuthGetOwnAuthorizedDevicesResponse &, const CMsgProtoBufHeader &) { - } ///////////////////////////////////////////////////////////////////////////////////////// diff --git a/protocols/Steam/src/steam_ws.cpp b/protocols/Steam/src/steam_ws.cpp index 27d244c45c..41acb5efbb 100644 --- a/protocols/Steam/src/steam_ws.cpp +++ b/protocols/Steam/src/steam_ws.cpp @@ -288,16 +288,47 @@ void CSteamProto::WSSendHeader(EMsg msgType, const CMsgProtoBufHeader &hdr, cons m_ws->sendBinary(hdrbuf.data(), hdrbuf.length()); } -int64_t CSteamProto::WSSendService(const char *pszServiceName, const ProtobufCppMessage &msg, bool bAnon) +void CSteamProto::WSSendAnon(const char *pszServiceName, const ProtobufCppMessage &msg) { CMsgProtoBufHeader hdr; hdr.has_client_sessionid = hdr.has_steamid = hdr.has_jobid_source = hdr.has_jobid_target = true; - if (!bAnon) - hdr.steamid = m_iSteamId, hdr.client_sessionid = m_iSessionId; hdr.jobid_source = getRandomInt(); hdr.jobid_target = -1; hdr.target_job_name = (char *)pszServiceName; - WSSendHeader(bAnon ? EMsg::ServiceMethodCallFromClientNonAuthed : EMsg::ServiceMethodCallFromClient, hdr, msg); + WSSendHeader(EMsg::ServiceMethodCallFromClientNonAuthed, hdr, msg); +} + +void CSteamProto::WSSendService(const char *pszServiceName, const ProtobufCppMessage &msg, void *pInfo) +{ + CMsgProtoBufHeader hdr; + hdr.has_client_sessionid = hdr.has_steamid = hdr.has_jobid_source = hdr.has_jobid_target = true; + hdr.steamid = m_iSteamId, hdr.client_sessionid = m_iSessionId; + hdr.jobid_source = getRandomInt(); + hdr.jobid_target = -1; + hdr.target_job_name = (char *)pszServiceName; + + if (pInfo) + SetRequestInfo(hdr.jobid_source, pInfo); - return hdr.jobid_source; + WSSendHeader(EMsg::ServiceMethodCallFromClient, hdr, msg); +} + +///////////////////////////////////////////////////////////////////////////////////////// + +void CSteamProto::SetRequestInfo(uint64_t requestId, void *pInfo) +{ + mir_cslock lck(m_csRequestLock); + m_requestInfo[requestId] = pInfo; +} + +void* CSteamProto::GetRequestInfo(uint64_t requestId) +{ + mir_cslock lck(m_csRequestLock); + auto it = m_requestInfo.find(requestId); + if (it == m_requestInfo.end()) + return nullptr; + + void *pRet = it->second; + m_requestInfo.erase(it); + return pRet; } |