|
|
|
@@ -62,11 +62,13 @@ command_result ConnectedClient::handleCommandClientKick(Command &cmd) {
|
|
|
|
|
CMD_REQ_SERVER;
|
|
|
|
|
CMD_CHK_AND_INC_FLOOD_POINTS(25);
|
|
|
|
|
|
|
|
|
|
command_result_bulk result{};
|
|
|
|
|
result.reserve(cmd.bulkCount());
|
|
|
|
|
|
|
|
|
|
std::vector<ConnectedLockedClient<ConnectedClient>> clients{};
|
|
|
|
|
clients.reserve(cmd.bulkCount());
|
|
|
|
|
|
|
|
|
|
auto type = cmd["reasonid"].as<ViewReasonId>();
|
|
|
|
|
auto single_client = cmd.bulkCount() == 1;
|
|
|
|
|
auto target_channel = type == ViewReasonId::VREASON_CHANNEL_KICK ? this->server->channelTree->getDefaultChannel() : nullptr;
|
|
|
|
|
auto kick_power = type == ViewReasonId::VREASON_CHANNEL_KICK ?
|
|
|
|
|
this->calculate_permission(permission::i_client_kick_from_channel_power, target_channel->channelId()) :
|
|
|
|
@@ -76,31 +78,28 @@ command_result ConnectedClient::handleCommandClientKick(Command &cmd) {
|
|
|
|
|
ConnectedLockedClient<ConnectedClient> client{this->server->find_client_by_id(cmd[index]["clid"].as<ClientId>())};
|
|
|
|
|
|
|
|
|
|
if (!client) {
|
|
|
|
|
if(single_client)
|
|
|
|
|
return command_result{error::client_invalid_id};
|
|
|
|
|
result.emplace_result(error::client_invalid_id);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
if (client->getType() == CLIENT_MUSIC) {
|
|
|
|
|
if(single_client)
|
|
|
|
|
return command_result{error::client_invalid_type};
|
|
|
|
|
result.emplace_result(error::client_invalid_type);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if(type == ViewReasonId::VREASON_CHANNEL_KICK) {
|
|
|
|
|
if(!permission::v2::permission_granted(client->calculate_permission(permission::i_client_needed_kick_from_channel_power, client->getChannelId()), kick_power)) {
|
|
|
|
|
if(single_client)
|
|
|
|
|
return command_result{permission::i_client_needed_kick_from_channel_power};
|
|
|
|
|
result.emplace_result(permission::i_client_needed_kick_from_channel_power);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
if(!permission::v2::permission_granted(client->calculate_permission(permission::i_client_needed_kick_from_server_power, client->getChannelId()), kick_power)) {
|
|
|
|
|
if(single_client)
|
|
|
|
|
return command_result{permission::i_client_needed_kick_from_server_power};
|
|
|
|
|
result.emplace_result(permission::i_client_needed_kick_from_server_power);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
clients.emplace_back(std::move(client));
|
|
|
|
|
result.emplace_result(error::ok);
|
|
|
|
|
}
|
|
|
|
|
if (clients.empty())
|
|
|
|
|
return command_result{error::database_empty_result};
|
|
|
|
@@ -114,7 +113,7 @@ command_result ConnectedClient::handleCommandClientKick(Command &cmd) {
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return command_result{error::ok};
|
|
|
|
|
return command_result{std::forward<command_result_bulk>(result)};
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
command_result ConnectedClient::handleCommandClientGetIds(Command &cmd) {
|
|
|
|
@@ -177,37 +176,35 @@ command_result ConnectedClient::handleCommandClientMove(Command &cmd) {
|
|
|
|
|
auto permission_error = this->calculate_and_get_join_state(channel);
|
|
|
|
|
if(permission_error != permission::unknown) return command_result{permission_error};
|
|
|
|
|
|
|
|
|
|
command_result_bulk result{};
|
|
|
|
|
result.reserve(cmd.bulkCount());
|
|
|
|
|
|
|
|
|
|
std::vector<ConnectedLockedClient<ConnectedClient>> clients{};
|
|
|
|
|
auto is_single_client = cmd.bulkCount() == 1;
|
|
|
|
|
|
|
|
|
|
for(size_t index{0}; index < cmd.bulkCount(); index++) {
|
|
|
|
|
auto target_client_id = cmd[index]["clid"].as<ClientId>();
|
|
|
|
|
ConnectedLockedClient target_client{target_client_id == 0 ? this->ref() : this->server->find_client_by_id(target_client_id)};
|
|
|
|
|
if(!target_client) {
|
|
|
|
|
if(is_single_client)
|
|
|
|
|
return command_result{error::client_invalid_id};
|
|
|
|
|
result.emplace_result(error::client_invalid_id);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if(!target_client->getChannel()) {
|
|
|
|
|
if(target_client.client != this) {
|
|
|
|
|
if(is_single_client)
|
|
|
|
|
return command_result{error::client_invalid_id};
|
|
|
|
|
result.emplace_result(error::client_invalid_id);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if(target_client.client != this) {
|
|
|
|
|
if(!permission::v2::permission_granted(target_client->calculate_permission(permission::i_client_needed_move_power, 0), this->calculate_permission(permission::i_client_move_power, 0))) {
|
|
|
|
|
if(is_single_client)
|
|
|
|
|
return command_result{permission::i_client_move_power};
|
|
|
|
|
result.emplace_result(permission::i_client_move_power);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
clients.emplace_back(std::move(target_client));
|
|
|
|
|
result.emplace_result(permission::ok);
|
|
|
|
|
}
|
|
|
|
|
if(clients.empty())
|
|
|
|
|
return command_result{error::database_empty_result};
|
|
|
|
|
|
|
|
|
|
if (!channel->properties()[property::CHANNEL_FLAG_MAXCLIENTS_UNLIMITED].as<bool>() || !channel->properties()[property::CHANNEL_FLAG_MAXFAMILYCLIENTS_UNLIMITED].as<bool>()) {
|
|
|
|
|
if(!permission::v2::permission_granted(1, this->calculate_permission(permission::b_channel_join_ignore_maxclients, channel->channelId()))) {
|
|
|
|
@@ -257,7 +254,7 @@ command_result ConnectedClient::handleCommandClientMove(Command &cmd) {
|
|
|
|
|
channels.push_back(oldChannel);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
for(auto oldChannel : channels) {
|
|
|
|
|
for(const auto& oldChannel : channels) {
|
|
|
|
|
if(!server_channel_w_lock.owns_lock())
|
|
|
|
|
server_channel_w_lock.lock();
|
|
|
|
|
if(oldChannel->channelType() == ChannelType::temporary && oldChannel->properties()[property::CHANNEL_DELETE_DELAY].as<int64_t>() == 0)
|
|
|
|
@@ -266,7 +263,7 @@ command_result ConnectedClient::handleCommandClientMove(Command &cmd) {
|
|
|
|
|
if(server_channel_w_lock.owns_lock())
|
|
|
|
|
server_channel_w_lock.unlock();
|
|
|
|
|
}
|
|
|
|
|
return command_result{error::ok};
|
|
|
|
|
return command_result{std::forward<command_result_bulk>(result)};
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
command_result ConnectedClient::handleCommandClientPoke(Command &cmd) {
|
|
|
|
@@ -274,42 +271,45 @@ command_result ConnectedClient::handleCommandClientPoke(Command &cmd) {
|
|
|
|
|
CMD_RESET_IDLE;
|
|
|
|
|
CMD_CHK_AND_INC_FLOOD_POINTS(25);
|
|
|
|
|
|
|
|
|
|
command_result_bulk result{};
|
|
|
|
|
result.reserve(cmd.bulkCount());
|
|
|
|
|
|
|
|
|
|
std::vector<ConnectedLockedClient<ConnectedClient>> clients{};
|
|
|
|
|
clients.reserve(cmd.bulkCount());
|
|
|
|
|
|
|
|
|
|
bool is_single_poke = cmd.bulkCount() == 1;
|
|
|
|
|
for(size_t index{0}; index < cmd.bulkCount(); index++) {
|
|
|
|
|
ConnectedLockedClient client{ this->server->find_client_by_id(cmd["clid"].as<ClientId>())};
|
|
|
|
|
ConnectedLockedClient client{ this->server->find_client_by_id(cmd[index]["clid"].as<ClientId>())};
|
|
|
|
|
if (!client) {
|
|
|
|
|
if(is_single_poke)
|
|
|
|
|
return command_result{error::client_invalid_id};
|
|
|
|
|
result.emplace_result(error::client_invalid_id);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
if (client->getType() == CLIENT_MUSIC) {
|
|
|
|
|
if(is_single_poke)
|
|
|
|
|
return command_result{error::client_invalid_type};
|
|
|
|
|
result.emplace_result(error::client_invalid_type);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
auto own_permission = this->calculate_permission(permission::i_client_poke_power, client->getChannelId());
|
|
|
|
|
if(!permission::v2::permission_granted(client->calculate_permission(permission::i_client_needed_poke_power, client->getChannelId()), own_permission)) {
|
|
|
|
|
if(is_single_poke)
|
|
|
|
|
return command_result{permission::i_client_poke_power};
|
|
|
|
|
result.emplace_result(permission::i_client_poke_power);
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
clients.push_back(std::move(client));
|
|
|
|
|
result.emplace_result(error::ok);
|
|
|
|
|
}
|
|
|
|
|
if(clients.empty())
|
|
|
|
|
return command_result{error::database_empty_result};
|
|
|
|
|
else if(clients.size() > 1) {
|
|
|
|
|
|
|
|
|
|
/* clients might be empty ;) */
|
|
|
|
|
|
|
|
|
|
if(clients.size() > 1) {
|
|
|
|
|
auto max_clients = this->calculate_permission(permission::i_client_poke_max_clients, 0);
|
|
|
|
|
if(!permission::v2::permission_granted(clients.size(), max_clients))
|
|
|
|
|
return command_result{permission::i_client_poke_max_clients};
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
for(auto& client : clients)
|
|
|
|
|
client->notifyClientPoke(_this.lock(), cmd["msg"]);
|
|
|
|
|
return command_result{error::ok};
|
|
|
|
|
|
|
|
|
|
return command_result{std::forward<command_result_bulk>(result)};
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|