From 738f94eed3a8e2b1c1659e0e973cfe3d4b28cfcb Mon Sep 17 00:00:00 2001 From: megamage Date: Wed, 21 Sep 2011 12:53:29 -0400 Subject: [PATCH 1/3] Fix incorrect logic in PetAI. Solve #3155. --- src/server/game/AI/CoreAI/PetAI.cpp | 40 ++++++++++------------------- 1 file changed, 14 insertions(+), 26 deletions(-) diff --git a/src/server/game/AI/CoreAI/PetAI.cpp b/src/server/game/AI/CoreAI/PetAI.cpp index 442da862b8..5a0c199a4c 100755 --- a/src/server/game/AI/CoreAI/PetAI.cpp +++ b/src/server/game/AI/CoreAI/PetAI.cpp @@ -141,13 +141,8 @@ void PetAI::UpdateAI(const uint32 diff) if (me->GetCharmInfo() && me->GetCharmInfo()->GetGlobalCooldownMgr().HasGlobalCooldown(spellInfo)) continue; - // ignore some combinations of combat state and combat/noncombat spells - if (!me->getVictim()) + if (spellInfo->IsPositive()) { - // ignore attacking spells, and allow only self/around spells - if (!spellInfo->IsPositive()) - continue; - // non combat spells allowed // only pet spells have IsNonCombatSpell and not fit this reqs: // Consume Shadows, Lesser Invisibility, so ignore checks for its @@ -163,36 +158,21 @@ void PetAI::UpdateAI(const uint32 diff) if (cooldown >= 0 && duration >= 0 && cooldown > duration) continue; } - } - else - { - // just ignore non-combat spells - if (!spellInfo->CanBeUsedInCombat()) - continue; - } - Spell* spell = new Spell(me, spellInfo, TRIGGERED_NONE, 0); + Spell* spell = new Spell(me, spellInfo, TRIGGERED_NONE, 0); - // Fix to allow pets on STAY to autocast - if (me->getVictim() && _CanAttack(me->getVictim()) && spell->CanAutoCast(me->getVictim())) - { - targetSpellStore.push_back(std::make_pair(me->getVictim(), spell)); - continue; - } - else - { bool spellUsed = false; for (std::set::const_iterator tar = m_AllySet.begin(); tar != m_AllySet.end(); ++tar) { - Unit* Target = ObjectAccessor::GetUnit(*me, *tar); + Unit* target = ObjectAccessor::GetUnit(*me, *tar); //only buff targets that are in combat, unless the spell can only be cast while out of combat - if (!Target) + if (!target) continue; - if (spell->CanAutoCast(Target)) + if (spell->CanAutoCast(target)) { - targetSpellStore.push_back(std::make_pair(Target, spell)); + targetSpellStore.push_back(std::make_pair(target, spell)); spellUsed = true; break; } @@ -200,6 +180,14 @@ void PetAI::UpdateAI(const uint32 diff) if (!spellUsed) delete spell; } + else if (me->getVictim() && _CanAttack(me->getVictim()) && spellInfo->CanBeUsedInCombat()) + { + Spell* spell = new Spell(me, spellInfo, TRIGGERED_NONE, 0); + if (spell->CanAutoCast(me->getVictim())) + targetSpellStore.push_back(std::make_pair(me->getVictim(), spell)); + else + delete spell; + } } //found units to cast on to From a35deba186bef436e68750d6c4f621cdc34c8a24 Mon Sep 17 00:00:00 2001 From: megamage Date: Mon, 26 Sep 2011 09:03:33 -0400 Subject: [PATCH 2/3] Fix some crashes caused by spell scripts without checking unit type. Fix #3216 and #3217. --- .../scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp | 10 +++++----- src/server/scripts/Spells/spell_dk.cpp | 6 +++--- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/server/scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp b/src/server/scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp index 7d355b2f71..dcb5ae8faf 100644 --- a/src/server/scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp +++ b/src/server/scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp @@ -237,12 +237,12 @@ class spell_intense_cold : public SpellScriptLoader void HandlePeriodicTick(AuraEffect const* aurEff) { - Unit* caster = GetCaster(); - if (!caster) + if (aurEff->GetBase()->GetStackAmount() < 2) return; - - if (aurEff->GetBase()->GetStackAmount() >= 2) - caster->GetAI()->SetGUID(GetTarget()->GetGUID(), DATA_INTENSE_COLD); + Unit* caster = GetCaster(); + if (!caster || !caster->GetAI()) + return; + caster->GetAI()->SetGUID(GetTarget()->GetGUID(), DATA_INTENSE_COLD); } void Register() diff --git a/src/server/scripts/Spells/spell_dk.cpp b/src/server/scripts/Spells/spell_dk.cpp index 98faef9e00..fc1b73df48 100644 --- a/src/server/scripts/Spells/spell_dk.cpp +++ b/src/server/scripts/Spells/spell_dk.cpp @@ -167,9 +167,9 @@ class spell_dk_anti_magic_zone : public SpellScriptLoader { SpellInfo const* talentSpell = sSpellMgr->GetSpellInfo(DK_SPELL_ANTI_MAGIC_SHELL_TALENT); amount = talentSpell->Effects[EFFECT_0].CalcValue(GetCaster()); - // assume caster is a player here - if (Unit* caster = GetCaster()) - amount += int32(2 * caster->ToPlayer()->GetTotalAttackPowerValue(BASE_ATTACK)); + Unit* caster = GetCaster(); + if(Player* player = caster->ToPlayer()) + amount += int32(2 * player->GetTotalAttackPowerValue(BASE_ATTACK)); } void Absorb(AuraEffect* /*aurEff*/, DamageInfo & dmgInfo, uint32 & absorbAmount) From 780747f5d39cd05e22d28f80eed7eda18453e0b8 Mon Sep 17 00:00:00 2001 From: megamage Date: Mon, 26 Sep 2011 09:14:12 -0400 Subject: [PATCH 3/3] Missing part of the previous commit. --- src/server/scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp | 1 + src/server/scripts/Spells/spell_dk.cpp | 2 ++ 2 files changed, 3 insertions(+) diff --git a/src/server/scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp b/src/server/scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp index dcb5ae8faf..1a15347441 100644 --- a/src/server/scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp +++ b/src/server/scripts/Northrend/Nexus/Nexus/boss_keristrasza.cpp @@ -240,6 +240,7 @@ class spell_intense_cold : public SpellScriptLoader if (aurEff->GetBase()->GetStackAmount() < 2) return; Unit* caster = GetCaster(); + //TODO: the caster should be boss but not the player if (!caster || !caster->GetAI()) return; caster->GetAI()->SetGUID(GetTarget()->GetGUID(), DATA_INTENSE_COLD); diff --git a/src/server/scripts/Spells/spell_dk.cpp b/src/server/scripts/Spells/spell_dk.cpp index fc1b73df48..5e08a8ae2e 100644 --- a/src/server/scripts/Spells/spell_dk.cpp +++ b/src/server/scripts/Spells/spell_dk.cpp @@ -168,6 +168,8 @@ class spell_dk_anti_magic_zone : public SpellScriptLoader SpellInfo const* talentSpell = sSpellMgr->GetSpellInfo(DK_SPELL_ANTI_MAGIC_SHELL_TALENT); amount = talentSpell->Effects[EFFECT_0].CalcValue(GetCaster()); Unit* caster = GetCaster(); + if(!caster) + return; if(Player* player = caster->ToPlayer()) amount += int32(2 * player->GetTotalAttackPowerValue(BASE_ATTACK)); }