+#include "inspircd.h"
+#include "xline.h"
+#include "main.h"
+#include "modules/spanningtree.h"
+
+#include "utils.h"
+#include "treeserver.h"
+
+/** We use this constructor only to create the 'root' item, Utils->TreeRoot, which
+ * represents our own server. Therefore, it has no route, no parent, and
+ * no socket associated with it. Its version string is our own local version.
+ */
+TreeServer::TreeServer()
+ : Server(ServerInstance->Config->ServerName)
+ , Parent(NULL), Route(NULL), ServerDesc(ServerInstance->Config->ServerDesc)
+ , VersionString(ServerInstance->GetVersionString()), Socket(NULL), sid(ServerInstance->Config->GetSID()), ServerUser(ServerInstance->FakeClient)
+ , age(ServerInstance->Time()), Warned(false), bursting(false), UserCount(0), OperCount(0), rtt(0), StartBurst(0), Hidden(false)
+{
+ AddHashEntry();
+}
+
+/** When we create a new server, we call this constructor to initialize it.
+ * This constructor initializes the server's Route and Parent, and sets up
+ * its ping counters so that it will be pinged one minute from now.
+ */
+TreeServer::TreeServer(const std::string& Name, const std::string& Desc, const std::string& id, TreeServer* Above, TreeSocket* Sock, bool Hide)
+ : Server(Name)
+ , Parent(Above), ServerDesc(Desc), Socket(Sock), sid(id), ServerUser(new FakeUser(id, this))
+ , age(ServerInstance->Time()), Warned(false), bursting(true), UserCount(0), OperCount(0), rtt(0), Hidden(Hide)
+{
+ CheckULine();
+ SetNextPingTime(ServerInstance->Time() + Utils->PingFreq);
+ SetPingFlag();
+
+ long ts = ServerInstance->Time() * 1000 + (ServerInstance->Time_ns() / 1000000);
+ this->StartBurst = ts;
+ ServerInstance->Logs->Log(MODNAME, LOG_DEBUG, "Server %s started bursting at time %lu", sid.c_str(), ts);
+
+ /* find the 'route' for this server (e.g. the one directly connected
+ * to the local server, which we can use to reach it)
+ *
+ * In the following example, consider we have just added a TreeServer
+ * class for server G on our network, of which we are server A.
+ * To route traffic to G (marked with a *) we must send the data to
+ * B (marked with a +) so this algorithm initializes the 'Route'
+ * value to point at whichever server traffic must be routed through
+ * to get here. If we were to try this algorithm with server B,
+ * the Route pointer would point at its own object ('this').
+ *
+ * A
+ * / \
+ * + B C
+ * / \ \
+ * D E F
+ * / \
+ * * G H
+ *
+ * We only run this algorithm when a server is created, as
+ * the routes remain constant while ever the server exists, and
+ * do not need to be re-calculated.