the game where you go into mines and start crafting! but for consoles (forked directly from smartcmd's github)
1#include "stdafx.h"
2#include "Options.h"
3#include "ServerConnection.h"
4#include "PendingConnection.h"
5#include "PlayerConnection.h"
6#include "ServerPlayer.h"
7#include "..\Minecraft.World\net.minecraft.network.h"
8#include "..\Minecraft.World\Socket.h"
9#include "..\Minecraft.World\net.minecraft.world.level.h"
10#include "MultiPlayerLevel.h"
11
12ServerConnection::ServerConnection(MinecraftServer *server)
13{
14 // 4J - added initialiser
15 connectionCounter = 0;
16 InitializeCriticalSection(&pending_cs);
17
18 this->server = server;
19}
20
21ServerConnection::~ServerConnection()
22{
23 DeleteCriticalSection(&pending_cs);
24}
25
26// 4J - added to handle incoming connections, to replace thread that original used to have
27void ServerConnection::NewIncomingSocket(Socket *socket)
28{
29 shared_ptr<PendingConnection> unconnectedClient = shared_ptr<PendingConnection>(new PendingConnection(server, socket, L"Connection #" + _toString<int>(connectionCounter++)));
30 handleConnection(unconnectedClient);
31}
32
33void ServerConnection::addPlayerConnection(shared_ptr<PlayerConnection> uc)
34{
35 players.push_back(uc);
36}
37
38void ServerConnection::handleConnection(shared_ptr<PendingConnection> uc)
39{
40 EnterCriticalSection(&pending_cs);
41 pending.push_back(uc);
42 LeaveCriticalSection(&pending_cs);
43}
44
45void ServerConnection::stop()
46{
47 EnterCriticalSection(&pending_cs);
48 for (unsigned int i = 0; i < pending.size(); i++)
49 {
50 shared_ptr<PendingConnection> uc = pending[i];
51 uc->connection->close(DisconnectPacket::eDisconnect_Closed);
52 }
53 LeaveCriticalSection(&pending_cs);
54
55 for (unsigned int i = 0; i < players.size(); i++)
56 {
57 shared_ptr<PlayerConnection> player = players[i];
58 player->connection->close(DisconnectPacket::eDisconnect_Closed);
59 }
60}
61
62void ServerConnection::tick()
63{
64 {
65 // MGH - changed this so that the the CS lock doesn't cover the tick (was causing a lockup when 2 players tried to join)
66 EnterCriticalSection(&pending_cs);
67 vector< shared_ptr<PendingConnection> > tempPending = pending;
68 LeaveCriticalSection(&pending_cs);
69
70 for (unsigned int i = 0; i < tempPending.size(); i++)
71 {
72 shared_ptr<PendingConnection> uc = tempPending[i];
73 // try { // 4J - removed try/catch
74 uc->tick();
75 // } catch (Exception e) {
76 // uc.disconnect("Internal server error");
77 // logger.log(Level.WARNING, "Failed to handle packet: " + e, e);
78 // }
79 if(uc->connection != NULL) uc->connection->flush();
80 }
81 }
82
83 // now remove from the pending list
84 EnterCriticalSection(&pending_cs);
85 for (unsigned int i = 0; i < pending.size(); i++)
86 if (pending[i]->done)
87 {
88 pending.erase(pending.begin()+i);
89 i--;
90 }
91 LeaveCriticalSection(&pending_cs);
92
93 for (unsigned int i = 0; i < players.size(); i++)
94 {
95 shared_ptr<PlayerConnection> player = players[i];
96 shared_ptr<ServerPlayer> serverPlayer = player->getPlayer();
97 if( serverPlayer )
98 {
99 serverPlayer->updateFrameTick();
100 serverPlayer->doChunkSendingTick(false);
101 }
102 player->tick();
103 if (player->done)
104 {
105 players.erase(players.begin()+i);
106 i--;
107 }
108 player->connection->flush();
109 }
110
111}
112
113bool ServerConnection::addPendingTextureRequest(const wstring &textureName)
114{
115 AUTO_VAR(it, find( m_pendingTextureRequests.begin(), m_pendingTextureRequests.end(), textureName));
116 if( it == m_pendingTextureRequests.end() )
117 {
118 m_pendingTextureRequests.push_back(textureName);
119 return true;
120 }
121
122 // 4J Stu - We want to request this texture from everyone, if we have a duplicate it's most likely because the first person we asked for it didn't have it
123 // eg They selected a skin then deleted the skin pack. The side effect of this change is that in certain cases we can send a few more requests, and receive
124 // a few more responses if people join with the same skin in a short space of time
125 return true;
126}
127
128void ServerConnection::handleTextureReceived(const wstring &textureName)
129{
130 AUTO_VAR(it, find( m_pendingTextureRequests.begin(), m_pendingTextureRequests.end(), textureName));
131 if( it != m_pendingTextureRequests.end() )
132 {
133 m_pendingTextureRequests.erase(it);
134 }
135 for (unsigned int i = 0; i < players.size(); i++)
136 {
137 shared_ptr<PlayerConnection> player = players[i];
138 if (!player->done)
139 {
140 player->handleTextureReceived(textureName);
141 }
142 }
143}
144
145void ServerConnection::handleTextureAndGeometryReceived(const wstring &textureName)
146{
147 AUTO_VAR(it, find( m_pendingTextureRequests.begin(), m_pendingTextureRequests.end(), textureName));
148 if( it != m_pendingTextureRequests.end() )
149 {
150 m_pendingTextureRequests.erase(it);
151 }
152 for (unsigned int i = 0; i < players.size(); i++)
153 {
154 shared_ptr<PlayerConnection> player = players[i];
155 if (!player->done)
156 {
157 player->handleTextureAndGeometryReceived(textureName);
158 }
159 }
160}
161
162void ServerConnection::handleServerSettingsChanged(shared_ptr<ServerSettingsChangedPacket> packet)
163{
164 Minecraft *pMinecraft = Minecraft::GetInstance();
165
166 if(packet->action==ServerSettingsChangedPacket::HOST_DIFFICULTY)
167 {
168 for(unsigned int i = 0; i < pMinecraft->levels.length; ++i)
169 {
170 if( pMinecraft->levels[i] != NULL )
171 {
172 app.DebugPrintf("ClientConnection::handleServerSettingsChanged - Difficulty = %d",packet->data);
173 pMinecraft->levels[i]->difficulty = packet->data;
174 }
175 }
176 }
177// else if(packet->action==ServerSettingsChangedPacket::HOST_IN_GAME_SETTINGS)// options
178// {
179// app.SetGameHostOption(eGameHostOption_All,packet->m_serverSettings)
180// }
181// else
182// {
183// unsigned char ucData=(unsigned char)packet->data;
184// if(ucData&1)
185// {
186// // hide gamertags
187// pMinecraft->options->SetGamertagSetting(true);
188// }
189// else
190// {
191// pMinecraft->options->SetGamertagSetting(false);
192// }
193//
194// for (unsigned int i = 0; i < players.size(); i++)
195// {
196// shared_ptr<PlayerConnection> playerconnection = players[i];
197// playerconnection->setShowOnMaps(pMinecraft->options->GetGamertagSetting());
198// }
199// }
200}
201
202vector< shared_ptr<PlayerConnection> > * ServerConnection::getPlayers()
203{
204 return &players;
205}