ソースを参照

crash fix with CastProc on dead spell ptr

Fix #186
image 4 年 前
コミット
b908936a6e
2 ファイル変更14 行追加1 行削除
  1. 3 1
      EQ2/source/WorldServer/Combat.cpp
  2. 11 0
      EQ2/source/WorldServer/LuaInterface.cpp

+ 3 - 1
EQ2/source/WorldServer/Combat.cpp

@@ -1387,6 +1387,7 @@ void Entity::CheckProcs(int8 type, Spawn* target) {
 			tmpProc->chance = proc->chance;
 			tmpProc->item = proc->item;
 			tmpProc->spell = proc->spell;
+			tmpProc->spellid = proc->spellid;
 			tmpList.push_back(tmpProc);
 		}
 	}
@@ -1394,9 +1395,10 @@ void Entity::CheckProcs(int8 type, Spawn* target) {
 
 
 	vector<Proc*>::iterator proc_itr;
-	for (proc_itr = tmpList.begin(); proc_itr != tmpList.end(); proc_itr++) {
+	for (proc_itr = tmpList.begin(); proc_itr != tmpList.end();) {
 		Proc* tmpProc = *proc_itr;
 		CastProc(tmpProc, type, target);
+		proc_itr++;
 		safe_delete(tmpProc);
 	}
 }

+ 11 - 0
EQ2/source/WorldServer/LuaInterface.cpp

@@ -633,6 +633,17 @@ void LuaInterface::RemoveSpell(LuaSpell* spell, bool call_remove_function, bool
 		MSpells.unlock();
 		lua_pcall(spell->state, 2, 0, 0);
 	}
+
+	spell->MSpellTargets.readlock(__FUNCTION__, __LINE__);
+	for (int8 i = 0; i < spell->targets.size(); i++) {
+		Spawn* target = spell->caster->GetZone()->GetSpawnByID(spell->targets.at(i));
+		if (!target || !target->IsEntity())
+			continue;
+
+		((Entity*)target)->RemoveProc(0, spell);
+	}
+	spell->MSpellTargets.releasereadlock(__FUNCTION__, __LINE__);
+
 	if (can_delete) {
 		AddPendingSpellDelete(spell);
 	}