summaryrefslogtreecommitdiff
path: root/protocols
diff options
context:
space:
mode:
authorGeorge Hazan <ghazan@miranda.im>2020-07-12 13:12:23 +0300
committerGeorge Hazan <ghazan@miranda.im>2020-07-12 13:12:23 +0300
commit1a0788c26404b5f42b6be2919bff5be261b2f3e7 (patch)
tree766341c3f0af30fd5c8c445ef7e8e9d5c66c3560 /protocols
parentdbf988c60736cc5e226c55b19e6a0a68a085bf3b (diff)
Jabber: ugly scheme with flags replaced with TJabberAuth instantiation
Diffstat (limited to 'protocols')
-rwxr-xr-xprotocols/JabberG/src/jabber_proto.cpp3
-rwxr-xr-xprotocols/JabberG/src/jabber_proto.h21
-rw-r--r--protocols/JabberG/src/jabber_secur.cpp75
-rw-r--r--protocols/JabberG/src/jabber_secur.h27
-rwxr-xr-xprotocols/JabberG/src/jabber_strm_mgmt.cpp5
-rwxr-xr-xprotocols/JabberG/src/jabber_thread.cpp168
-rwxr-xr-xprotocols/JabberG/src/stdafx.h4
7 files changed, 109 insertions, 194 deletions
diff --git a/protocols/JabberG/src/jabber_proto.cpp b/protocols/JabberG/src/jabber_proto.cpp
index 27b02bbf34..b91f9bc881 100755
--- a/protocols/JabberG/src/jabber_proto.cpp
+++ b/protocols/JabberG/src/jabber_proto.cpp
@@ -27,6 +27,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include "jabber_iq.h"
#include "jabber_caps.h"
#include "jabber_disco.h"
+#include "jabber_secur.h"
#pragma warning(disable:4355)
@@ -57,6 +58,7 @@ CJabberProto::CJabberProto(const char *aProtoName, const wchar_t *aUserName) :
m_impl(*this),
m_omemo(this),
m_arChatMarks(50, NumericKeySortT),
+ m_arAuthMechs(1, &TJabberAuth::compare),
m_lstTransports(50, compareTransports),
m_lstRoster(50, compareListItems),
m_iqManager(this),
@@ -250,7 +252,6 @@ CJabberProto::~CJabberProto()
ListWipe();
mir_free(m_tszSelectedLang);
- mir_free(m_gssapiHostName);
mir_free(m_modeMsgs.szOnline);
mir_free(m_modeMsgs.szAway);
diff --git a/protocols/JabberG/src/jabber_proto.h b/protocols/JabberG/src/jabber_proto.h
index 6531e59319..139a7371cd 100755
--- a/protocols/JabberG/src/jabber_proto.h
+++ b/protocols/JabberG/src/jabber_proto.h
@@ -794,26 +794,9 @@ struct CJabberProto : public PROTO<CJabberProto>, public IJabberInterface
ptrA m_szGroupDelimiter;
ptrW m_savedPassword;
- union {
- int m_dwAuthMechs;
- struct {
- bool m_isPlainAvailable : 1;
- bool m_isPlainOldAvailable : 1;
- bool m_isMd5Available : 1;
- bool m_isScramSha1Available : 1;
- bool m_isScramSha1PlusAvailable : 1;
- bool m_isScramSha256Available : 1;
- bool m_isScramSha256PlusAvailable : 1;
- bool m_isNtlmAvailable : 1;
- bool m_isSpnegoAvailable : 1;
- bool m_isKerberosAvailable : 1;
- bool m_isAuthAvailable : 1;
- bool m_isSessionAvailable : 1;
- };
- };
+ OBJLIST<class TJabberAuth> m_arAuthMechs;
+ bool m_isSessionAvailable, m_isAuthAvailable;
- char* m_gssapiHostName;
-
void __cdecl ServerThread(JABBER_CONN_DATA *info);
void OnProcessFailure(const TiXmlElement *node, ThreadData *info);
diff --git a/protocols/JabberG/src/jabber_secur.cpp b/protocols/JabberG/src/jabber_secur.cpp
index 0a20304cc7..c92cc4dc64 100644
--- a/protocols/JabberG/src/jabber_secur.cpp
+++ b/protocols/JabberG/src/jabber_secur.cpp
@@ -28,33 +28,30 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
/////////////////////////////////////////////////////////////////////////////////////////
// ntlm auth - LanServer based authorization
-TNtlmAuth::TNtlmAuth(ThreadData *info, const char *mechanism, const char *hostname) :
- TJabberAuth(info)
+TNtlmAuth::TNtlmAuth(ThreadData *info, const char *mechanism) :
+ TJabberAuth(info, mechanism)
{
- szName = mechanism;
- szHostName = hostname;
+ bIsValid = false;
const wchar_t *szProvider;
if (!mir_strcmp(mechanism, "GSS-SPNEGO"))
- szProvider = L"Negotiate";
+ szProvider = L"Negotiate", priority = 703;
else if (!mir_strcmp(mechanism, "GSSAPI"))
- szProvider = L"Kerberos";
+ szProvider = L"Kerberos", priority = 702;
else if (!mir_strcmp(mechanism, "NTLM"))
- szProvider = L"NTLM";
- else {
-LBL_Invalid:
- bIsValid = false;
- hProvider = nullptr;
+ szProvider = L"NTLM", priority = 701;
+ else
return;
- }
wchar_t szSpn[1024]; szSpn[0] = 0;
if (!mir_strcmp(mechanism, "GSSAPI"))
if (!getSpn(szSpn, _countof(szSpn)))
- goto LBL_Invalid;
+ return;
if ((hProvider = Netlib_InitSecurityProvider(szProvider, szSpn)) == nullptr)
- bIsValid = false;
+ return;
+
+ bIsValid = true;
}
TNtlmAuth::~TNtlmAuth()
@@ -77,9 +74,9 @@ bool TNtlmAuth::getSpn(wchar_t* szSpn, size_t dwSpnLen)
if (name) *name = 0;
else return false;
- if (szHostName && szHostName[0]) {
+ if (info->gssapiHostName && info->gssapiHostName[0]) {
wchar_t *szFullUserNameU = wcsupr(mir_wstrdup(szFullUserName));
- mir_snwprintf(szSpn, dwSpnLen, L"xmpp/%s/%s@%s", szHostName, szFullUserName, szFullUserNameU);
+ mir_snwprintf(szSpn, dwSpnLen, L"xmpp/%s/%s@%s", info->gssapiHostName, szFullUserName, szFullUserNameU);
mir_free(szFullUserNameU);
}
else {
@@ -127,10 +124,10 @@ char* TNtlmAuth::getChallenge(const char *challenge)
// md5 auth - digest-based authorization
TMD5Auth::TMD5Auth(ThreadData *info) :
- TJabberAuth(info),
+ TJabberAuth(info, "DIGEST-MD5"),
iCallCount(0)
{
- szName = "DIGEST-MD5";
+ priority = 301;
}
TMD5Auth::~TMD5Auth()
@@ -206,19 +203,23 @@ char* TMD5Auth::getChallenge(const char *challenge)
/////////////////////////////////////////////////////////////////////////////////////////
// SCRAM-SHA-1 authorization
-TScramAuth::TScramAuth(ThreadData *info, bool bSha1, void *pData, size_t cbLen) :
- TJabberAuth(info),
- hashMethod(bSha1 ? EVP_sha1() : EVP_sha256())
+TScramAuth::TScramAuth(ThreadData *info, const char *pszMech, const EVP_MD *pMethod, int iPriority) :
+ TJabberAuth(info, pszMech),
+ hashMethod(pMethod)
{
- if (pData) {
- szName = bSha1 ? "SCRAM-SHA-1-PLUS" : "SCRAM-SHA-256-PLUS";
+ priority = iPriority;
+
+ if ((iPriority % 10) == 1) {
bindFlag = "p=tls-unique,,";
- bindData.append(pData, cbLen);
+
+ int cbLen;
+ void *pData = Netlib_GetTlsUnique(info->s, cbLen);
+ if (pData == nullptr)
+ bIsValid = false;
+ else
+ bindData.append(pData, cbLen);
}
- else {
- szName = bSha1 ? "SCRAM-SHA-1" : "SCRAM-SHA-256";
- bindFlag = "n,,";
- }
+ else bindFlag = "n,,";
}
TScramAuth::~TScramAuth()
@@ -335,14 +336,10 @@ bool TScramAuth::validateLogin(const char *challenge)
// plain auth - the most simple one
TPlainAuth::TPlainAuth(ThreadData *info, bool old) :
- TJabberAuth(info)
-{
- szName = "PLAIN";
- bOld = old;
-}
-
-TPlainAuth::~TPlainAuth()
+ TJabberAuth(info, "PLAIN"),
+ bOld(old)
{
+ priority = (old) ? 100 : 101;
}
char* TPlainAuth::getInitialRequest()
@@ -359,11 +356,9 @@ char* TPlainAuth::getInitialRequest()
/////////////////////////////////////////////////////////////////////////////////////////
// basic type
-TJabberAuth::TJabberAuth(ThreadData* pInfo) :
- bIsValid(true),
- complete(0),
- szName(nullptr),
- info(pInfo)
+TJabberAuth::TJabberAuth(ThreadData* pInfo, const char *pszMech) :
+ info(pInfo),
+ szName(mir_strdup(pszMech))
{
}
diff --git a/protocols/JabberG/src/jabber_secur.h b/protocols/JabberG/src/jabber_secur.h
index 78dccfa70a..14ad699b70 100644
--- a/protocols/JabberG/src/jabber_secur.h
+++ b/protocols/JabberG/src/jabber_secur.h
@@ -28,19 +28,24 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
// basic class - provides interface for various Jabber auth
-class TJabberAuth
+class TJabberAuth : public MZeroedObject
{
-protected: bool bIsValid;
- const char* szName;
+protected: bool bIsValid = true;
+ ptrA szName;
unsigned complete;
+ int priority;
ThreadData *info;
public:
- TJabberAuth(ThreadData*);
+ TJabberAuth(ThreadData *pInfo, const char *pszMech);
virtual ~TJabberAuth();
virtual char* getInitialRequest();
virtual char* getChallenge(const char *challenge);
- virtual bool validateLogin(const char *challenge);
+ virtual bool validateLogin(const char *challenge);
+
+ static int compare(const TJabberAuth *p1, const TJabberAuth *p2)
+ { return p2->priority - p1->priority; // reverse sorting order
+ }
inline const char* getName() const
{ return szName;
@@ -59,11 +64,10 @@ class TPlainAuth : public TJabberAuth
bool bOld;
+public:
+ TPlainAuth(ThreadData*, bool);
-public: TPlainAuth(ThreadData*, bool);
- virtual ~TPlainAuth();
-
- virtual char* getInitialRequest();
+ char* getInitialRequest() override;
};
// md5 auth - digest-based authorization
@@ -89,7 +93,7 @@ class TScramAuth : public TJabberAuth
const EVP_MD *hashMethod;
public:
- TScramAuth(ThreadData*, bool bSha1, void *pData = nullptr, size_t cbLen = 0);
+ TScramAuth(ThreadData *pInfo, const char *pszMech, const EVP_MD *pMethod, int priority);
~TScramAuth();
char* getInitialRequest() override;
@@ -106,10 +110,9 @@ class TNtlmAuth : public TJabberAuth
typedef TJabberAuth CSuper;
HANDLE hProvider;
- const char *szHostName;
public:
- TNtlmAuth(ThreadData*, const char* mechanism, const char *hostname = nullptr);
+ TNtlmAuth(ThreadData*, const char* mechanism);
~TNtlmAuth();
char* getInitialRequest() override;
diff --git a/protocols/JabberG/src/jabber_strm_mgmt.cpp b/protocols/JabberG/src/jabber_strm_mgmt.cpp
index 151de8203e..1fcd6e3ac3 100755
--- a/protocols/JabberG/src/jabber_strm_mgmt.cpp
+++ b/protocols/JabberG/src/jabber_strm_mgmt.cpp
@@ -268,8 +268,7 @@ bool strm_mgmt::IsResumeIdPresent()
void strm_mgmt::FinishLoginProcess(ThreadData *info)
{
-
- if (info->auth) { //We are already logged-in
+ if (proto->m_arAuthMechs.getCount()) { //We are already logged-in
info->send(
XmlNodeIq(proto->AddIQ(&CJabberProto::OnIqResultBind, JABBER_IQ_TYPE_SET))
<< XCHILDNS("bind", JABBER_FEAT_BIND)
@@ -281,6 +280,6 @@ void strm_mgmt::FinishLoginProcess(ThreadData *info)
return;
}
- //mechanisms not available and we are not logged in
+ // mechanisms not available and we are not logged in
proto->PerformIqAuth(info);
}
diff --git a/protocols/JabberG/src/jabber_thread.cpp b/protocols/JabberG/src/jabber_thread.cpp
index 586cbce6f9..6f734a68a6 100755
--- a/protocols/JabberG/src/jabber_thread.cpp
+++ b/protocols/JabberG/src/jabber_thread.cpp
@@ -585,93 +585,10 @@ void CJabberProto::OnProcessStreamOpening(const TiXmlElement *node, ThreadData *
void CJabberProto::PerformAuthentication(ThreadData *info)
{
- TJabberAuth* auth = nullptr;
- char* request = nullptr;
-
- if (info->auth) {
- delete info->auth;
- info->auth = nullptr;
- }
-
- if (m_isSpnegoAvailable) {
- m_isSpnegoAvailable = false;
- auth = new TNtlmAuth(info, "GSS-SPNEGO");
- if (!auth->isValid()) {
- delete auth;
- auth = nullptr;
- }
- }
-
- if (auth == nullptr && m_isKerberosAvailable) {
- m_isKerberosAvailable = false;
- auth = new TNtlmAuth(info, "GSSAPI", m_gssapiHostName);
- if (!auth->isValid()) {
- delete auth;
- auth = nullptr;
- }
- else {
- request = auth->getInitialRequest();
- if (!request) {
- delete auth;
- auth = nullptr;
- }
- }
- }
-
- if (auth == nullptr && m_isNtlmAvailable) {
- m_isNtlmAvailable = false;
- auth = new TNtlmAuth(info, "NTLM");
- if (!auth->isValid()) {
- delete auth;
- auth = nullptr;
- }
- }
-
- if (auth == nullptr && m_isScramSha256PlusAvailable) {
- m_isScramSha256PlusAvailable = false;
-
- int len = 0;
- void *pBuf = Netlib_GetTlsUnique(info->s, len);
- if (pBuf)
- auth = new TScramAuth(info, EVP_sha256(), pBuf, len);
- }
-
- if (auth == nullptr && m_isScramSha256Available) {
- m_isScramSha256Available = false;
- auth = new TScramAuth(info, EVP_sha256());
- }
-
- if (auth == nullptr && m_isScramSha1PlusAvailable) {
- m_isScramSha1PlusAvailable = false;
-
- int len = 0;
- void *pBuf = Netlib_GetTlsUnique(info->s, len);
- if (pBuf)
- auth = new TScramAuth(info, EVP_sha1(), pBuf, len);
- }
-
- if (auth == nullptr && m_isScramSha1Available) {
- m_isScramSha1Available = false;
- auth = new TScramAuth(info, EVP_sha1());
- }
-
- if (auth == nullptr && m_isMd5Available) {
- m_isMd5Available = false;
- auth = new TMD5Auth(info);
- }
-
- if (auth == nullptr && m_isPlainAvailable) {
- m_isPlainAvailable = false;
- auth = new TPlainAuth(info, false);
- }
-
- if (auth == nullptr && m_isPlainOldAvailable) {
- m_isPlainOldAvailable = false;
- auth = new TPlainAuth(info, true);
- }
-
- if (auth == nullptr) {
- if (m_isAuthAvailable) { // no known mechanisms but iq_auth is available
+ // no known mechanisms
+ if (m_arAuthMechs.getCount() == 0) {
+ // if iq_auth is available, use it
+ if (m_isAuthAvailable) {
m_isAuthAvailable = false;
PerformIqAuth(info);
return;
@@ -687,12 +604,8 @@ void CJabberProto::PerformAuthentication(ThreadData *info)
return;
}
- info->auth = auth;
-
- if (!request) request = auth->getInitialRequest();
- info->send(XmlNode("auth", request) << XATTR("xmlns", "urn:ietf:params:xml:ns:xmpp-sasl")
- << XATTR("mechanism", auth->getName()));
- mir_free(request);
+ auto &auth = m_arAuthMechs[0];
+ info->send(XmlNode("auth", ptrA(auth.getInitialRequest())) << XATTR("xmlns", "urn:ietf:params:xml:ns:xmpp-sasl") << XATTR("mechanism", auth.getName()));
}
/////////////////////////////////////////////////////////////////////////////////////////
@@ -725,37 +638,57 @@ void CJabberProto::OnProcessFeatures(const TiXmlElement *node, ThreadData *info)
}
if (!mir_strcmp(pszName, "mechanisms")) {
- m_dwAuthMechs = 0;
- replaceStr(m_gssapiHostName, nullptr);
+ m_arAuthMechs.destroy();
+ replaceStr(info->gssapiHostName, nullptr);
areMechanismsDefined = true;
for (auto *c : TiXmlEnum(n)) {
if (!mir_strcmp(c->Name(), "mechanism")) {
+ TJabberAuth *pAuth = nullptr;
const char *szMechanism = c->GetText();
- if (!mir_strcmp(szMechanism, "PLAIN"))
- m_isPlainOldAvailable = m_isPlainAvailable = true;
+ if (!mir_strcmp(szMechanism, "PLAIN")) {
+ m_arAuthMechs.insert(new TPlainAuth(info, false));
+ pAuth = new TPlainAuth(info, true);
+ }
else if (!mir_strcmp(szMechanism, "DIGEST-MD5"))
- m_isMd5Available = true;
+ pAuth = new TMD5Auth(info);
else if (!mir_strcmp(szMechanism, "SCRAM-SHA-1"))
- m_isScramSha1Available = true;
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha1(), 500);
else if (!mir_strcmp(szMechanism, "SCRAM-SHA-1-PLUS"))
- m_isScramSha1PlusAvailable = true;
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha1(), 501);
+ else if (!mir_strcmp(szMechanism, "SCRAM-SHA-224"))
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha224(), 510);
+ else if (!mir_strcmp(szMechanism, "SCRAM-SHA-224-PLUS"))
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha224(), 511);
else if (!mir_strcmp(szMechanism, "SCRAM-SHA-256"))
- m_isScramSha256Available = true;
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha256(), 520);
else if (!mir_strcmp(szMechanism, "SCRAM-SHA-256-PLUS"))
- m_isScramSha256PlusAvailable = true;
- else if (!mir_strcmp(szMechanism, "NTLM"))
- m_isNtlmAvailable = true;
- else if (!mir_strcmp(szMechanism, "GSS-SPNEGO"))
- m_isSpnegoAvailable = true;
- else if (!mir_strcmp(szMechanism, "GSSAPI"))
- m_isKerberosAvailable = true;
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha256(), 521);
+ else if (!mir_strcmp(szMechanism, "SCRAM-SHA-384"))
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha384(), 530);
+ else if (!mir_strcmp(szMechanism, "SCRAM-SHA-384-PLUS"))
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha384(), 531);
+ else if (!mir_strcmp(szMechanism, "SCRAM-SHA-512"))
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha512(), 540);
+ else if (!mir_strcmp(szMechanism, "SCRAM-SHA-512-PLUS"))
+ pAuth = new TScramAuth(info, szMechanism, EVP_sha512(), 541);
+ else if (!mir_strcmp(szMechanism, "NTLM") || !mir_strcmp(szMechanism, "GSS-SPNEGO") || !mir_strcmp(szMechanism, "GSSAPI"))
+ pAuth = new TNtlmAuth(info, szMechanism);
+ else {
+ debugLogA("Unsupported auth mechanism: %s, skipping", szMechanism);
+ continue;
+ }
+
+ if (!pAuth->isValid())
+ delete pAuth;
+ else
+ m_arAuthMechs.insert(pAuth);
}
else if (!mir_strcmp(c->Name(), "hostname")) {
const char *mech = XmlGetAttr(c, "mechanism");
if (mech && mir_strcmpi(mech, "GSSAPI") == 0)
- m_gssapiHostName = mir_strdup(c->GetText());
+ info->gssapiHostName = mir_strdup(c->GetText());
}
}
}
@@ -783,7 +716,7 @@ void CJabberProto::OnProcessFeatures(const TiXmlElement *node, ThreadData *info)
if (m_bEnableStreamMgmt && m_StrmMgmt.IsResumeIdPresent()) // resume should be done here
m_StrmMgmt.CheckState();
else {
- if (info->auth) { // we are already logged-in
+ if (m_arAuthMechs.getCount()) { // we are already logged-in
info->send(
XmlNodeIq(AddIQ(&CJabberProto::OnIqResultBind, JABBER_IQ_TYPE_SET))
<< XCHILDNS("bind", JABBER_FEAT_BIND)
@@ -801,8 +734,10 @@ void CJabberProto::OnProcessFailure(const TiXmlElement *node, ThreadData *info)
{
// failure xmlns=\"urn:ietf:params:xml:ns:xmpp-sasl\"
const char *type = XmlGetAttr(node, "xmlns");
- if (!mir_strcmp(type, "urn:ietf:params:xml:ns:xmpp-sasl"))
+ if (!mir_strcmp(type, "urn:ietf:params:xml:ns:xmpp-sasl")) {
+ m_arAuthMechs.remove(0L);
PerformAuthentication(info);
+ }
}
void CJabberProto::OnProcessFailed(const TiXmlElement *node, ThreadData *info) //used failed instead of failure, notes: https://xmpp.org/extensions/xep-0198.html#errors
@@ -810,14 +745,12 @@ void CJabberProto::OnProcessFailed(const TiXmlElement *node, ThreadData *info) /
m_StrmMgmt.OnProcessFailed(node, info);
}
-
void CJabberProto::OnProcessEnabled(const TiXmlElement *node, ThreadData * info)
{
if (m_bEnableStreamMgmt && !mir_strcmp(XmlGetAttr(node, "xmlns"), "urn:xmpp:sm:3"))
m_StrmMgmt.OnProcessEnabled(node, info);
}
-
void CJabberProto::OnProcessError(const TiXmlElement *node, ThreadData *info)
{
//failure xmlns=\"urn:ietf:params:xml:ns:xmpp-sasl\"
@@ -858,7 +791,7 @@ void CJabberProto::OnProcessSuccess(const TiXmlElement *node, ThreadData *info)
return;
if (!mir_strcmp(type, "urn:ietf:params:xml:ns:xmpp-sasl")) {
- if (!info->auth->validateLogin(node->GetText())) {
+ if (!m_arAuthMechs[0].validateLogin(node->GetText())) {
info->send("</stream:stream>");
return;
}
@@ -875,7 +808,7 @@ void CJabberProto::OnProcessSuccess(const TiXmlElement *node, ThreadData *info)
void CJabberProto::OnProcessChallenge(const TiXmlElement *node, ThreadData *info)
{
- if (info->auth == nullptr) {
+ if (m_arAuthMechs.getCount() == 0) {
debugLogA("No previous auth have been made, exiting...");
return;
}
@@ -883,7 +816,7 @@ void CJabberProto::OnProcessChallenge(const TiXmlElement *node, ThreadData *info
if (mir_strcmp(XmlGetAttr(node, "xmlns"), "urn:ietf:params:xml:ns:xmpp-sasl"))
return;
- char* challenge = info->auth->getChallenge(node->GetText());
+ char* challenge = m_arAuthMechs[0].getChallenge(node->GetText());
info->send(XmlNode("response", challenge) << XATTR("xmlns", "urn:ietf:params:xml:ns:xmpp-sasl"));
mir_free(challenge);
}
@@ -2005,8 +1938,7 @@ ThreadData::~ThreadData()
if (!bIsReg && proto->m_ThreadInfo == this)
proto->m_ThreadInfo = nullptr;
- delete auth;
-
+ mir_free(gssapiHostName);
mir_free(zRecvData);
mir_free(buffer);
diff --git a/protocols/JabberG/src/stdafx.h b/protocols/JabberG/src/stdafx.h
index 8b0f14ab70..dc11269456 100755
--- a/protocols/JabberG/src/stdafx.h
+++ b/protocols/JabberG/src/stdafx.h
@@ -376,7 +376,9 @@ struct ThreadData
char fullJID[JABBER_MAX_JID_LEN];
ptrA tszNewPassword;
- class TJabberAuth *auth;
+// class TJabberAuth *auth;
+ char *gssapiHostName;
+
JabberCapsBits jabberServerCaps;
void close(void);