Rearrange CAP requests between ZNC and server in a way

that each next REQ is sent only after receiving ACK/NAK
of previous REQ. Also now you can call CIRCSock::PauseCap()
and CIRCSock::ResumeCap() if you need to pause CAP negotiation
and process of logging in for a while.

git-svn-id: https://znc.svn.sourceforge.net/svnroot/znc/trunk@2137 726aef4b-f618-498e-8847-2d620e286838
This commit is contained in:
darthgandalf
2010-09-13 17:00:50 +00:00
parent 1d6f11f71a
commit 633c225811
2 changed files with 37 additions and 10 deletions
+25 -10
View File
@@ -24,6 +24,7 @@ CIRCSock::CIRCSock(CUser* pUser) : CZNCSock() {
m_Nick.SetHost(pUser->GetBindHost());
m_uMaxNickLen = 9;
m_uCapPaused = 0;
m_sPerms = "*!@%+";
m_sPermModes = "qaohv";
m_mueChanModes['b'] = ListArg;
@@ -679,15 +680,11 @@ void CIRCSock::ReadLine(const CString& sData) {
for (it = vsTokens.begin(); it != vsTokens.end(); ++it) {
if (OnServerCapAvailable(*it) || *it == "multi-prefix" || *it == "userhost-in-names") {
// For real support of ack (~) modifier need also
// to queue these cap requests.
PutIRC("CAP REQ :" + *it);
m_ssPendingCaps.insert(*it);
}
}
} else if (sSubCmd == "ACK") {
sArgs.Trim();
m_ssPendingCaps.erase(sArgs);
MODULECALL(OnServerCapResult(sArgs, true), m_pUser, NULL, );
if ("multi-prefix" == sArgs) {
m_bNamesx = true;
@@ -699,14 +696,10 @@ void CIRCSock::ReadLine(const CString& sData) {
// This should work because there's no [known]
// capability with length of name more than 100 characters.
sArgs.Trim();
m_ssPendingCaps.erase(sArgs);
MODULECALL(OnServerCapResult(sArgs, false), m_pUser, NULL, );
}
if (m_ssPendingCaps.empty()) {
// We already got all needed ACK/NAK replies.
PutIRC("CAP END");
}
SendNextCap();
}
// Don't forward any CAP stuff to the client
return;
@@ -716,6 +709,28 @@ void CIRCSock::ReadLine(const CString& sData) {
m_pUser->PutUser(sLine);
}
void CIRCSock::SendNextCap() {
if (!m_uCapPaused) {
if (m_ssPendingCaps.empty()) {
// We already got all needed ACK/NAK replies.
PutIRC("CAP END");
} else {
CString sCap = *m_ssPendingCaps.begin();
m_ssPendingCaps.erase(m_ssPendingCaps.begin());
PutIRC("CAP REQ :" + sCap);
}
}
}
void CIRCSock::PauseCap() {
++m_uCapPaused;
}
void CIRCSock::ResumeCap() {
--m_uCapPaused;
SendNextCap();
}
bool CIRCSock::OnServerCapAvailable(const CString& sCap) {
MODULECALL(OnServerCapAvailable(sCap), m_pUser, NULL, return true);
return false;