diff --git a/include/protocol.h b/include/protocol.h index 5ffbdf7c9..4dc9b7525 100644 --- a/include/protocol.h +++ b/include/protocol.h @@ -131,11 +131,15 @@ public: /* The maximum length of a username. */ size_t MaxUser = 0; - /* Retrieves the next free UID or SID */ virtual Anope::string UID_Retrieve(); virtual Anope::string SID_Retrieve(); + /** Retrieves advice on what might be the problem when a link fails. + * @param advice The location to store the advice. + */ + virtual void GetLinkAdvice(std::vector &advice) { } + /** Extracts a timestamp from a string. */ virtual time_t ExtractTimestamp(const Anope::string &str); diff --git a/modules/protocol/inspircd.cpp b/modules/protocol/inspircd.cpp index 22e89c58e..b1b168401 100644 --- a/modules/protocol/inspircd.cpp +++ b/modules/protocol/inspircd.cpp @@ -192,6 +192,11 @@ public: MaxLine = 0; } + void GetLinkAdvice(std::vector &advice) override + { + advice.push_back("You do not have the account, hidechans, services, and spanningtree modules loaded on InspIRCd."); + } + size_t GetMaxListFor(Channel *c, ChannelMode *cm) override { ListLimits *limits = maxlist.Get(c); diff --git a/src/messages.cpp b/src/messages.cpp index 5668bcc38..d13ed5104 100644 --- a/src/messages.cpp +++ b/src/messages.cpp @@ -46,9 +46,9 @@ void Capab::Run(MessageSource &source, const std::vector ¶ms, void Error::Run(MessageSource &source, const std::vector ¶ms, const Anope::map &tags) { - Log(LOG_TERMINAL) << "ERROR: " << params[0]; - Anope::QuitReason = "Received ERROR from uplink: " + params[0]; + Anope::QuitReason = "Received an error from the uplink: " + params.back(); Anope::Quitting = true; + Log(LOG_TERMINAL) << Anope::QuitReason; } Ignore::Ignore(Module *creator, const Anope::string &mname) diff --git a/src/uplink.cpp b/src/uplink.cpp index c8bfc0b3b..f0873f73b 100644 --- a/src/uplink.cpp +++ b/src/uplink.cpp @@ -114,11 +114,20 @@ UplinkSocket::~UplinkSocket() if (!error && !Anope::Quitting) { this->OnError(""); - Module *protocol = ModuleManager::FindFirstOf(PROTOCOL); - if (protocol && !protocol->name.find("inspircd")) - Log(LOG_TERMINAL) << "Check that you have loaded m_spanningtree.so on InspIRCd, and are not connecting Anope to an SSL enabled port without configuring SSL in Anope (or vice versa)"; - else - Log(LOG_TERMINAL) << "Check that you are not connecting Anope to an SSL enabled port without configuring SSL in Anope (or vice versa)"; + + std::vector advice = { + "You are connecting Anope to an SSL-only port without configuring SSL (or vice versa).", + }; + if (IRCD) + { + advice.push_back(Anope::Format("You are using the wrong protocol module (currently %s for %s).", + IRCD->owner->name.c_str(), IRCD->GetProtocolName().c_str())); + IRCD->GetLinkAdvice(advice); + } + + Log(LOG_TERMINAL) << "Potential causes include:"; + for (const auto &line : advice) + Log(LOG_TERMINAL) << "* " << line; } if (IRCD && Servers::GetUplink() && Servers::GetUplink()->IsSynced())