فهرست منبع

* small timer.c cleaning
- removed "with less than 4 values, it's speedier to use a simple loop" as this case will never occur (premature optimization from r1284)

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

ultramage 17 سال پیش
والد
کامیت
6b2c679c3f
3فایلهای تغییر یافته به همراه61 افزوده شده و 100 حذف شده
  1. 4 0
      Changelog-Trunk.txt
  2. 53 85
      src/common/timer.c
  3. 4 15
      src/common/timer.h

+ 4 - 0
Changelog-Trunk.txt

@@ -3,6 +3,10 @@ Date	Added
 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.
 
+2007/10/17
+	* small timer.c cleaning
+	- removed "with less than 4 values, it's speedier to use a simple loop"
+	  as this case will never occur (premature optimization from r1284)
 2007/10/16
 	* Venom Splasher fixes according to bugreport:230
 	- added passive skillv*30% bonus from Poison React

+ 53 - 85
src/common/timer.c

@@ -1,29 +1,20 @@
 // Copyright (c) Athena Dev Teams - Licensed under GNU GPL
 // For more information, see LICENCE in the main folder
 
-#include <sys/types.h>
-
 #include "../common/cbasetypes.h"
 #include "../common/malloc.h"
 #include "../common/showmsg.h"
 #include "timer.h"
 
-#ifdef WIN32
-//#define __USE_W32_SOCKETS
-// Well, this won't last another 30++ years (where conversion will truncate).
-//#define _USE_32BIT_TIME_T	// use 32 bit time variables on 64bit windows
-//#include <windows.h>
-#include <winsock2.h>
-#else
-#include <sys/socket.h>
-#include <sys/time.h>
-#endif
-
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
 #include <time.h>
 
+#ifdef WIN32
+#include <windows.h> // GetTickCount()
+#endif
+
 // タイマー間隔の最小値。モンスターの大量召還時、多数のクライアント接続時に
 // サーバーが反応しなくなる場合は、TIMER_MIN_INTERVAL を増やしてください。
 
@@ -47,20 +38,6 @@ static int free_timer_list_pos	= 0;
 static int timer_heap_num = 0;
 static int timer_heap_max = 0;
 static int* timer_heap = NULL;
