Browse Source

* Simplified the search in pop_timer_heap and added more debug info to help determine the source condition of timer errors. (bugreport:1860)
* Fixed crash in skill_castend_id. (bugreport:1860)

git-svn-id: https://svn.code.sf.net/p/rathena/svn/trunk@12968 54d463be-8e91-2dee-dedb-b68131a5f0ec

FlavioJS 17 years ago
parent
commit
99a1aaa9e1
3 changed files with 36 additions and 11 deletions
  1. 4 1
      Changelog-Trunk.txt
  2. 15 6
      src/common/timer.c
  3. 17 4
      src/map/skill.c

+ 4 - 1
Changelog-Trunk.txt

@@ -3,7 +3,10 @@ Date	Added
 AS OF SVN REV. 5091, WE ARE NOW USING TRUNK.  ALL UNTESTED BUGFIXES/FEATURES GO INTO TRUNK.
 AS OF SVN REV. 5091, WE ARE NOW USING TRUNK.  ALL UNTESTED BUGFIXES/FEATURES GO INTO TRUNK.
 IF YOU HAVE A WORKING AND TESTED BUGFIX PUT IT INTO STABLE AS WELL AS TRUNK.
 IF YOU HAVE A WORKING AND TESTED BUGFIX PUT IT INTO STABLE AS WELL AS TRUNK.
 
 
-2008/07/16
+2008/07/20
+	* Simplified the search in pop_timer_heap and added more debug info to help 
+	  determine the source condition of timer errors. (bugreport:1860)
+	* Fixed crash in skill_castend_id. (bugreport:1860) [FlavioJS]
 	* Corrected #storagelist target typo (bugreport:1873) [SketchyPhoenix]
 	* Corrected #storagelist target typo (bugreport:1873) [SketchyPhoenix]
 	
 	
 2008/07/16
 2008/07/16

+ 15 - 6
src/common/timer.c

@@ -4,6 +4,7 @@
 #include "../common/cbasetypes.h"
 #include "../common/cbasetypes.h"
 #include "../common/malloc.h"
 #include "../common/malloc.h"
 #include "../common/showmsg.h"
 #include "../common/showmsg.h"
+#include "../common/db.h"
 #include "timer.h"
 #include "timer.h"
 
 
 #include <stdio.h>
 #include <stdio.h>
@@ -145,6 +146,7 @@ unsigned int gettick(void)
  * 	CORE : Timer Heap
  * 	CORE : Timer Heap
  *--------------------------------------*/
  *--------------------------------------*/
 
 
+// root at index 0
 #define BHEAP_PARENT(pos) ( ((pos) - 1)/2 )
 #define BHEAP_PARENT(pos) ( ((pos) - 1)/2 )
 #define BHEAP_LEFT(pos)   ( (pos)*2 + 1   )
 #define BHEAP_LEFT(pos)   ( (pos)*2 + 1   )
 #define BHEAP_RIGHT(pos)  ( (pos)*2 + 2   )
 #define BHEAP_RIGHT(pos)  ( (pos)*2 + 2   )
@@ -166,7 +168,7 @@ void push_timer_heap(int tid)
 		memset(timer_heap + (timer_heap_max - 256), 0, sizeof(int)*256);
 		memset(timer_heap + (timer_heap_max - 256), 0, sizeof(int)*256);
 	}
 	}
 
 
-	// add the timer
+	// add the timer at the end
 	pos = timer_heap_num++;
 	pos = timer_heap_num++;
 	timer_heap[pos] = tid;
 	timer_heap[pos] = tid;
 	// restore binary heap properties
 	// restore binary heap properties
@@ -187,6 +189,10 @@ bool pop_timer_heap(int tid)
 	int pos;
 	int pos;
 
 
 	// find the timer
 	// find the timer
+#if 1
+	// trying a simple array search
+	ARR_FIND(0, timer_heap_num, pos, timer_heap[pos] == tid);
+#else
 	pos = 0;
 	pos = 0;
 	while( pos < timer_heap_num )
 	while( pos < timer_heap_num )
 	{// search in the order current-left-right
 	{// search in the order current-left-right
@@ -220,10 +226,11 @@ bool pop_timer_heap(int tid)
 		}
 		}
 		pos = right;
 		pos = right;
 	}
 	}
+#endif
 	if( pos >= timer_heap_num )
 	if( pos >= timer_heap_num )
 		return false;// not found
 		return false;// not found
 
 
-	// remove timer
+	// remove timer (replace with last one)
 	timer_heap[pos] = timer_heap[--timer_heap_num];
 	timer_heap[pos] = timer_heap[--timer_heap_num];
 	// restore binary heap properties
 	// restore binary heap properties
 	while( pos < timer_heap_num )
 	while( pos < timer_heap_num )
