diff --git a/src/d_clisrv.c b/src/d_clisrv.c
index f949777f24a221a1f9798ecea017302ddb3fd8a6..e982400e330c4d7e6667d5ab6ae652ef01577c3d 100755
--- a/src/d_clisrv.c
+++ b/src/d_clisrv.c
@@ -5044,7 +5044,7 @@ int recommendedSimulateTics = 0;
 int smoothingDelay;
 precise_t saveStateBenchmark = 0;
 precise_t loadStateBenchmark = 0;
-int netUpdateFudge; // our last net update fudge
+double netUpdateFudge; // our last net update fudge
 
 tic_t SavestatesClearedTic;
 
@@ -5077,6 +5077,10 @@ void TryRunTics(tic_t realtics, tic_t entertic)
 			D_MapChange(-1, 0, ultimatemode, false, 2, false, fromlevelselect); // finish the map change
 	}
 
+	//TODO: remove these 1000000s for 2.2.9/next
+	double frame = ((double)SDL_GetPerformanceCounter() / tic_frequency);
+	netUpdateFudge = (((double)SDL_GetPerformanceCounter() / tic_frequency) - frame); // record the timefudge where the net update typically occurs
+
 	NetUpdate();
 
 	if (demoplayback)
diff --git a/src/d_netcmd.c b/src/d_netcmd.c
index 0956e2df0c30fba8478650a21369cf1bb47c38fb..752175111d43a579912056a990181377d1951b93 100644
--- a/src/d_netcmd.c
+++ b/src/d_netcmd.c
@@ -671,41 +671,39 @@ void D_RegisterServerCommands(void)
 
 #include "i_net.h"
 
-extern int netUpdateFudge;
+extern double netUpdateFudge;
 void Command_Autotimefudge(void)
 {
-	UINT64 startTime = I_GetTimeUs();
-	static UINT64 packetTimeFudge[512];
+	// you can use SDL_GetPerformanceFrequency() instead of tic_frequency to get more precise timings
+	double startTime = (double)SDL_GetPerformanceCounter() / tic_frequency;
+	UINT8 packetTimeFudge[64];
 	int numReceivedPackets = 0;
-	int numSampleTics = 14;
+	const double numSampleTics = 10;
 	int i;
 
-	if (server)
+	if (server && netgame)
 	{
-		if (netgame)
-		{
-			CONS_Printf("Servers do not need a time fudge! Heck, why are you hosting with this exe anyway? You don't need to ;)\n");
-		}
+		CONS_Printf("Servers do not need a time fudge!\n");
 		return;
 	}
 
-	// New experimental version! Run a precise while loop that picks up packets instantly
-	while (I_GetTimeUs() - startTime < ((UINT64)numSampleTics * 1000000 / NEWTICRATE))
+	while ((abs((double)SDL_GetPerformanceCounter() / tic_frequency - startTime) < numSampleTics) || numReceivedPackets < 10)
 	{
+		double now = (double)SDL_GetPerformanceCounter() / tic_frequency;
 		I_NetGet();
-		if (doomcom->remotenode != -1 && I_GetTimeUs() - startTime > (unsigned long long)2*1000000/NEWTICRATE) // wait a couple frames before recording
+		if ((doomcom->remotenode != -1))
 		{
-			unsigned long long frame = I_GetTimeUs() * NEWTICRATE / 1000000;
-			packetTimeFudge[numReceivedPackets++] = (I_GetTimeUs() - frame * 1000000 / NEWTICRATE) * 100 * NEWTICRATE / 1000000
-				- netUpdateFudge; // gets the time fudge offset (0-100)
+			packetTimeFudge[numReceivedPackets] = 100 * (UINT8)(abs((SDL_GetPerformanceCounter() / tic_frequency - now) - netUpdateFudge)); // gets the time fudge offset (0-100)
+			numReceivedPackets++;
 		}
 	}
 
 	if (numReceivedPackets > 0)
 	{
-		int minOffset = 100, maxOffset = 0, averageOffset = 0;
-		int newTimeFudge;
-		int estimatedRange;
+		UINT8 minOffset = 100, maxOffset = 0, averageOffset = 0;
+		UINT8 newTimeFudge;
+		UINT8 estimatedRange;
+
 
 		for (i = 0; i < numReceivedPackets; i++)
 		{
@@ -729,9 +727,15 @@ void Command_Autotimefudge(void)
 		estimatedRange = maxOffset - minOffset;
 		averageOffset = (maxOffset + minOffset) / 2;
 
-		CONS_Printf("%i packets, min: %d max: %d avg: %d est. range: %d (mynetupdate: %i)\n", numReceivedPackets, minOffset, maxOffset, averageOffset,
+		CONS_Printf("%i packets received\n Timer fluctuations:\nmin: %d max: %d avg: %d est. range: %d (local timer update: %lf)\n", numReceivedPackets, minOffset, maxOffset, averageOffset,
 			estimatedRange, netUpdateFudge);
 
+		if (averageOffset <= 0)
+		{
+			CONS_Printf("Timers are OK, no time fudging required\n");
+			return;
+		}
+
 		newTimeFudge = (cv_timefudge.value + averageOffset + 50) % 100;
 		CONS_Printf("New time fudge: %i%%\n", newTimeFudge);
 
diff --git a/src/i_system.h b/src/i_system.h
index 452a7b12183dd06d06cadc53c2b486c3c085d671..c4197832ea6d274d9d4669de63cd07d16b4bebc9 100644
--- a/src/i_system.h
+++ b/src/i_system.h
@@ -25,6 +25,8 @@
 */
 #define MAX_QUIT_FUNCS     16
 
+extern double tic_frequency;
+extern double elapsed;
 
 /**	\brief Graphic system had started up
 */
diff --git a/src/sdl/i_system.c b/src/sdl/i_system.c
index 47717ab3f12cddd8f5efbd2981a3bac262dc989e..4e6b30d2a88d1e2a80512c135827d5c40dcc5dfe 100755
--- a/src/sdl/i_system.c
+++ b/src/sdl/i_system.c
@@ -2151,11 +2151,11 @@ void I_StartupTimer(void)
 
 static Uint64 timer_frequency;
 
-static double tic_frequency;
+double tic_frequency;
 static Uint64 tic_epoch;
 
 int8_t lastTimeFudge = 0;
-static double elapsed;
+double elapsed;
 
 tic_t I_GetTime(void)
 {