Exemplo n.º 1
0
void Doors::HandleClick(Client* sender, uint8 trigger)
{
	//door debugging info dump
	Log.Out(Logs::Detail, Logs::Doors, "%s clicked door %s (dbid %d, eqid %d) at %s", sender->GetName(), door_name, db_id, door_id, to_string(m_Position).c_str());
	Log.Out(Logs::Detail, Logs::Doors, "  incline %d, opentype %d, lockpick %d, key %d, nokeyring %d, trigger %d type %d, param %d", incline, opentype, lockpick, keyitem, nokeyring, trigger_door, trigger_type, door_param);
	Log.Out(Logs::Detail, Logs::Doors, "  size %d, invert %d, dest: %s %s", size, invert_state, dest_zone, to_string(m_Destination).c_str());

	EQApplicationPacket* outapp = new EQApplicationPacket(OP_MoveDoor, sizeof(MoveDoor_Struct));
	MoveDoor_Struct* md = (MoveDoor_Struct*)outapp->pBuffer;
	md->doorid = door_id;
	/////////////////////////////////////////////////////////////////
	//used_pawn: Locked doors! Rogue friendly too =)
	//TODO: add check for other lockpick items
	//////////////////////////////////////////////////////////////////

	//TODO: ADVENTURE DOOR
	if(IsLDoNDoor())
	{
		if(sender)
		{
			if(RuleI(Adventure, ItemIDToEnablePorts) != 0)
			{
				if(!sender->KeyRingCheck(RuleI(Adventure, ItemIDToEnablePorts)))
				{
					if (sender->GetInv().HasItem(RuleI(Adventure, ItemIDToEnablePorts)) == INVALID_INDEX)
					{
						sender->Message_StringID(13, DUNGEON_SEALED);
						safe_delete(outapp);
						return;
					}
					else
					{
						sender->KeyRingAdd(RuleI(Adventure, ItemIDToEnablePorts));
					}
				}
			}

			if(!sender->GetPendingAdventureDoorClick())
			{
				sender->PendingAdventureDoorClick();
				ServerPacket *pack = new ServerPacket(ServerOP_AdventureClickDoor, sizeof(ServerPlayerClickedAdventureDoor_Struct));
				ServerPlayerClickedAdventureDoor_Struct *ads = (ServerPlayerClickedAdventureDoor_Struct*)pack->pBuffer;
				strcpy(ads->player, sender->GetName());
				ads->zone_id = zone->GetZoneID();
				ads->id = GetDoorDBID();
				worldserver.SendPacket(pack);
				safe_delete(pack);
				safe_delete(outapp);
			}
			return;
		}
	}

	uint32 keyneeded = GetKeyItem();
	uint8 keepoffkeyring = GetNoKeyring();
	uint32 haskey = 0;
	uint32 playerkey = 0;
	const ItemInst *lockpicks = sender->GetInv().GetItem(MainCursor);

	haskey = sender->GetInv().HasItem(keyneeded, 1);

	if (haskey != INVALID_INDEX)
	{
		playerkey = keyneeded;
	}

	if(GetTriggerType() == 255)
	{ // this object isnt triggered
		if(trigger == 1)
		{ // this door is only triggered by an object
			if(!IsDoorOpen() || (opentype == 58))
			{
				md->action = invert_state == 0 ? OPEN_DOOR : OPEN_INVDOOR;
			}
			else
			{
				md->action = invert_state == 0 ? CLOSE_DOOR : CLOSE_INVDOOR;
			}
		}
		else
		{
			safe_delete(outapp);
			return;
		}
	}

	// guild doors
	if(((keyneeded == 0) && (GetLockpick() == 0) && (guild_id == 0)) ||
		(IsDoorOpen() && (opentype == 58)) ||
		((guild_id > 0) && (guild_id == sender->GuildID())))
	{	//door not locked
		if(!IsDoorOpen() || (opentype == 58))
		{
			md->action = invert_state == 0 ? OPEN_DOOR : OPEN_INVDOOR;
		}
		else
		{
			md->action = invert_state == 0 ? CLOSE_DOOR : CLOSE_INVDOOR;
		}
	}
	else
	{	// guild doors
		if((guild_id > 0) && !sender->GetGM())
		{
			std::string tmp;
			char tmpmsg[240]; // guild doors msgs
			if(guild_mgr.GetGuildNameByID(guild_id, tmp))
			{
				sprintf(tmpmsg, "Only members of the <%s> guild may enter here", tmp.c_str());
			}
			else
			{
				strcpy(tmpmsg, "Door is locked by an unknown guild");
			}
			sender->Message(4, tmpmsg);
			safe_delete(outapp);
			return;
		}
		// a key is required or the door is locked but can be picked or both
		sender->Message(4, "This is locked...");		// debug spam - should probably go
		if(sender->GetGM())		// GM can always open locks - should probably be changed to require a key
		{
			sender->Message_StringID(4,DOORS_GM);
			if(!IsDoorOpen() || (opentype == 58))
			{
				md->action = invert_state == 0 ? OPEN_DOOR : OPEN_INVDOOR;
			}
			else
			{
				md->action = invert_state == 0 ? CLOSE_DOOR : CLOSE_INVDOOR;
			}
		}
		else if(playerkey)
		{	// they have something they are trying to open it with
			if(keyneeded && (keyneeded == playerkey))
			{	// key required and client is using the right key
				if(!keepoffkeyring)
				{
					sender->KeyRingAdd(playerkey);
				}
				sender->Message(4, "You got it open!");
				if(!IsDoorOpen() || (opentype == 58))
				{
					md->action = invert_state == 0 ? OPEN_DOOR : OPEN_INVDOOR;
				}
				else
				{
					md->action = invert_state == 0 ? CLOSE_DOOR : CLOSE_INVDOOR;
				}
			}
		}
		else if(lockpicks != nullptr)
		{
			if(sender->GetSkill(SkillPickLock))
			{
				if(lockpicks->GetItem()->ItemType == ItemTypeLockPick)
				{
					float modskill=sender->GetSkill(SkillPickLock);
					sender->CheckIncreaseSkill(SkillPickLock, nullptr, 1);

					Log.Out(Logs::General, Logs::Skills, "Client has lockpicks: skill=%f", modskill);

					if(GetLockpick() <= modskill)
					{
						if(!IsDoorOpen())
						{
							md->action = invert_state == 0 ? OPEN_DOOR : OPEN_INVDOOR;
						}
						else
						{
							md->action = invert_state == 0 ? CLOSE_DOOR : CLOSE_INVDOOR;
						}
						sender->Message_StringID(4, DOORS_SUCCESSFUL_PICK);
					}
					else
					{
						sender->Message_StringID(4, DOORS_INSUFFICIENT_SKILL);
						safe_delete(outapp);
						return;
					}
				}
				else
				{
					sender->Message_StringID(4, DOORS_NO_PICK);
					safe_delete(outapp);
					return;
				}
			}
			else
			{
				sender->Message_StringID(4, DOORS_CANT_PICK);
				safe_delete(outapp);
				return;
			}
		}
		else
		{	// locked door and nothing to open it with
			// search for key on keyring
			if(sender->KeyRingCheck(keyneeded))
			{
				playerkey = keyneeded;
				sender->Message(4, "You got it open!"); // more debug spam
				if(!IsDoorOpen() || (opentype == 58))
				{
					md->action = invert_state == 0 ? OPEN_DOOR : OPEN_INVDOOR;
				}
				else
				{
					md->action = invert_state == 0 ? CLOSE_DOOR : CLOSE_INVDOOR;
				}
			}
			else
			{
				sender->Message_StringID(4, DOORS_LOCKED);
				safe_delete(outapp);
				return;
			}
		}
	}

	entity_list.QueueClients(sender, outapp, false);
	if(!IsDoorOpen() || (opentype == 58))
	{
		close_timer.Start();
		SetOpenState(true);
	}
	else
	{
		close_timer.Disable();
		SetOpenState(false);
	}

	//everything past this point assumes we opened the door
	//and met all the reqs for opening
	//everything to do with closed doors has already been taken care of
	//we return because we don't want people using teleports on an unlocked door (exploit!)
	if((md->action == CLOSE_DOOR && invert_state == 0) || (md->action == CLOSE_INVDOOR && invert_state == 1))
	{
		safe_delete(outapp);
		return;
	}

	safe_delete(outapp);

	if((GetTriggerDoorID() != 0) && (GetTriggerType() == 1))
	{
		Doors* triggerdoor = entity_list.FindDoor(GetTriggerDoorID());
		if(triggerdoor && !triggerdoor->triggered)
		{
			triggered=true;
			triggerdoor->HandleClick(sender, 1);
		}
		else
		{
			triggered=false;
		}
	}
	else if((GetTriggerDoorID() != 0) && (GetTriggerType() != 1))
	{
		Doors* triggerdoor = entity_list.FindDoor(GetTriggerDoorID());
		if(triggerdoor && !triggerdoor->triggered)
		{
			triggered=true;
			triggerdoor->HandleClick(sender, 0);
		}
		else
		{
			triggered=false;
		}
	}

	if(((opentype == 57) || (opentype == 58)) && (strncmp(dest_zone, "NONE", strlen("NONE")) != 0))
	{ // Teleport door!
		if (( strncmp(dest_zone,zone_name,strlen(zone_name)) == 0) && (!keyneeded))
		{
			if(!keepoffkeyring)
			{
				sender->KeyRingAdd(playerkey);
			}
			sender->MovePC(zone->GetZoneID(), zone->GetInstanceID(), m_Destination.x, m_Destination.y, m_Destination.z, m_Destination.w);
		}
		else if (( !IsDoorOpen() || opentype == 58 ) && (keyneeded && ((keyneeded == playerkey) || sender->GetGM())))
		{
			if(!keepoffkeyring)
			{
				sender->KeyRingAdd(playerkey);
			}
			if(database.GetZoneID(dest_zone) == zone->GetZoneID())
			{
				sender->MovePC(zone->GetZoneID(), zone->GetInstanceID(), m_Destination.x, m_Destination.y, m_Destination.z, m_Destination.w);
			}
			else
			{
				sender->MovePC(database.GetZoneID(dest_zone), dest_instance_id, m_Destination.x, m_Destination.y, m_Destination.z, m_Destination.w);
			}
		}
		if (( !IsDoorOpen() || opentype == 58 ) && (!keyneeded))
		{
			if(database.GetZoneID(dest_zone) == zone->GetZoneID())
			{
				sender->MovePC(zone->GetZoneID(), zone->GetInstanceID(), m_Destination.x, m_Destination.y, m_Destination.z, m_Destination.w);
			}
			else
			{
				sender->MovePC(database.GetZoneID(dest_zone), dest_instance_id, m_Destination.x, m_Destination.y, m_Destination.z, m_Destination.w);
			}
		}
	}
}
Exemplo n.º 2
0
void SpawnConditionManager::ToggleEvent(uint32 event_id, bool enabled, bool strict, bool reset_base) {

	Log(Logs::Detail, Logs::Spawns, "Request to %s spawn event %d %sresetting trigger time", enabled?"enable":"disable", event_id, reset_base?"":"without ");

	//first look for the event in our local event list
	std::vector<SpawnEvent>::iterator cur,end;
	cur = spawn_events.begin();
	end = spawn_events.end();
	for(; cur != end; ++cur) {
		SpawnEvent &cevent = *cur;

		if(cevent.id == event_id) {
			//make sure were actually changing something
			if(cevent.enabled != enabled || reset_base || cevent.strict != strict) {
				cevent.enabled = enabled;
				cevent.strict = strict;
				if(reset_base) {
					Log(Logs::Detail, Logs::Spawns, "Spawn event %d located in this zone. State set. Trigger time reset (period %d).", event_id, cevent.period);
					//start with the time now
					zone->zone_time.GetCurrentEQTimeOfDay(&cevent.next);
					//advance the next time by our period
					EQTime::AddMinutes(cevent.period, &cevent.next);
				} else {
					Log(Logs::Detail, Logs::Spawns, "Spawn event %d located in this zone. State changed.", event_id);
				}

				//save the event in the DB
				UpdateDBEvent(cevent);

				//sync up our nearest event
				FindNearestEvent();
			} else {
				Log(Logs::Detail, Logs::Spawns, "Spawn event %d located in this zone but no change was needed.", event_id);
			}
			//even if we dont change anything, we still found it
			return;
		}
	}

	//if we get here, the condition must be in another zone.
	//first figure out what zone it applies to.
	//update the DB and send and send an update packet to
	//the zone if its up

	//we need to load the event from the DB and then update
	//the values in the DB, because we do not know if the zone
	//is up or not. The message to the zone will just tell it to
	//update its in-memory event list
	SpawnEvent e;
	std::string zone_short_name;
	if(!LoadDBEvent(event_id, e, zone_short_name)) {
		Log(Logs::Detail, Logs::Spawns, "Unable to find spawn event %d in the database.", event_id);
		//unable to find the event in the database...
		return;
	}
	if(e.enabled == enabled && !reset_base) {
		Log(Logs::Detail, Logs::Spawns, "Spawn event %d is not located in this zone but no change was needed.", event_id);
		return;	//no changes.
	}

	e.enabled = enabled;
	if(reset_base) {
		Log(Logs::Detail, Logs::Spawns, "Spawn event %d is in zone %s. State set. Trigger time reset (period %d). Notifying world.", event_id, zone_short_name.c_str(), e.period);
		//start with the time now
		zone->zone_time.GetCurrentEQTimeOfDay(&e.next);
		//advance the next time by our period
		EQTime::AddMinutes(e.period, &e.next);
	} else {
		Log(Logs::Detail, Logs::Spawns, "Spawn event %d is in zone %s. State changed. Notifying world.", event_id, zone_short_name.c_str(), e.period);
	}
	//save the event in the DB
	UpdateDBEvent(e);


	//now notify the zone
	auto pack = new ServerPacket(ServerOP_SpawnEvent, sizeof(ServerSpawnEvent_Struct));
	ServerSpawnEvent_Struct* sse = (ServerSpawnEvent_Struct*)pack->pBuffer;

	sse->zoneID = database.GetZoneID(zone_short_name.c_str());
	sse->event_id = event_id;

	worldserver.SendPacket(pack);
	safe_delete(pack);
}
Exemplo n.º 3
0
bool Corpse::Process() {
	if (player_corpse_depop)
		return false;

	if (corpse_delay_timer.Check()) {
		for (int i = 0; i < MAX_LOOTERS; i++)
			allowed_looters[i] = 0;
		corpse_delay_timer.Disable();
		return true;
	}

	if (corpse_graveyard_timer.Check()) {
		if (zone->HasGraveyard()) {
			Save();
			player_corpse_depop = true;
			database.SendCharacterCorpseToGraveyard(corpse_db_id, zone->graveyard_zoneid(),
				(zone->GetZoneID() == zone->graveyard_zoneid()) ? zone->GetInstanceID() : 0, zone->GetGraveyardPoint());
			corpse_graveyard_timer.Disable();
			auto pack = new ServerPacket(ServerOP_SpawnPlayerCorpse, sizeof(SpawnPlayerCorpse_Struct));
			SpawnPlayerCorpse_Struct* spc = (SpawnPlayerCorpse_Struct*)pack->pBuffer;
			spc->player_corpse_id = corpse_db_id;
			spc->zone_id = zone->graveyard_zoneid();
			worldserver.SendPacket(pack);
			safe_delete(pack);
			Log.Out(Logs::General, Logs::None, "Moved %s player corpse to the designated graveyard in zone %s.", this->GetName(), database.GetZoneName(zone->graveyard_zoneid()));
			corpse_db_id = 0;
		}

		corpse_graveyard_timer.Disable();
		return false;
	}
	/*
	if(corpse_res_timer.Check()) {
		can_rez = false;
		corpse_res_timer.Disable();
	}
	*/

	/* This is when a corpse hits decay timer and does checks*/
	if (corpse_decay_timer.Check()) {
		/* NPC */
		if (IsNPCCorpse()){
			corpse_decay_timer.Disable();
			return false;
		}
		/* Client */
		if (!RuleB(Zone, EnableShadowrest)){
			Delete();
		}
		else {
			if (database.BuryCharacterCorpse(corpse_db_id)) {
				Save();
				player_corpse_depop = true;
				corpse_db_id = 0;
				Log.Out(Logs::General, Logs::None, "Tagged %s player corpse has buried.", this->GetName());
			}
			else {
				Log.Out(Logs::General, Logs::Error, "Unable to bury %s player corpse.", this->GetName());
				return true;
			}
		}
		corpse_decay_timer.Disable();
		return false;
	}

	return true;
}
Exemplo n.º 4
0
void SpawnConditionManager::SetCondition(const char *zone_short, uint32 instance_id, uint16 condition_id, int16 new_value, bool world_update)
{
	if(world_update) {
		//this is an update coming from another zone, they
		//have allready updated the DB, just need to update our
		//memory, and check for condition changes
		std::map<uint16, SpawnCondition>::iterator condi;
		condi = spawn_conditions.find(condition_id);
		if(condi == spawn_conditions.end()) {
			Log(Logs::Detail, Logs::Spawns, "Condition update received from world for %d, but we do not have that conditon.", condition_id);
			return;	//unable to find the spawn condition
		}

		SpawnCondition &cond = condi->second;

		if(cond.value == new_value) {
			Log(Logs::Detail, Logs::Spawns, "Condition update received from world for %d with value %d, which is what we already have.", condition_id, new_value);
			return;
		}

		int16 old_value = cond.value;

		//set our local value
		cond.value = new_value;

		Log(Logs::Detail, Logs::Spawns, "Condition update received from world for %d with value %d", condition_id, new_value);

		//now we have to test each spawn point to see if it changed.
		zone->SpawnConditionChanged(cond, old_value);
	} else if(!strcasecmp(zone_short, zone->GetShortName()) && instance_id == zone->GetInstanceID())
	{
		//this is a local spawn condition, we need to update the DB,
		//our memory, then notify spawn points of the change.
		std::map<uint16, SpawnCondition>::iterator condi;
		condi = spawn_conditions.find(condition_id);
		if(condi == spawn_conditions.end()) {
			Log(Logs::Detail, Logs::Spawns, "Local Condition update requested for %d, but we do not have that conditon.", condition_id);
			return;	//unable to find the spawn condition
		}

		SpawnCondition &cond = condi->second;

		if(cond.value == new_value) {
			Log(Logs::Detail, Logs::Spawns, "Local Condition update requested for %d with value %d, which is what we already have.", condition_id, new_value);
			return;
		}

		int16 old_value = cond.value;

		//set our local value
		cond.value = new_value;
		//save it in the DB too
		UpdateDBCondition(zone_short, instance_id, condition_id, new_value);

		Log(Logs::Detail, Logs::Spawns, "Local Condition update requested for %d with value %d", condition_id, new_value);

		//now we have to test each spawn point to see if it changed.
		zone->SpawnConditionChanged(cond, old_value);
	}
	else
	{
		//this is a remote spawn condition, update the DB and send
		//an update packet to the zone if its up

		Log(Logs::Detail, Logs::Spawns, "Remote spawn condition %d set to %d. Updating DB and notifying world.", condition_id, new_value);

		UpdateDBCondition(zone_short, instance_id, condition_id, new_value);

		auto pack = new ServerPacket(ServerOP_SpawnCondition, sizeof(ServerSpawnCondition_Struct));
		ServerSpawnCondition_Struct* ssc = (ServerSpawnCondition_Struct*)pack->pBuffer;

		ssc->zoneID = database.GetZoneID(zone_short);
		ssc->instanceID = instance_id;
		ssc->condition_id = condition_id;
		ssc->value = new_value;

		worldserver.SendPacket(pack);
		safe_delete(pack);
	}
}
Exemplo n.º 5
0
bool Group::DelMember(Mob* oldmember,bool ignoresender)
{
	if (oldmember == nullptr)
	{
		return false;
	}

	for (uint32 i = 0; i < MAX_GROUP_MEMBERS; i++)
	{
		if (members[i] == oldmember)
		{
			members[i] = nullptr;
			membername[i][0] = '\0';
			memset(membername[i],0,64);
			MemberRoles[i] = 0;
			Log.Out(Logs::Detail, Logs::Group, "DelMember: Removed Member: %s", oldmember->GetCleanName());
			break;
		}
	}

	if(GroupCount() < 2)
	{
		DisbandGroup();
		return true;
	}

	// If the leader has quit and we have 2 or more players left in group, we want to first check the zone the old leader was in for a new leader. 
	// If a suitable replacement cannot be found, we need to go out of zone. If checkleader remains true after this method completes, another
	// loop will be run in DelMemberOOZ.
	bool checkleader = true;
	if (strcmp(GetOldLeaderName(),oldmember->GetCleanName()) == 0 && GroupCount() >= 2)
	{
		for(uint32 nl = 0; nl < MAX_GROUP_MEMBERS; nl++)
		{
			if(members[nl]) 
			{
				if (members[nl]->IsClient())
				{
					ChangeLeader(members[nl]);
					checkleader = false;
					break;
				}
			}
		}
	}
			
	ServerPacket* pack = new ServerPacket(ServerOP_GroupLeave, sizeof(ServerGroupLeave_Struct));
	ServerGroupLeave_Struct* gl = (ServerGroupLeave_Struct*)pack->pBuffer;
	gl->gid = GetID();
	gl->zoneid = zone->GetZoneID();
	gl->instance_id = zone->GetInstanceID();
	strcpy(gl->member_name, oldmember->GetName());
	gl->checkleader = checkleader;
	worldserver.SendPacket(pack);
	safe_delete(pack);

	EQApplicationPacket* outapp = new EQApplicationPacket(OP_GroupUpdate, sizeof(GroupJoin_Struct));
	GroupJoin_Struct* gu = (GroupJoin_Struct*)outapp->pBuffer;
	gu->action = groupActLeave;
	strcpy(gu->membername, oldmember->GetCleanName());
	strcpy(gu->yourname, oldmember->GetCleanName());

	for (uint32 i = 0; i < MAX_GROUP_MEMBERS; i++) {
		if (members[i] == nullptr) {
			//if (DEBUG>=5) Log.Out(Logs::Detail, Logs::Group, "Group::DelMember() null member at slot %i", i);
			continue;
		}
		if (members[i] != oldmember) {
			strcpy(gu->yourname, members[i]->GetCleanName());
			if(members[i]->IsClient())
				members[i]->CastToClient()->QueuePacket(outapp);
		}
	}

	if (!ignoresender)
	{
		strcpy(gu->yourname,oldmember->GetCleanName());
		strcpy(gu->membername,oldmember->GetCleanName());
		gu->action = groupActLeave;

		if(oldmember->IsClient())
			oldmember->CastToClient()->QueuePacket(outapp);
	}

	if(oldmember->IsClient())
	{
		database.SetGroupID(oldmember->GetCleanName(), 0, oldmember->CastToClient()->CharacterID());
	}
	
	oldmember->SetGrouped(false);
	disbandcheck = true;

	safe_delete(outapp);

	return true;
}
Exemplo n.º 6
0
void Client::GuildCommand(Seperator* sep)
{
		zgm.LoadGuilds();
		Guild_Struct* guilds = zgm.GetGuildList();


	if (strcasecmp(sep->arg[1], "help") == 0)
	{
		this->GuildPCCommandHelp();
		this->GuildGMCommandHelp();
	}
	else if (strcasecmp(sep->arg[1], "status") == 0 || strcasecmp(sep->arg[1], "stat") == 0)
	{
		Client* client = 0;

		if (sep->arg[2][0] != 0)
		{
			client = entity_list.GetClientByName(sep->argplus[2]);
		}
		else if (target != 0 && target->IsClient())
		{
			client = target->CastToClient();
		}

		if (client == 0)
		{
			this->Message(BLACK, "You must target someone or specify a character name");
		}
		else if ((client->Admin() >= 100 && admin < 100) && client->GuildDBID() != guilddbid) // no peeping for GMs, make sure tell message stays the same
		{
			this->Message(BLACK, "You must target someone or specify a character name.");
		}
		else 
		{
			if (client->GuildDBID() == 0)
			{
				this->Message(BLACK, "%s is not in a guild.", client->GetName());
			}
			else if (guilds[client->GuildEQID()].leader == client->AccountID())
			{
				this->Message(BLACK, "%s is the leader of <%s> rank: %s", client->GetName(), guilds[client->GuildEQID()].name, guilds[client->GuildEQID()].rank[client->GuildRank()].rankname);
			}
			else
			{
				this->Message(BLACK, "%s is a member of <%s> rank: %s", client->GetName(), guilds[client->GuildEQID()].name, guilds[client->GuildEQID()].rank[client->GuildRank()].rankname);
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "info") == 0)
	{
		if (sep->arg[2][0] == 0 && guilddbid == 0)
		{
			if (admin >= 100)
			{
				this->Message(BLACK, "Usage: #guildinfo guilddbid");
			}
			else
			{
				this->Message(BLACK, "You're not in a guild");
			}
		}
		else
		{
			int32 tmp;
		
			if (sep->arg[2][0] == 0)
			{
				tmp = Database::Instance()->GetGuildEQID(guilddbid);
			}
			else
			{
				tmp = Database::Instance()->GetGuildEQID(atoi(sep->arg[2]));
			}

			if (tmp < 0 || tmp >= 512)
			{
				this->Message(BLACK, "Guild not found.");
			}
			else
			{
				this->Message(BLACK, "Guild info DB# %i, %s", guilds[tmp].databaseID, guilds[tmp].name);
			
				if (this->admin >= 100 || guildeqid == tmp)
				{
					if (this->account_id == guilds[tmp].leader || guildrank == 0 || admin >= 100)
					{
						char leadername[32];
						Database::Instance()->GetAccountName(guilds[tmp].leader, leadername);
						this->Message(BLACK, "Guild Leader: %s", leadername);
					}

					for (int i = 0; i <= GUILD_MAX_RANK; i++)
					{
						this->Message(BLACK, "Rank %i: %s", i, guilds[tmp].rank[i].rankname);
						this->Message(BLACK, "  HearGU: %i  SpeakGU: %i  Invite: %i  Remove: %i  Promote: %i  Demote: %i  MOTD: %i  War/Peace: %i", guilds[tmp].rank[i].heargu, guilds[tmp].rank[i].speakgu, guilds[tmp].rank[i].invite, guilds[tmp].rank[i].remove, guilds[tmp].rank[i].promote, guilds[tmp].rank[i].demote, guilds[tmp].rank[i].motd, guilds[tmp].rank[i].warpeace);
					}
				}
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "leader") == 0) 
	{
		if (guilddbid == 0)
		{
			this->Message(BLACK, "You arent in a guild!");
		}
		else if (guilds[guildeqid].leader != account_id)
		{
			this->Message(BLACK, "You aren't the guild leader.");
		}
		else
		{
			char* tmptar = 0;

			if (sep->arg[2][0] != 0)
			{
				tmptar = sep->argplus[2];
			}
			else if (tmptar == 0 && target != 0 && target->IsClient())
			{
				tmptar = target->CastToClient()->GetName();
			}
			
			if (tmptar == 0)
			{
				Message(BLACK, "You must target someone or specify a character name.");
			}
			else
			{
				// Dark-Prince - 10/05/2008 - Code Consolidation
				//zgm.InviteToGuild(
				//this->SendGuildInvitePacket(tmptar);
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "invite") == 0)
	{
		int32 GuildDBID = atoi(sep->arg[2]);
		Client* Invitee = entity_list.GetClientByName(sep->arg[3]);
		GUILDRANK Rank = (GUILDRANK)atoi(sep->arg[4]);

		int32 GuidlEQID = Database::Instance()->GetGuildEQID(GuildDBID);

		zgm.InviteToGuild(GuildDBID, GuidlEQID, this, Invitee, Rank);
	}
	else if (strcasecmp(sep->arg[1], "remove") == 0)
	{
		Client* Removee = entity_list.GetClientByName(sep->arg[2]);

		if(Removee != 0)
		{
			zgm.RemovePCFromGuild(this, Removee);
		}
	}
	else if (strcasecmp(sep->arg[1], "promote") == 0)
	{
		if (guilddbid == 0)
		{
			Message(BLACK, "You arent in a guild!");
		}
		else if (!(strlen(sep->arg[2]) == 1 && sep->arg[2][0] >= '0' && sep->arg[2][0] <= '9'))
		{
			Message(BLACK, "Usage: #guild promote rank [charname]");
		}
		else if (atoi(sep->arg[2]) < 0 || atoi(sep->arg[2]) > GUILD_MAX_RANK)
		{
			Message(BLACK, "Error: invalid rank #.");
		}
		else
		{
			char* tmptar = 0;

			if (sep->arg[3][0] != 0)
			{
				tmptar = sep->argplus[3];
			}
			else if (tmptar == 0 && target != 0 && target->IsClient())
			{
				tmptar = target->CastToClient()->GetName();
			}

			if (tmptar == 0)
			{
				Message(BLACK, "You must target someone or specify a character name.");
			}
			else
			{
				zgm.SendGuildPromotePacket(tmptar, this->GetName());
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "demote") == 0)
	{
		if (guilddbid == 0)
		{
			Message(BLACK, "You arent in a guild!");
		}
		else if (!(strlen(sep->arg[2]) == 1 && sep->arg[2][0] >= '0' && sep->arg[2][0] <= '9'))
		{
			Message(BLACK, "Usage: #guild demote rank [charname]");
		}
		else if (atoi(sep->arg[2]) < 0 || atoi(sep->arg[2]) > GUILD_MAX_RANK)
		{
			Message(BLACK, "Error: invalid rank #.");
		}
		else 
		{
			char* tmptar = 0;
			if (sep->arg[3][0] != 0)
			{
				tmptar = sep->argplus[3];
			}
			else if (tmptar == 0 && target != 0 && target->IsClient())
			{
				tmptar = target->CastToClient()->GetName();
			}
			if (tmptar == 0)
			{
				Message(BLACK, "You must target someone or specify a character name.");
			}
			else
			{
				zgm.SendGuildDemotePacket(tmptar);
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "motd") == 0)
	{
		if (guilddbid == 0)
		{
			Message(BLACK, "You arent in a guild!");
		}
		else if (!guilds[guildeqid].rank[guildrank].motd)
		{
			Message(BLACK, "You dont have permission to change the motd.");
		}
		else if (!worldserver.Connected())
		{
			Message(BLACK, "Error: World server dirconnected");
		}
		else
		{
			char tmp[255];

			if (strcasecmp(sep->argplus[2], "none") == 0)
			{
				strcpy(tmp, "");
			}
			else
			{
				snprintf(tmp, sizeof(tmp), "%s - %s", this->GetName(), sep->argplus[2]);
			}

			if (Database::Instance()->SetGuildMOTD(guilddbid, tmp))
			{
				// Dark-Prince - 10/05/2008 - Code Consolidation
/*
				ServerPacket* pack = new ServerPacket;
				pack->opcode = ServerOP_RefreshGuild;
				pack->size = 5;
				pack->pBuffer = new uchar[pack->size];
				memcpy(pack->pBuffer, &guildeqid, 4);
				worldserver.SendPacket(pack);
				safe_delete(pack);//delete pack;
*/
			}
			else
			{
				this->Message(BLACK, "Motd update failed.");
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "edit") == 0)
	{
		if (guilddbid == 0)
		{
			Message(BLACK, "You arent in a guild!");
		}
		else if (!sep->IsNumber(2))
		{
			Message(BLACK, "Error: invalid rank #.");
		}
		else if (atoi(sep->arg[2]) < 0 || atoi(sep->arg[2]) > GUILD_MAX_RANK)
		{
			Message(BLACK, "Error: invalid rank #.");
		}
		else if (!guildrank == 0)
		{
			Message(BLACK, "You must be rank %s to use edit.", guilds[guildeqid].rank[0].rankname);
		}
		else if (!worldserver.Connected())
		{
			Message(BLACK, "Error: World server dirconnected");
		}
		else
		{
			if (!GuildEditCommand(guilddbid, guildeqid, atoi(sep->arg[2]), sep->arg[3], sep->argplus[4]))
			{
				Message(BLACK, "  #guild edit rank title newtitle");
				Message(BLACK, "  #guild edit rank permission 0/1");
			}
			else
			{
				zgm.SendGuildRefreshPacket(guildeqid);
			}
		}
	}
	// Start of GM Guild Commands
	else if (strcasecmp(sep->arg[1], "gmedit") == 0 && admin >= 100) 
	{
		if (!sep->IsNumber(2))
		{
			Message(BLACK, "Error: invalid guilddbid.");
		}
		else if (!sep->IsNumber(3))
		{
			Message(BLACK, "Error: invalid rank #.");
		}
		else if (atoi(sep->arg[3]) < 0 || atoi(sep->arg[3]) > GUILD_MAX_RANK)
		{
			Message(BLACK, "Error: invalid rank #.");
		}
		else if (!worldserver.Connected())
		{
			Message(BLACK, "Error: World server dirconnected");
		}
		else 
		{
			int32 eqid = Database::Instance()->GetGuildEQID(atoi(sep->arg[2]));
			
			if (eqid == 0xFFFFFFFF)
			{
				Message(BLACK, "Error: Guild not found");
			}
			else if (!GuildEditCommand(atoi(sep->arg[2]), eqid, atoi(sep->arg[3]), sep->arg[4], sep->argplus[5]))
			{
				Message(BLACK, "  #guild gmedit guilddbid rank title newtitle");
				Message(BLACK, "  #guild gmedit guilddbid rank permission 0/1");
			}
			else
			{
				zgm.SendGuildRefreshPacket(eqid);
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "set") == 0 && admin >= 100)
	{
		if (!sep->IsNumber(3))
		{
			Message(BLACK, "Usage: #guild set charname guildgbid (0 = clear guildtag)");
		}
		else
		{
			/* -- Work in progress
			GUILDRANK rank = GuildMember;

			Client* c = entity_list.GetClientByName(sep->arg[2]);

			if(c == 0)
			{
				Message(BLACK, "Player not found!");
				return;
			}

			int GuidDBID = atoi(sep->arg[3]);

			if(sep->IsNumber(4))
			{
				rank = (GUILDRANK)atoi(sep->arg[4]);
			}
			
			zgm.LoadGuilds();

			
			int32 GuidEQID = Database::Instance()->GetGuildEQID(GuidDBID);
			zgm.InviteToGuild(GuidDBID, GuidEQID, this, c, rank);
			*/
			
			ServerPacket* pack = new ServerPacket(ServerOP_GuildGMSet, sizeof(ServerGuildCommand_Struct));
			pack->pBuffer = new uchar[pack->size];
			memset(pack->pBuffer, 0, pack->size);
			ServerGuildCommand_Struct* sgc = (ServerGuildCommand_Struct*) pack->pBuffer;
			sgc->guilddbid = atoi(sep->arg[3]);
			sgc->admin = admin;
			strcpy(sgc->from, name);
			strcpy(sgc->target, sep->arg[2]);
			worldserver.SendPacket(pack);
			safe_delete(pack);//delete pack;
		}
	}
	else if (strcasecmp(sep->arg[1], "setrank") == 0 && admin >= 100)
	{
		if (!sep->IsNumber(3))
		{
			Message(BLACK, "Usage: #guild setrank charname rank");
		}
		else if (atoi(sep->arg[3]) < 0 || atoi(sep->arg[3]) > GUILD_MAX_RANK)
		{
			Message(BLACK, "Error: invalid rank #.");
		}
		else
		{
			ServerPacket* pack = new ServerPacket(ServerOP_GuildGMSetRank, sizeof(ServerGuildCommand_Struct));


			pack->pBuffer = new uchar[pack->size];
			memset(pack->pBuffer, 0, pack->size);
			ServerGuildCommand_Struct* sgc = (ServerGuildCommand_Struct*) pack->pBuffer;
			sgc->newrank = (GUILDRANK)atoi(sep->arg[3]);
			sgc->admin = admin;
			strcpy(sgc->from, name);
			strcpy(sgc->target, sep->arg[2]);
			worldserver.SendPacket(pack);
			

			target->CastToClient()->SetGuild(target->CastToClient()->guilddbid, sgc->newrank);

			safe_delete(pack);//delete pack;
		}
	}
	/* New Guild Creation -> Challenge/Response method */
	else if (strcasecmp(sep->arg[1], "dpcreate") == 0 && admin >= 100)
	{
		if (sep->arg[3][0] == 0)
		{
			Message(BLACK, "Usage: #guild create {guildleader charname or AccountID} guild name");
		}
		else if (!worldserver.Connected())
		{
			Message(BLACK, "Error: World server dirconnected");
		}
		else
		{
			zgm.CreateGuildRequest(this, sep->arg[2], sep->argplus[3]);
		}
	}
	/* END New Guild Creation -> Challenge/Response method */
	else if (strcasecmp(sep->arg[1], "create") == 0 && admin >= 100)
	{
		if (sep->arg[3][0] == 0)
		{
			Message(BLACK, "Usage: #guild create {guildleader charname or AccountID} guild name");
		}
		else if (!worldserver.Connected())
		{
			Message(BLACK, "Error: World server dirconnected");
		}
		else
		{
			Client* Leader = entity_list.GetClientByName(sep->arg[2]);

			int32 guilddbid = 0;

			if(Leader != 0)
			{
				zgm.CreateGuild(this, Leader, sep->argplus[3], guilddbid);
			}			
		}
	}
	else if (strcasecmp(sep->arg[1], "delete") == 0 && admin >= 100)
	{
		if (!sep->IsNumber(2))
		{
			Message(BLACK, "Usage: #guild delete guildDBID");
		}
		else if (!worldserver.Connected())
		{
			Message(BLACK, "Error: World server dirconnected");
		}
		else
		{
			int32 tmpeq = Database::Instance()->GetGuildEQID(atoi(sep->arg[2]));
			char tmpname[32];

			if (tmpeq != 0xFFFFFFFF)
			{
				strcpy(tmpname, guilds[tmpeq].name);
			}

			if (!Database::Instance()->DeleteGuild(atoi(sep->arg[2])))
			{
				Message(BLACK, "Guild delete failed.");
			}
			else
			{
				if (tmpeq != 0xFFFFFFFF)
				{
					zgm.LoadGuilds();

					ServerPacket* pack = new ServerPacket(ServerOP_RefreshGuild, 5);
					
					pack->pBuffer = new uchar[pack->size];
					memcpy(pack->pBuffer, &tmpeq, 4);
					pack->pBuffer[4] = 1;
					worldserver.SendPacket(pack);
					safe_delete(pack);//delete pack;

					Message(BLACK, "Guild deleted: DB# %i, EQ# %i: %s", atoi(sep->arg[2]), tmpeq, tmpname);
				} 
				else
				{
					Message(BLACK, "Guild deleted: DB# %i", atoi(sep->arg[2]));
				}
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "rename") == 0 && admin >= 100)
	{
		if ((!sep->IsNumber(2)) || sep->arg[3][0] == 0)
		{
			Message(BLACK, "Usage: #guild rename guildDBID newname");
		}
		else if (!worldserver.Connected())
		{
			Message(BLACK, "Error: World server dirconnected");
		}
		else
		{
			int32 tmpeq = Database::Instance()->GetGuildEQID(atoi(sep->arg[2]));
			char tmpname[32];

			if (tmpeq != 0xFFFFFFFF)
			{
				strcpy(tmpname, guilds[tmpeq].name);
			}

			if (!Database::Instance()->RenameGuild(atoi(sep->arg[2]), sep->argplus[3]))
			{
				Message(BLACK, "Guild rename failed.");
			}
			else 
			{
				if (tmpeq != 0xFFFFFFFF) 
				{
					ServerPacket* pack = new ServerPacket(ServerOP_RefreshGuild, 5);
					pack->pBuffer = new uchar[pack->size];
					memcpy(pack->pBuffer, &tmpeq, 4);
					pack->pBuffer[4] = 1;
					worldserver.SendPacket(pack);
					safe_delete(pack);//delete pack;

					Message(BLACK, "Guild renamed: DB# %i, EQ# %i, OldName: %s, NewName: %s", atoi(sep->arg[2]), tmpeq, tmpname, sep->argplus[3]);
				}
				else
				{
					Message(BLACK, "Guild renamed: DB# %i, NewName: %s", atoi(sep->arg[2]), sep->argplus[3]);
				}
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "setleader") == 0 && admin >= 100) 
	{
		if (sep->arg[3][0] == 0 || !sep->IsNumber(2))
		{
			Message(BLACK, "Usage: #guild setleader guilddbid {guildleader charname or AccountID}");
		}
		else if (!worldserver.Connected())
		{
			Message(BLACK, "Error: World server dirconnected");
		}
		else
		{
			int32 leader = 0;
			
			if (sep->IsNumber(3))
			{
				leader = atoi(sep->arg[3]);
			}
			else
			{
				leader = Database::Instance()->GetAccountIDByChar(sep->argplus[3]);
			}

			int32 tmpdb = Database::Instance()->GetGuildDBIDbyLeader(leader);
			
			if (leader == 0)
			{
				Message(BLACK, "New leader not found.");
			}
			else if (tmpdb != 0) 
			{
				int32 tmpeq = Database::Instance()->GetGuildEQID(tmpdb);

				if (tmpeq >= 512)
				{
					Message(BLACK, "Error: %s already is the leader of DB# %i.", sep->argplus[3], tmpdb);
				}
				else
				{
					Message(BLACK, "Error: %s already is the leader of DB# %i <%s>.", sep->argplus[3], tmpdb, guilds[tmpeq].name);
				}
			}
			else 
			{
				int32 tmpeq = Database::Instance()->GetGuildEQID(atoi(sep->arg[2]));

				if (tmpeq == 0xFFFFFFFF)
				{
					Message(BLACK, "Guild not found.");
				}
				else if (!Database::Instance()->SetGuildLeader(atoi(sep->arg[2]), leader))
				{
					Message(BLACK, "Guild leader change failed.");
				}
				else
				{
					zgm.SendGuildRefreshPacket(tmpeq);

					Message(BLACK, "Guild leader changed: DB# %s, Leader: %s, Name: <%s>", sep->arg[2], sep->argplus[3], guilds[tmpeq].name);
				}
			}
		}
	}
	else if (strcasecmp(sep->arg[1], "list") == 0 && admin >= 100)
	{
		int x = 0;
		Message(BLACK, "Listing guilds on the server:");
		char leadername[32];
		int magicnumber = 512;

		zgm.LoadGuilds();
		guilds = zgm.GetGuildList();

		for (int i = 0; i < magicnumber; i++)
		{
			if (guilds[i].databaseID != 0)
			{
				leadername[0] = 0;
				Database::Instance()->GetAccountName(guilds[i].leader, leadername);

				if (leadername[0] == 0)
				{
					Message(BLACK, "  DB# %i EQ# %i  <%s>", guilds[i].databaseID, i, guilds[i].name);
				}
				else
				{
					Message(BLACK, "  DB# %i EQ# %i  <%s> Leader: %s", guilds[i].databaseID, i, guilds[i].name, leadername);
				}

				x++;
			}
		}
		Message(BLACK, "%i guilds listed.", x);
	}
	else if (strcasecmp(sep->arg[1], "reload") == 0 && admin >= 100)
	{

		Message(BLACK, "Reloading Guilds");

		int32 eqdbid = atoi(sep->arg[2]);
		zgm.LoadGuilds();
		zgm.SendGuildRefreshPacket(eqdbid);
	}
	else 
	{
		Message(BLACK, "Unknown guild command, try #guild help");
	}
}
Exemplo n.º 7
0
void Client::DoZoneSuccess(ZoneChange_Struct *zc, uint16 zone_id, uint32 instance_id, float dest_x, float dest_y, float dest_z, float dest_h, int8 ignore_r) {
	//this is called once the client is fully allowed to zone here
	//it takes care of all the activities which occur when a client zones out

	SendLogoutPackets();

	//dont clear aggro until the zone is successful
	entity_list.RemoveFromHateLists(this);

	if(this->GetPet())
		entity_list.RemoveFromHateLists(this->GetPet());

	LogFile->write(EQEMuLog::Status, "Zoning '%s' to: %s (%i) - (%i) x=%f, y=%f, z=%f",
		m_pp.name, database.GetZoneName(zone_id), zone_id, instance_id,
		dest_x, dest_y, dest_z);

	//set the player's coordinates in the new zone so they have them
	//when they zone into it
	x_pos = dest_x; //these coordinates will now be saved when ~client is called
	y_pos = dest_y;
	z_pos = dest_z;
	heading = dest_h; // Cripp: fix for zone heading
	m_pp.heading = dest_h;
	m_pp.zone_id = zone_id;
	m_pp.zoneInstance = instance_id;

	//Force a save so its waiting for them when they zone
	Save(2);

	if (zone_id == zone->GetZoneID() && instance_id == zone->GetInstanceID()) {
		// No need to ask worldserver if we're zoning to ourselves (most
		// likely to a bind point), also fixes a bug since the default response was failure
		EQApplicationPacket* outapp = new EQApplicationPacket(OP_ZoneChange,sizeof(ZoneChange_Struct));
		ZoneChange_Struct* zc2 = (ZoneChange_Struct*) outapp->pBuffer;
		strcpy(zc2->char_name, GetName());
		zc2->zoneID = zone_id;
		zc2->instanceID = instance_id;
		zc2->success = 1;
		outapp->priority = 6;
		FastQueuePacket(&outapp);

		zone->StartShutdownTimer(AUTHENTICATION_TIMEOUT * 1000);
	} else {
	// vesuvias - zoneing to another zone so we need to the let the world server
	//handle things with the client for a while
		ServerPacket* pack = new ServerPacket(ServerOP_ZoneToZoneRequest, sizeof(ZoneToZone_Struct));
		ZoneToZone_Struct* ztz = (ZoneToZone_Struct*) pack->pBuffer;
		ztz->response = 0;
		ztz->current_zone_id = zone->GetZoneID();
		ztz->current_instance_id = zone->GetInstanceID();
		ztz->requested_zone_id = zone_id;
		ztz->requested_instance_id = instance_id;
		ztz->admin = admin;
		ztz->ignorerestrictions = ignore_r;
		strcpy(ztz->name, GetName());
		ztz->guild_id = GuildID();
		worldserver.SendPacket(pack);
		safe_delete(pack);
	}

	//reset to unsolicited.
	zone_mode = ZoneUnsolicited;
	zonesummon_x = 0;
	zonesummon_y = 0;
	zonesummon_z = 0;
	zonesummon_id = 0;
	zonesummon_ignorerestrictions = 0;
}
Exemplo n.º 8
0
void WorldServer::Process()
{
	if(this == 0)
	{
		return;
	}
	if(!Connected())
	{
		return;
	}

	SOCKADDR_IN to;
	memset((char *) &to, 0, sizeof(to));
	to.sin_family = AF_INET;
	to.sin_port = port;
	to.sin_addr.s_addr = ip;

	/************ Get all packets from packet manager out queue and process them ************/
	ServerPacket *pack = 0;
	while(pack = ServerRecvQueuePop())
	{
		switch(pack->opcode) 
		{
		case 0: 
			{
				break;
			}
		case ServerOP_KeepAlive: 
			{
				// ignore this
				break;
			}
		case ServerOP_ChannelMessage:
			{
				if (!ZoneLoaded) break;
				ServerChannelMessage_Struct* scm = (ServerChannelMessage_Struct*) pack->pBuffer;
				if (scm->deliverto[0] == 0) 
				{
					entity_list.ChannelMessageFromWorld(scm->from, scm->to, scm->chan_num, scm->guilddbid, scm->language, scm->message);
				}
				else 
				{
					Client* client;
					client = entity_list.GetClientByName(scm->deliverto);
					if (client != 0)
					{
						if (client->Connected()) 
						{
							client->ChannelMessageSend(scm->from, scm->to, scm->chan_num, scm->language, scm->message);
							if (!scm->noreply) 
							{
								// if it's a tell, echo back so it shows up
								scm->noreply = true;
								scm->chan_num = 14;
								memset(scm->deliverto, 0, sizeof(scm->deliverto));
								strcpy(scm->deliverto, scm->from);
								SendPacket(pack);
							}
						}
					}
				}
				break;
			}
		case ServerOP_EmoteMessage: 
			{
				if (!ZoneLoaded)
				{
					break;
				}

				ServerEmoteMessage_Struct* sem = (ServerEmoteMessage_Struct*) pack->pBuffer;

				if (sem->to[0] != 0)
				{
					if (strcasecmp(sem->to, zone->GetShortName()) == 0)
					{
						entity_list.Message(sem->guilddbid, (MessageFormat)sem->type, sem->message);
					}
					else
					{
						Client* client = entity_list.GetClientByName(sem->to);
						if (client != 0)
						{
							client->Message((MessageFormat)sem->type, sem->message);
						}
					}
				}
				else
				{
					entity_list.Message(sem->guilddbid, (MessageFormat)sem->type, sem->message);
				}
				break;
			}
/*		case ServerOP_GroupRefresh: //Kibanu - 4/22/2009
			{
				cout << "WorldServer_Process: In Group Refresh" << endl;
				if (!ZoneLoaded)
				{
					break;
				}

				ServerGroupRefresh_Struct* gr = (ServerGroupRefresh_Struct*) pack->pBuffer;

				if (gr->member[0] != 0)
				{
					cout << "WorldServer_Process: Refreshing group for " << gr->member << endl;
					Client* client = entity_list.GetClientByName(gr->member);
					if (client != 0)
					{
						client->RefreshGroup(gr->gid, gr->action);
					}
				}
				break;
			}*/
		case ServerOP_ShutdownAll: 
			{
				entity_list.Save();
				CatchSignal(2);
				break;
			}
		case ServerOP_ZoneShutdown: 
			{
				// Annouce the change to the world
				if (!ZoneLoaded)
				{
					SetZone("");
				}
				else
				{
					worldserver.SendEmoteMessage(0, 0, 15, "Zone shutdown: %s", zone->GetLongName());

					ServerZoneStateChange_struct* zst = (ServerZoneStateChange_struct *) pack->pBuffer;
					cout << "Zone shutdown by " << zst->adminname << endl;
					Zone::Shutdown();
				}
				break;
			}
		case ServerOP_ZoneBootup:
			{
				ServerZoneStateChange_struct* zst = (ServerZoneStateChange_struct *) pack->pBuffer;
				if (ZoneLoaded)
				{
					SetZone(zone->GetShortName());
					if (strcasecmp(Database::Instance()->GetZoneName(zst->zoneid), zone->GetShortName()) == 0) 
					{
						// This packet also doubles as "incomming client" notification, lets not shut down before they get here
						zone->StartShutdownTimer(AUTHENTICATION_TIMEOUT * 1000);
					}
					else 
					{
						worldserver.SendEmoteMessage(zst->adminname, 0, 0, "Zone bootup failed: Already running '%s'", zone->GetShortName());
					}
					break;
				}

				if (zst->adminname[0] != 0)
				{
					cout << "Zone bootup by " << zst->adminname << endl;
				}

				if (!(Zone::Bootup(Database::Instance()->GetZoneName(zst->zoneid)))) 
				{
					worldserver.SendChannelMessage(0, 0, 10, 0, 0, "%s:%i Zone::Bootup failed: %s", net.GetZoneAddress(), net.GetZonePort(), Database::Instance()->GetZoneName(zst->zoneid));
				}
				break;
			}
		case ServerOP_ZonePlayer: 
			{
				ServerZonePlayer_Struct* szp = (ServerZonePlayer_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(szp->name);
				if (client != 0) 
				{
					if (strcasecmp(szp->adminname, szp->name) == 0)
					{
						client->Message(BLACK, "Zoning to: %s", szp->zone);
					}
					else if (client->GetAnon() == 1 && client->Admin() > szp->adminrank)
					{
						break;
					}
					else 
					{
						worldserver.SendEmoteMessage(szp->adminname, 0, 0, "Summoning %s to %s %1.1f, %1.1f, %1.1f", szp->name, szp->zone, szp->x_pos, szp->y_pos, szp->z_pos);
					}
					client->SetIsZoning(true);
					client->SetUsingSoftCodedZoneLine(true);
					client->SetZoningHeading(client->GetHeading());
					client->SetZoningX(szp->x_pos);
					client->SetZoningY(szp->y_pos);
					client->SetZoningZ(szp->z_pos);
					client->ZonePC(szp->zone, szp->x_pos, szp->y_pos, szp->z_pos);
				}
				break;
			}
			// Cofruben: used to send a packet directly to a client.
/*		case ServerOP_SendPacket: 
			{
				ServerSendPacket_Struct* sss = (ServerSendPacket_Struct*)pack->pBuffer;
				int32 PacketSize = pack->size - sizeof(sss->charname) - sizeof(sss->opcode);
				Client* PacketTo = entity_list.GetClientByName(sss->charname);
				if(!PacketTo)
				{
					break;
				}
				APPLAYER* outapp = new APPLAYER(sss->opcode, PacketSize);
				memcpy(outapp->pBuffer, sss->packet, PacketSize);
				PacketTo->QueuePacket(outapp);
				safe_delete(outapp);//delete outapp;
				break;
			}*/
		case ServerOP_KickPlayer:
			{
				ServerKickPlayer_Struct* skp = (ServerKickPlayer_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(skp->name);
				if (client != 0) 
				{
					if (skp->adminrank >= client->Admin()) 
					{
						client->Kick();
						if (ZoneLoaded)
						{
							worldserver.SendEmoteMessage(skp->adminname, 0, 0, "Remote Kick: %s booted in zone %s.", skp->name, zone->GetShortName());
						}
						else
						{
							worldserver.SendEmoteMessage(skp->adminname, 0, 0, "Remote Kick: %s booted.", skp->name);
						}
					}
					else if (client->GetAnon() != 1)
					{
						worldserver.SendEmoteMessage(skp->adminname, 0, 0, "Remote Kick: Your avatar level is not high enough to kick %s", skp->name);
					}
				}
				break;
			}
		case ServerOP_KillPlayer:
			{
				ServerKillPlayer_Struct* skp = (ServerKillPlayer_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(skp->target);
				if (client != 0) 
				{
					if (skp->admin >= client->Admin()) 
					{
						client->Kill();
						if (ZoneLoaded)
						{
							worldserver.SendEmoteMessage(skp->gmname, 0, 0, "Remote Kill: %s killed in zone %s.", skp->target, zone->GetShortName());
						}
						else
						{
							worldserver.SendEmoteMessage(skp->gmname, 0, 0, "Remote Kill: %s killed.", skp->target);
						}
					}
					else if (client->GetAnon() != 1)
					{
						worldserver.SendEmoteMessage(skp->gmname, 0, 0, "Remote Kill: Your avatar level is not high enough to kill %s", skp->target);
					}
				}
				break;
			}
		case ServerOP_RefreshGuild:
			{
				if (pack->size == 5)
				{
					int32 guildeqid = 0;
					memcpy(&guildeqid, pack->pBuffer, 4);

					zgm.LoadGuilds();
					Guild_Struct* guilds = zgm.GetGuildList();


					if (pack->pBuffer[4] == 1)
					{
						APPLAYER* outapp = new APPLAYER(OP_GuildUpdate, 64);
						memset(outapp->pBuffer, 0, outapp->size);
						GuildUpdate_Struct* gu = (GuildUpdate_Struct*) outapp->pBuffer;
						gu->guildID = guildeqid;
						gu->entry.guildID = guildeqid;

						if (guilds[guildeqid].databaseID == 0) 
						{
							gu->entry.exists = 0; // = 0x01 if exists, 0x00 on empty
						}
						else
						{
							strcpy(gu->entry.name, guilds[guildeqid].name);
							gu->entry.exists = 1; // = 0x01 if exists, 0x00 on empty
						}
						gu->entry.unknown1[0] = 0xFF;
						gu->entry.unknown1[1] = 0xFF;
						gu->entry.unknown1[2] = 0xFF;
						gu->entry.unknown1[3] = 0xFF;
						gu->entry.unknown3[0] = 0xFF;
						gu->entry.unknown3[1] = 0xFF;
						gu->entry.unknown3[2] = 0xFF;
						gu->entry.unknown3[3] = 0xFF;

						entity_list.QueueClients(0, outapp, false);
						safe_delete(outapp);//delete outapp;
					}
				}
				else
					cout << "Wrong size: ServerOP_RefreshGuild. size=" << pack->size << endl;
				break;
			}
		case ServerOP_GuildLeader:
			{
				ServerGuildCommand_Struct* sgc = (ServerGuildCommand_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(sgc->target);

				if (client == 0)
				{
					// do nothing
				}
				else if (client->GuildDBID() != sgc->guilddbid)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s is not in your guild.", client->GetName());
				}
				else if ((client->GuildRank() != 0) || (client->GuildRank() != 1))
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s is not rank 0.", client->GetName());
				}
				else 
				{
					if (Database::Instance()->SetGuildLeader(sgc->guilddbid, client->AccountID())) 
					{
						worldserver.SendEmoteMessage(0, sgc->guilddbid, MESSAGETYPE_Guild, "%s is now the leader of your guild.", client->GetName());
						ServerPacket* pack2 = new ServerPacket(ServerOP_RefreshGuild, 4);

						pack2->pBuffer = new uchar[pack->size];
						memcpy(pack2->pBuffer, &sgc->guildeqid, 4);
						worldserver.SendPacket(pack2);
						safe_delete(pack2);//delete pack2;
					}
					else
					{
						worldserver.SendEmoteMessage(sgc->from, 0, 0, "Guild leadership transfer failed.");
					}
				}
				break;
			}
		case ServerOP_GuildInvite: 
			{
				ServerGuildCommand_Struct* sgc = (ServerGuildCommand_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(sgc->target);
				zgm.LoadGuilds();
				Guild_Struct* guilds = zgm.GetGuildList();

				if (client == 0)
				{
					// do nothing
				}
				else if (!guilds[sgc->guildeqid].rank[sgc->fromrank].invite)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "You dont have permission to invite.");
				}
				else if (client->GuildDBID() != 0)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s is already in another guild.", client->GetName());
				}
				else if (client->PendingGuildInvite != 0 && !(client->PendingGuildInvite == sgc->guilddbid))
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s has another pending guild invite.", client->GetName());
				}
				else
				{
					client->PendingGuildInvite = sgc->guilddbid;
					APPLAYER* outapp = new APPLAYER(OP_GuildInvite, sizeof(GuildCommand_Struct));
					memset(outapp->pBuffer, 0, outapp->size);
					GuildCommand_Struct* gc = (GuildCommand_Struct*) outapp->pBuffer;
					gc->guildeqid = sgc->guildeqid;
					strcpy(gc->Inviter, sgc->target);
					strcpy(gc->Invitee, sgc->from);
					client->QueuePacket(outapp);
					/*				
					if (client->SetGuild(sgc->guilddbid, GUILD_MAX_RANK))
					worldserver.SendEmoteMessage(0, sgc->guilddbid, MT_Guild, "%s has joined the guild. Rank: %s.", client->GetName(), guilds[sgc->guildeqid].rank[GUILD_MAX_RANK].rankname);
					else
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "Guild invite failed.");
					*/
				}
				break;
			}
		case ServerOP_GuildRemove:
			{
				ServerGuildCommand_Struct* sgc = (ServerGuildCommand_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(sgc->target);
				zgm.LoadGuilds();
				Guild_Struct* guilds = zgm.GetGuildList();

				if (client == 0)
				{
					// do nothing
				}
				else if ((!guilds[sgc->guildeqid].rank[sgc->fromrank].remove) && !(strcasecmp(sgc->from, sgc->target) == 0))
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "You dont have permission to remove.");
				}
				else if (client->GuildDBID() != sgc->guilddbid)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s is not in your guild.", client->GetName());
				}
				else if (client->GuildRank() <= sgc->fromrank && !(sgc->fromaccountid == guilds[sgc->guildeqid].leader) && !(strcasecmp(sgc->from, sgc->target) == 0))
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s's rank is too high for you to remove them.", client->GetName());
				}
				else
				{
					if (client->SetGuild(0, GUILD_MAX_RANK))
					{
						if (strcasecmp(sgc->from, sgc->target) == 0)
						{
							worldserver.SendEmoteMessage(0, sgc->guilddbid, GUILD, "%s has left the guild.", client->GetName());
						}
						else
						{
							worldserver.SendEmoteMessage(0, sgc->guilddbid, GUILD, "%s has been removed from the guild by %s.", client->GetName(), sgc->from);
							client->Message(GUILD, "You have been removed from the guild by %s.", sgc->from);
						}
					}
					else
					{
						worldserver.SendEmoteMessage(sgc->from, 0, 0, "Guild remove failed.");
					}
				}
				break;
			}
		case ServerOP_GuildPromote:
			{
				ServerGuildCommand_Struct* sgc = (ServerGuildCommand_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(sgc->target);
				zgm.LoadGuilds();
				Guild_Struct* guilds = zgm.GetGuildList();

				if (client == 0)
				{
					// do nothing
				}

				else if (client->GuildDBID() != sgc->guilddbid)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s is not in your guild.", client->GetName());
				}
				else if ((!guilds[sgc->guildeqid].rank[sgc->fromrank].promote) && !(strcasecmp(sgc->from, sgc->target) == 0))
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "You dont have permission to promote.");
				}
				else if (client->GuildDBID() != sgc->guilddbid)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s isnt in your guild.", client->GetName());
				}
				else if (client->GuildRank() <= sgc->newrank)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s is already rank %i.", client->GetName(), client->GuildRank());
				}
				else if (sgc->newrank <= sgc->fromrank && sgc->fromaccountid != guilds[sgc->guildeqid].leader)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "You cannot promote people to a greater or equal rank than yourself.");
				}
				else 
				{
					if (client->SetGuild(sgc->guilddbid, sgc->newrank)) 
					{
						worldserver.SendEmoteMessage(0, sgc->guilddbid, MESSAGETYPE_Guild, "%s has been promoted to %s by %s.", client->GetName(), guilds[sgc->guildeqid].rank[sgc->newrank].rankname, sgc->from);
					}
					else
					{
						worldserver.SendEmoteMessage(sgc->from, 0, 0, "Guild promote failed");
					}
				}
				break;
			}
		case ServerOP_GuildDemote:
			{
				ServerGuildCommand_Struct* sgc = (ServerGuildCommand_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(sgc->target);

				zgm.LoadGuilds();
				Guild_Struct* guilds = zgm.GetGuildList();

				if (client == 0)
				{
					// do nothing
				}
				else if (client->GuildDBID() != sgc->guilddbid)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s is not in your guild.", client->GetName());
				}
				else if (!guilds[sgc->guildeqid].rank[sgc->fromrank].demote)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "You dont have permission to demote.");
				}
				else if (client->GuildRank() >= sgc->newrank)
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "%s is already rank %i.", client->GetName(), client->GuildRank());
				}
				else if (sgc->newrank <= sgc->fromrank && sgc->fromaccountid != guilds[sgc->guildeqid].leader && !(strcasecmp(sgc->from, sgc->target) == 0))
				{
					worldserver.SendEmoteMessage(sgc->from, 0, 0, "You cannot demote people with a greater or equal rank than yourself.");
				}
				else
				{
					if (client->SetGuild(sgc->guilddbid, sgc->newrank)) 
					{
						worldserver.SendEmoteMessage(0, sgc->guilddbid, MESSAGETYPE_Guild, "%s has been demoted to %s by %s.", client->GetName(), guilds[sgc->guildeqid].rank[sgc->newrank].rankname, sgc->from);
					}
					else
					{
						worldserver.SendEmoteMessage(sgc->from, 0, 0, "Guild demote failed");
					}
				}
				break;
			}
		case ServerOP_GuildGMSet:
			{
				ServerGuildCommand_Struct* sgc = (ServerGuildCommand_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(sgc->target);
				if (client != 0) 
				{
					if (client->GuildDBID() == 0 || sgc->guilddbid == 0) 
					{
						if (!client->SetGuild(sgc->guilddbid, GUILD_MAX_RANK))
						{
							worldserver.SendEmoteMessage(sgc->from, 0, 0, "Error: Guild #%i not found", sgc->guilddbid);
						}
					}
					else
					{
						worldserver.SendEmoteMessage(sgc->from, 0, 0, "Error: %s is already in a guild", sgc->target);
					}
				}
				break;
			}
		case ServerOP_GuildGMSetRank:
			{
				ServerGuildCommand_Struct* sgc = (ServerGuildCommand_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(sgc->target);
				if (client != 0)
				{
					if (client->GuildDBID() != 0)
					{
						if (!client->SetGuild(client->GuildDBID(), sgc->newrank))
						{
							worldserver.SendEmoteMessage(sgc->from, 0, 0, "Error: SetRank failed.", sgc->guilddbid);
						}
					}
					else
					{
						worldserver.SendEmoteMessage(sgc->from, 0, 0, "Error: %s is not in a guild", sgc->target);
					}
				}
				break;
			}
/*		case ServerOP_GuildCreateResponse:
			{
				GuildCreateResponse_Struct* gcrs = (GuildCreateResponse_Struct*) pack->pBuffer;

				if(gcrs->Created)
				{
					cout << "Guild " << gcrs->GuildName << " created." << endl;
					Client* client = entity_list.GetClientByName(gcrs->LeaderCharName);
					// invite the client to guild
					zgm.InviteToGuild(0, gcrs->eqid, client, client, GuildLeader);
				}
				
				break;
			}*/
		case ServerOP_FlagUpdate:
			{
				Client* client = entity_list.GetClientByAccID(Database::Instance()->GetAccountIDByName((char*) pack->pBuffer));
				if (client != 0) 
				{
					client->UpdateAdmin();
				}
				break;
			}
		case ServerOP_GMGoto: 
			{
				if (pack->size != sizeof(ServerGMGoto_Struct)) 
				{
					cout << "Wrong size on ServerOP_GMGoto. Got: " << pack->size << ", Expected: " << sizeof(ServerGMGoto_Struct) << endl;
					break;
				}
				if (!ZoneLoaded) 
				{
					break;
				}
				ServerGMGoto_Struct* gmg = (ServerGMGoto_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(gmg->gotoname);
				if (client != 0) 
				{
					worldserver.SendEmoteMessage(gmg->myname, 0, 13, "Summoning you to: %s @ %s, %1.1f, %1.1f, %1.1f", client->GetName(), zone->GetShortName(), client->GetX(), client->GetY(), client->GetZ());

					ServerPacket* outpack = new ServerPacket(ServerOP_ZonePlayer, sizeof(ServerZonePlayer_Struct));


					outpack->pBuffer = new uchar[outpack->size];
					memset(outpack->pBuffer, 0, outpack->size);
					ServerZonePlayer_Struct* szp = (ServerZonePlayer_Struct*) outpack->pBuffer;
					strcpy(szp->adminname, gmg->myname);
					strcpy(szp->name, gmg->myname);
					strcpy(szp->zone, zone->GetShortName());
					szp->x_pos = client->GetX();
					szp->y_pos = client->GetY();
					szp->z_pos = client->GetZ();
					worldserver.SendPacket(outpack);
					safe_delete(outpack);//delete outpack;
				}
				else
				{
					worldserver.SendEmoteMessage(gmg->myname, 0, 13, "Error: %s not found", gmg->gotoname);
				}
				break;
			}
		case ServerOP_MultiLineMsg:
			{
				ServerMultiLineMsg_Struct* mlm = (ServerMultiLineMsg_Struct*) pack->pBuffer;
				Client* client = entity_list.GetClientByName(mlm->to);
				if (client) 
				{
					APPLAYER* outapp = new APPLAYER(OP_MultiLineMsg, strlen(mlm->message));
					strcpy((char*) outapp->pBuffer, mlm->message);
					client->QueuePacket(outapp);
					safe_delete(outapp);//delete outapp;
				}
				break;
			}
		case ServerOP_RezzPlayer:
			{
				RezzPlayer_Struct* srs = (RezzPlayer_Struct*)pack->pBuffer;
				//Yeahlight: A resurrection request has been made
				if(srs->rezzopcode == OP_RezzRequest)
				{
					Client* client = entity_list.GetClientByName(srs->owner);
					//Yeahlight: Owner of the corpse is online
					if(client)
					{
						Spell* spell = spells_handler.GetSpellPtr(srs->rez.spellID);
						//Yeahlight: Spell passed through the packet is a legit spell
						if(spell)
						{
							//Yeahlight: Record the pending resurrection information
							client->SetPendingRez(true);
							client->SetPendingRezExp(srs->exp);
							client->SetPendingCorpseID(srs->corpseDBID);
							client->SetPendingRezX(srs->rez.x);
							client->SetPendingRezY(srs->rez.y);
							client->SetPendingRezZ(srs->rez.z);
							client->SetPendingRezZone(srs->rez.zoneName);
							client->SetPendingSpellID(spell->GetSpellID());
							client->StartPendingRezTimer();
							if(client->GetDebugMe())
								client->Message(YELLOW, "Debug: Forwarding the resurrection request to your client (%s)", srs->rez.targetName);
							//Yeahlight: Forward the resurrection packet to the corpse's owner
							APPLAYER* outapp = new APPLAYER(OP_RezzRequest, sizeof(Resurrect_Struct));
							Resurrect_Struct* rez = (Resurrect_Struct*)outapp->pBuffer;
							memset(rez, 0, sizeof(Resurrect_Struct));
							memcpy(rez, &srs->rez, sizeof(Resurrect_Struct));
							client->QueuePacket(outapp);
							safe_delete(outapp);
						}
					}
				}
				//Yeahlight: A resurrection confirmation has been made
				else if(srs->rezzopcode == OP_RezzAnswer)
				{
					Client* client = entity_list.GetClientByName(srs->owner);
					//Yeahlight: Owner of the corpse is online
					if(client)
					{
						bool fullGMRez = false;
						//Yeahlight: The corpse owner answers 'yes' to the request
						if(srs->action == 1)
						{
							Database::Instance()->SetCorpseRezzed(client->GetPendingCorpseID());
							//Yeahlight: Player casted resurrection
							if(client->GetPendingSpellID() != 994)
							{
								float expRefund = 0.00;
								//Yeahlight: PC has exp on the corpse
								if(client->GetPendingRezExp())
								{
									//Yeahlight: Switch based on spell ID
									switch(client->GetPendingSpellID())
									{
										//Yeahlight: Revive
										case 391:
										{
											expRefund = 0.00;
											break;
										}
										//Yeahlight: Resuscitate
										case 388:
										{
											expRefund = 0.50;
											break;
										}
										//Yeahlight: Resurrection
										case 392:
										{
											expRefund = 0.90;
											break;
										}
										//Yeahlight: Reviviscence
										case 1524:
										{
											expRefund = 0.96;
											break;
										}
										//Yeahlight: Convergence
										case 1733:
										{
											expRefund = 0.93;
											break;
										}
										default:
										{
											client->Message(RED, "ERROR: Unknown resurrection spell ID: %i", client->GetPendingSpellID());
											expRefund = 0.00;
										}
									}
									if(client->GetDebugMe())
										client->Message(LIGHTEN_BLUE, "Debug: Your resurrection return on exp: %1.2f", expRefund);
									client->AddEXP(client->GetPendingRezExp() * expRefund, true);
								}
							}
							//Yeahlight: GM casted resurrection
							else
							{
								fullGMRez = true;
								if(client->GetDebugMe())
									client->Message(LIGHTEN_BLUE, "Debug: Your resurrection return on exp: 1.00");
								client->AddEXP(client->GetPendingRezExp(), true);
							}
							//Yeahlight: Client is being resurrected in another zone; prepare them for transit
							if(strcmp(zone->GetShortName(), srs->rez.zoneName) != 0)
							{
								client->SetTempHeading(0);
								client->SetUsingSoftCodedZoneLine(true);
								client->SetIsZoning(true);
								client->SetZoningX(client->GetPendingRezX());
								client->SetZoningY(client->GetPendingRezY());
								client->SetZoningZ(client->GetPendingRezZ());
							}
							//Yeahlight: Send the packet back to the owner of the corpse
							APPLAYER* outapp = new APPLAYER(OP_RezzComplete, sizeof(Resurrect_Struct));
							memcpy(outapp->pBuffer, &srs->rez, sizeof(Resurrect_Struct));
							srs->rez.fullGMRez = fullGMRez;
							client->QueuePacket(outapp);
							safe_delete(outapp);
						}
						//Yeahlight: The corpse owner answers 'no' to the request
						else if(srs->action == 0)
						{
							client->Message(BLACK, "You decline the request to be resurrected.");
							client->SetPendingRez(false);
							client->SetPendingRezExp(0);
						}
					}
				}
				break;
			}
		case ServerOP_Uptime: 
			{
				if (pack->size != sizeof(ServerUptime_Struct))
				{
					cout << "Wrong size on ServerOP_Uptime. Got: " << pack->size << ", Expected: " << sizeof(ServerUptime_Struct) << endl;
					break;
				}
				ServerUptime_Struct* sus = (ServerUptime_Struct*) pack->pBuffer;
				int32 ms = Timer::GetCurrentTime();
				int32 d = ms / 86400000;
				ms -= d * 86400000;
				int32 h = ms / 3600000;
				ms -= h * 3600000;
				int32 m = ms / 60000;
				ms -= m * 60000;
				int32 s = ms / 1000;
				if (d)
				{
					this->SendEmoteMessage(sus->adminname, 0, 0, "Zone #%i Uptime: %02id %02ih %02im %02is", sus->zoneserverid, d, h, m, s);
				}
				else if (h)
				{
					this->SendEmoteMessage(sus->adminname, 0, 0, "Zone #%i Uptime: %02ih %02im %02is", sus->zoneserverid, h, m, s);
				}
				else
				{
					this->SendEmoteMessage(sus->adminname, 0, 0, "Zone #%i Uptime: %02im %02is", sus->zoneserverid, m, s);
				}
				break;
			}
		case ServerOP_Petition:
			{
				cout << "Got Server Requested Petition List Refresh" << endl;
				ServerPetitionUpdate_Struct* sus = (ServerPetitionUpdate_Struct*) pack->pBuffer;
				if (sus->status = 0) 
				{
					petition_list.ReadDatabase();
				}

				else if (sus->status = 1)
				{
					petition_list.ReadDatabase(); // Until I fix this to be better....
				}
				break;
			}
		case ServerOP_RemoveBoat: // Tazadar (06/12/09) : We remove the boat from the zone 
			{
				BoatName_Struct* bs = (BoatName_Struct*) pack->pBuffer;
				
				cout << "Trying to remove the boat : " << bs->boatname << endl;
	
				Mob * tmp = entity_list.GetMob(bs->boatname);
				
				if(tmp){
					tmp->CastToNPC()->Depop(false);
					entity_list.RemoveNPC(tmp->CastToNPC());
				}

				break;
			}
		case ServerOP_ZoneBoat	: // Tazadar (06/16/09) : We teleport player to the other zone !
			{
				cout << "A boat is zoning ! Teleporting clients !" << endl;
				ZoneBoat_Struct * zb = (ZoneBoat_Struct *) pack->pBuffer;
				Entity * tmp = 0;
				Mob * boat = entity_list.GetMob(zb->boatname);
				float xboat,yboat,zboat,headingboat;
				if(boat){
					xboat = boat->GetX();
					yboat = boat->GetY();
					zboat = boat->GetZ();;
					headingboat = boat->GetHeading();
				}
				else{
					cerr << "Error in ServerOP_ZoneBoat boat : "<< zb->boatname << " does not exist."<<endl;
					break;
				}
				char  * clients = (char *) pack->pBuffer;
				char zone[16] = "";
				strcpy(zone, zb->zonename);
				char name[30];
				float x,y,z,heading;
				for(int i=0 ; i < zb->numberOfPlayers ; i++){
					memcpy(name,clients+sizeof(ZoneBoat_Struct)+30*i,30*sizeof(char));
					cout << "Trying to teleport : "<< name << endl;
					tmp = entity_list.GetClientByName(name);
					if(tmp != 0 && tmp->IsClient()){
						//cout << "ZonePC to " << zone << endl;

						Client * client = tmp->CastToClient();

						heading = client->GetHeading()-headingboat; // Tazadar : Relative heading from the boat
						z = client->GetZ()-zboat; // Tazadar : Relative z from the boat
						
						
						client->GetRelativeCoordToBoat(client->GetY()-yboat,client->GetX()-xboat,(zb->heading-headingboat)*1.4,y,x);
						client->SetZoningHeading(zb->heading+heading);
						client->SetUsingSoftCodedZoneLine(true);
						client->SetIsZoning(true);
						client->SetZoningX(zb->x+x);
						client->SetZoningY(zb->y+y);
						client->SetZoningZ(zb->z+z);
						client->ZonePC(zone,0,0,10);
					}
					else{ // Tazadar : Player has crashed ? We remove it from boat infos

						// Tazadar : Make the packet for the World Serv
						ServerPacket* pack = new ServerPacket(ServerOP_BoatPL, sizeof(ServerBoat_Struct));

						ServerBoat_Struct* servBoatInfos = (ServerBoat_Struct*) pack->pBuffer;

						// Tazadar : Fill the packet
						memcpy(servBoatInfos->player_name,name,sizeof(servBoatInfos->player_name));

						// Tazadar : Send the packet
						worldserver.SendPacket(pack);

					}
				}

				break;
			}
		case ServerOP_SpawnBoat: // Tazadar (06/13/09) : We make the boat spawn before the zone in at the correct location.
			{

				SpawnBoat_Struct * bs = (SpawnBoat_Struct *) pack->pBuffer; 
				
				Mob * tmp = 0;
				
				cout << "Spawning the boat :" << bs->boatname << "at loc " << bs->x <<","<< bs->y << "," << bs->z <<" heading " << bs->heading<<endl;
				//cout << "Loading boat from DB " << endl;
				string name = bs->boatname;
				name.resize(name.length()-2);
				NPCType boat;
				bool lineroute = false;
				Database::Instance()->LoadBoatData(name.c_str(),boat,lineroute);
				NPC* npc = new NPC(&boat, 0, bs->x, bs->y, bs->z, bs->heading);
				npc->SetLineRoute(lineroute);
				entity_list.AddNPC(npc);
				npc->SendPosUpdate(false);
				
				break;
			}

		case ServerOP_BoatGoTo :  // Tazadar (06/14/09) : We make the boat move
			{
				BoatGoTo_Struct * gt = (BoatGoTo_Struct *) pack->pBuffer;
				cout << "World orders " << gt->boatname << " to go to node number " << gt->toNode << endl;
				
				Mob * tmp = entity_list.GetMob(gt->boatname);
				if(tmp && tmp->IsNPC()){
					if(tmp->CastToNPC()->IsBoat()){
						tmp->CastToNPC()->setBoatDestinationNode(gt->fromNode,gt->toNode);
					}
					else{
						cerr << "Tried to give an order to the npc "<< gt->boatname <<" which is not a boat " << endl;
					}
				}
				else{
					cerr << "Error in ServerOP_BoatGoTo boat " << gt->boatname << " does not exist"<<endl;
				}

				break;
			}
		case ServerOP_DayTime : // Kibanu - 7/30/2009 : Switch to day time for spawn data
			{
				if (ZoneLoaded)
					zone->SetTimeOfDay(true);
				break;
			}
		case ServerOP_NightTime : // Kibanu - 7/30/2009 : Switch to day time for spawn data
			{
				if (ZoneLoaded)
					zone->SetTimeOfDay(false);
				break;
			}
		case ServerOP_ZoneToZoneRequest: 
			{
				if(pack->size != sizeof(ZoneToZone_Struct)) 
					break;
				if (!ZoneLoaded)
					break;
				ZoneToZone_Struct* ztz = (ZoneToZone_Struct*) pack->pBuffer;
			
				if(ztz->current_zone_id == zone->GetZoneID()) 
				{
					// it's a response
					Entity* entity = entity_list.GetClientByName(ztz->name);
					if(entity == 0)
						break;

					APPLAYER *outapp;
					outapp = new APPLAYER(OP_ZoneChange,sizeof(ZoneChange_Struct));
					ZoneChange_Struct* zc2=(ZoneChange_Struct*)outapp->pBuffer;

					if(ztz->response == 0 || ztz->response == -1) 
					{
						zc2->success = ZONE_ERROR_NOTREADY;
						entity->CastToMob()->SetZone(ztz->current_zone_id);
					}
					else 
					{
						strncpy(zc2->char_name,entity->CastToMob()->GetName(),64);
						zc2->zoneID=ztz->requested_zone_id;
						zc2->success = 1;
					}
					entity->CastToClient()->QueuePacket(outapp);
					delete outapp;

					switch(ztz->response)
					{
						case -1: 
						{
							entity->CastToMob()->Message(RED,"The zone is currently full, please try again later.");
							break;
						}
						case 0:	
						{
							entity->CastToMob()->Message(RED,"All zone servers are taken at this time, please try again later.");
							break;
						}
					}
				}
				else 
				{
					// it's a request
					if(zone->GetMaxClients() != 0 && numclients >= zone->GetMaxClients())
						ztz->response = -1;
					else 
					{
						ztz->response = 1;
						// since they asked about coming, lets assume they are on their way and not shut down.
						zone->StartShutdownTimer(AUTHENTICATION_TIMEOUT * 1000);
					}
					SendPacket(pack);
					break;
				}
			break;
		}
			default:
			{
				cout << "Unknown ZSopcode:" << (int)pack->opcode;
				cout << "size:" << pack->size << endl;
				//DumpPacket(pack->pBuffer, pack->size);
				break;
			}
		}

		safe_delete(pack);//delete pack;
		//Yeahlight: Zone freeze debug
		if(ZONE_FREEZE_DEBUG && rand()%ZONE_FREEZE_DEBUG == 1)
			EQC_FREEZE_DEBUG(__LINE__, __FILE__);
	}
	return;
}