@@ -231,9 +238,9 @@ bool pop_timer_heap(int tid)
 		int left = BHEAP_LEFT(pos);
 		int left = BHEAP_LEFT(pos);
 		int right = BHEAP_RIGHT(pos);
 		int right = BHEAP_RIGHT(pos);
 		if( left < timer_heap_num && DIFF_TICK(timer_data[timer_heap[pos]].tick, timer_data[timer_heap[left]].tick) > 0 )
 		if( left < timer_heap_num && DIFF_TICK(timer_data[timer_heap[pos]].tick, timer_data[timer_heap[left]].tick) > 0 )
-		{
+		{// left exists and has smaller tick
 			if( right < timer_heap_num && DIFF_TICK(timer_data[timer_heap[left]].tick, timer_data[timer_heap[right]].tick) > 0 )	
 			if( right < timer_heap_num && DIFF_TICK(timer_data[timer_heap[left]].tick, timer_data[timer_heap[right]].tick) > 0 )	
-			{
+			{// right exists and has even smaller tick
 				swap(timer_heap[pos], timer_heap[right]);
 				swap(timer_heap[pos], timer_heap[right]);
 				pos = right;
 				pos = right;
 			}
 			}
@@ -244,7 +251,7 @@ bool pop_timer_heap(int tid)
 			}
 			}
 		}
 		}
 		else if( right < timer_heap_num && DIFF_TICK(timer_data[timer_heap[pos]].tick, timer_data[timer_heap[right]].tick) > 0 )
 		else if( right < timer_heap_num && DIFF_TICK(timer_data[timer_heap[pos]].tick, timer_data[timer_heap[right]].tick) > 0 )
-		{
+		{// right exists and has smaller tick
 			swap(timer_heap[pos], timer_heap[right]);
 			swap(timer_heap[pos], timer_heap[right]);
 			pos = right;
 			pos = right;
 		}
 		}
@@ -429,6 +436,8 @@ int delete_timer(int tid, TimerFunc func)
 		timer_data[tid].type = TIMER_FORCE_REMOVE|TIMER_REMOVE_HEAP;
 		timer_data[tid].type = TIMER_FORCE_REMOVE|TIMER_REMOVE_HEAP;
 	else if( pop_timer_heap(tid) )
 	else if( pop_timer_heap(tid) )
 		release_timer(tid);
 		release_timer(tid);
+	else if( (timer_data[tid].type|TIMER_REMOVE_HEAP) == 0 )
+		ShowDebug("delete_timer: failed to remove timer %d (%08x(%s), type=%d)\n", tid, (int)func, search_timer_func_list(func), timer_data[tid].type);
 	return 0;
 	return 0;
 }
 }
 
 
@@ -474,7 +483,7 @@ int do_timer(unsigned int tick)
 	// process all timers one by one
 	// process all timers one by one
 	while( timer_heap_num )
 	while( timer_heap_num )
 	{
 	{
-		int tid = timer_heap[0]; // first element in heap (=>smallest)
+		int tid = timer_heap[0]; // first element in heap (smallest tick)
 
 
 		diff = DIFF_TICK(timer_data[tid].tick, tick);
 		diff = DIFF_TICK(timer_data[tid].tick, tick);
 		if( diff > 0 )
 		if( diff > 0 )

+ 17 - 4
src/map/skill.c

@@ -5216,15 +5216,28 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, in
  *------------------------------------------*/
  *------------------------------------------*/
 int skill_castend_id(int tid, unsigned int tick, int id, intptr data)
 int skill_castend_id(int tid, unsigned int tick, int id, intptr data)
 {
 {
-	struct block_list *target, *src = map_id2bl(id);
+	struct block_list* target = NULL;
+	struct block_list* src = NULL;
 	struct map_session_data* sd = NULL;
 	struct map_session_data* sd = NULL;
 	struct homun_data* hd = NULL;	//[orn]
 	struct homun_data* hd = NULL;	//[orn]
 	struct mob_data* md = NULL;
 	struct mob_data* md = NULL;
-	struct unit_data* ud = unit_bl2ud(src);
-	struct status_change *sc = NULL;
+	struct unit_data* ud = NULL;
+	struct status_change* sc = NULL;
 	int inf,inf2,flag=0;
 	int inf,inf2,flag=0;
 
 
-	nullpo_retr(0, ud);
+	src = map_id2bl(id);
+	if( src == NULL )
+	{
+		ShowDebug("skill_castend_id: src == NULL (tid=%d, id=%d)\n", tid, id);
+		return 0;// not found
+	}
+
+	ud = unit_bl2ud(src);
+	if( ud == NULL )
+	{
+		ShowDebug("skill_castend_id: ud == NULL (tid=%d, id=%d)\n", tid, id);
+		return 0;// ???
+	}
 
 
 	sd = BL_CAST(BL_PC,  src);
 	sd = BL_CAST(BL_PC,  src);
 	hd = BL_CAST(BL_HOM, src);
 	hd = BL_CAST(BL_HOM, src);