-// searches for the target tick's position and stores it in pos (binary search)
-#define HEAP_SEARCH(target,from,to,pos) \
-	do { \
-		int max,pivot; \
-		pos = from; \
-		max = to; \
-		while (pos < max) { \
-			pivot = (pos + max) / 2; \
-			if (DIFF_TICK(target, timer_data[timer_heap[pivot]].tick) < 0) \
-				pos = pivot + 1; \
-			else \
-				max = pivot; \
-		} \
-	} while(0)
 
 // for debug
 struct timer_func_list {
@@ -70,6 +47,7 @@ struct timer_func_list {
 };
 static struct timer_func_list* tfl_root = NULL;
 
+// server startup time
 time_t start_time;
 
 /// Sets the name of a timer function.
@@ -110,48 +88,48 @@ char* search_timer_func_list(TimerFunc func)
  * 	Get tick time
  *----------------------------*/
 
+/// platform-abstracted tick retrieval
+static unsigned int tick(void)
+{
+#ifdef WIN32
+	return GetTickCount();
+#else
+	struct timeval tval;
+	gettimeofday(&tval, NULL);
+	return tval.tv_sec * 1000 + tval.tv_usec / 1000;
+#endif
+}
+
 //////////////////////////////////////////////////////////////////////////
 #if defined(TICK_CACHE) && TICK_CACHE > 1
 //////////////////////////////////////////////////////////////////////////
 // tick is cached for TICK_CACHE calls
 static unsigned int gettick_cache;
-static int gettick_count;
+static int gettick_count = 1;
 
 unsigned int gettick_nocache(void)
 {
-#ifdef WIN32
 	gettick_count = TICK_CACHE;
-	return gettick_cache = GetTickCount();
-#else
-	struct timeval tval;
-
-	gettimeofday(&tval, NULL);
-	gettick_count = TICK_CACHE;
-
-	return gettick_cache = tval.tv_sec * 1000 + tval.tv_usec / 1000;
-#endif
+	gettick_cache = tick();
+	return gettick_cache;
 }
 
 unsigned int gettick(void)
 {
-	if (--gettick_count < 0)
-		return gettick_nocache();
-
-	return gettick_cache;
+	return ( --gettick_count == 0 ) ? gettick_nocache() : gettick_cache;
 }
 //////////////////////////////
 #else
 //////////////////////////////
 // tick doesn't get cached
+unsigned int gettick_nocache(void)
+{
+	return tick();
+}
+
 unsigned int gettick(void)
 {
-#ifdef WIN32
-	return GetTickCount();
-#else
-	struct timeval tval;
-	gettimeofday(&tval, NULL);
-	return tval.tv_sec * 1000 + tval.tv_usec / 1000;
-#endif
+	return tick();
 }
 //////////////////////////////////////////////////////////////////////////
 #endif
@@ -160,12 +138,26 @@ unsigned int gettick(void)
 /*======================================
  * 	CORE : Timer Heap
  *--------------------------------------*/
+
+// searches for the target tick's position and stores it in pos (binary search)
+#define HEAP_SEARCH(target,from,to,pos) \
+	do { \
+		int max,pivot; \
+		pos = from; \
+		max = to; \
+		while (pos < max) { \
+			pivot = (pos + max) / 2; \
+			if (DIFF_TICK(target, timer_data[timer_heap[pivot]].tick) < 0) \
+				pos = pivot + 1; \
+			else \
+				max = pivot; \
+		} \
+	} while(0)
+
 /// Adds a timer to the timer_heap
 static void push_timer_heap(int tid)
 {
-	unsigned int tick;
 	int pos;
-	int i;
 
 	// check number of element
 	if (timer_heap_num >= timer_heap_max) {
@@ -180,37 +172,16 @@ static void push_timer_heap(int tid)
 	}
 
 	// do a sorting from higher to lower
-	tick = timer_data[tid].tick; // speed up
-	// with less than 4 values, it's speeder to use simple loop
-	if (timer_heap_num < 4) {
-		for(i = timer_heap_num; i > 0; i--)
-		{
-//			if (j < timer_data[timer_heap[i - 1]].tick) //Plain comparisons break on bound looping timers. [Skotlex]
-			if (DIFF_TICK(tick, timer_data[timer_heap[i - 1]].tick) < 0)
-				break;
-			else
-				timer_heap[i] = timer_heap[i - 1];
-		}
-		timer_heap[i] = tid;
-	// searching by dichotomy (binary search)
-	} else {
-		// if lower actual item is higher than new
-//		if (j < timer_data[timer_heap[timer_heap_num - 1]].tick) //Plain comparisons break on bound looping timers. [Skotlex]
-		if (DIFF_TICK(tick, timer_data[timer_heap[timer_heap_num - 1]].tick) < 0)
-			timer_heap[timer_heap_num] = tid;
-		else {
-			// searching position
-			HEAP_SEARCH(tick,0,timer_heap_num-1,pos);
-			// move elements - do loop if there are a little number of elements to move
-			if (timer_heap_num - pos < 5) {
-				for(i = timer_heap_num; i > pos; i--)
-					timer_heap[i] = timer_heap[i - 1];
-			// move elements - else use memmove (speeder for a lot of elements)
-			} else
-				memmove(&timer_heap[pos + 1], &timer_heap[pos], sizeof(int) * (timer_heap_num - pos));
-			// save new element
-			timer_heap[pos] = tid;
-		}
+	if( timer_heap_num == 0 || DIFF_TICK(timer_data[tid].tick, timer_data[timer_heap[timer_heap_num - 1]].tick) < 0 )
+		timer_heap[timer_heap_num] = tid; // if lower actual item is higher than new
+	else
+	{
+		// searching position
+		HEAP_SEARCH(timer_data[tid].tick,0,timer_heap_num-1,pos);
+		// move elements
+		memmove(&timer_heap[pos + 1], &timer_heap[pos], sizeof(int) * (timer_heap_num - pos));
+		// save new element
+		timer_heap[pos] = tid;
 	}
 
 	timer_heap_num++;
@@ -328,9 +299,6 @@ int settick_timer(int tid, unsigned int tick)
 	if( old_tick == tick )
 		return tick;
 
-	//FIXME: This search is not all that effective... there doesn't seems to be a better way to locate an element in the heap.
-	//for(i = timer_heap_num-1; i >= 0 && timer_heap[i] != tid; i--);
-
 	// search old_tick position
 	HEAP_SEARCH(old_tick,0,timer_heap_num-1,old_pos);
 	while( timer_heap[old_pos] != tid )

+ 4 - 15
src/common/timer.h

@@ -8,18 +8,11 @@
 #include "../common/cbasetypes.h"
 #endif
 
-#ifdef WIN32
-/* We need winsock lib to have timeval struct - windows is weirdo */
-//#define __USE_W32_SOCKETS
-//#include <windows.h>
-#include <winsock2.h>
-#endif
-
 #define BASE_TICK 5
 
-#define TIMER_ONCE_AUTODEL 0x1
-#define TIMER_INTERVAL 0x2
-#define TIMER_REMOVE_HEAP 0x10
+#define TIMER_ONCE_AUTODEL 0x01
+#define TIMER_INTERVAL     0x02
+#define TIMER_REMOVE_HEAP  0x10
 
 #define DIFF_TICK(a,b) ((int)((a)-(b)))
 
@@ -41,12 +34,8 @@ struct TimerData {
 
 // Function prototype declaration
 
-#if defined(TICK_CACHE) && TICK_CACHE > 1
-unsigned int gettick_nocache(void);
-#else
-#define gettick_nocache gettick
-#endif
 unsigned int gettick(void);
+unsigned int gettick_nocache(void);
 
 int add_timer(unsigned int,TimerFunc f,int,int);
 int add_timer_interval(unsigned int tick, TimerFunc func, int id, int data, int interval);