From 6abcf7283ecc495023ce700c1028611649b718bd Mon Sep 17 00:00:00 2001
From: Nicholas Hastings <skamonkey@gmail.com>
Date: Wed, 31 Jul 2013 06:49:21 -0400
Subject: [PATCH] Split TF2, DoD:S, HL2:DM, and ND to separate binaries (bug
 5667, r=asherkin).

---
 AMBuildScript                  | 45 ++++++++++++++++++++--------------
 core/ISmmPluginExt.h           |  6 ++++-
 core/metamod_console.cpp       | 12 ++++++---
 core/metamod_plugins.cpp       | 11 ++++++---
 core/provider/provider_ep2.cpp | 10 ++++++--
 loader/loader.cpp              | 25 ++++++++++++++++---
 loader/loader.h                |  6 ++++-
 loader/serverplugin.cpp        |  8 ++++--
 8 files changed, 90 insertions(+), 33 deletions(-)

diff --git a/AMBuildScript b/AMBuildScript
index 9874c33..52a4b47 100644
--- a/AMBuildScript
+++ b/AMBuildScript
@@ -15,37 +15,46 @@ class MMS:
 		self.possibleSdks['ep2'] =   {'sdk': 'HL2SDKOB',        'ext': '2.ep2',   'def': '3',
 		                         'name': 'ORANGEBOX',      'platform': ['windows', 'linux'],
 		                         'dir': 'hl2sdk-ob'}
-		self.possibleSdks['css'] =  {'sdk': 'HL2SDKCSS',   'ext': '2.css',  'def': '6',
+		self.possibleSdks['css'] =   {'sdk': 'HL2SDKCSS',       'ext': '2.css',   'def': '6',
 		                         'name': 'CSS',            'platform': ['windows', 'linux', 'darwin'],
 		                         'dir': 'hl2sdk-css'}
-		self.possibleSdks['ep2v'] =  {'sdk': 'HL2SDKOBVALVE',   'ext': '2.ep2v',  'def': '7',
-		                         'name': 'ORANGEBOXVALVE', 'platform': ['windows', 'linux', 'darwin'],
-		                        'dir': 'hl2sdk-ob-valve'}
-		self.possibleSdks['l4d'] =   {'sdk': 'HL2SDKL4D',       'ext': '2.l4d',   'def': '8',
+		self.possibleSdks['hl2dm'] = {'sdk': 'HL2SDKHL2DM',     'ext': '2.hl2dm', 'def': '7',
+		                         'name': 'HL2DM',          'platform': ['windows', 'linux', 'darwin'],
+		                         'dir': 'hl2sdk-hl2dm'}
+		self.possibleSdks['dods'] =  {'sdk': 'HL2SDKDODS',      'ext': '2.dods',  'def': '8',
+		                         'name': 'DODS',           'platform': ['windows', 'linux', 'darwin'],
+		                         'dir': 'hl2sdk-dods'}
+		self.possibleSdks['tf2'] =   {'sdk': 'HL2SDKTF2',       'ext': '2.tf2',   'def': '9',
+		                         'name': 'TF2',            'platform': ['windows', 'linux', 'darwin'],
+		                         'dir': 'hl2sdk-tf2'}
+		self.possibleSdks['l4d'] =   {'sdk': 'HL2SDKL4D',       'ext': '2.l4d',   'def': '10',
 		                         'name': 'LEFT4DEAD',      'platform': ['windows', 'linux', 'darwin'],
 		                         'dir': 'hl2sdk-l4d'}
-		self.possibleSdks['l4d2'] =  {'sdk': 'HL2SDKL4D2',      'ext': '2.l4d2',  'def': '9',
+		self.possibleSdks['nd'] =    {'sdk': 'HL2SDKND',        'ext': '2.nd',    'def': '11',
+		                         'name': 'NUCLEARDAWN',    'platform': ['windows', 'linux', 'darwin'],
+		                         'dir': 'hl2sdk-nd'}
+		self.possibleSdks['l4d2'] =  {'sdk': 'HL2SDKL4D2',      'ext': '2.l4d2',  'def': '12',
 		                         'name': 'LEFT4DEAD2',     'platform': ['windows', 'linux', 'darwin'],
 		                         'dir': 'hl2sdk-l4d2'}
 		self.possibleSdks['darkm'] = {'sdk': 'HL2SDK-DARKM',    'ext': '2.darkm', 'def': '2',
 		                         'name': 'DARKMESSIAH',    'platform': ['windows'],
 		                          'dir': 'hl2sdk-darkm'}
-		self.possibleSdks['swarm'] = {'sdk': 'HL2SDK-SWARM',    'ext': '2.swarm', 'def': '10',
+		self.possibleSdks['swarm'] = {'sdk': 'HL2SDK-SWARM',    'ext': '2.swarm', 'def': '13',
 		                         'name': 'ALIENSWARM',     'platform': ['windows'],
 		                         'dir': 'hl2sdk-swarm'}
-		self.possibleSdks['bgt'] =   {'sdk': 'HL2SDK-BGT',      'ext': '2.bgt', 'def': '4',
+		self.possibleSdks['bgt'] =   {'sdk': 'HL2SDK-BGT',      'ext': '2.bgt',   'def': '4',
 		                         'name': 'BLOODYGOODTIME', 'platform': ['windows'],
 		                         'dir': 'hl2sdk-bgt'}
-		self.possibleSdks['eye'] =   {'sdk': 'HL2SDK-EYE',      'ext': '2.eye', 'def': '5',
-		                         'name': 'EYE',             'platform': ['windows'],
+		self.possibleSdks['eye'] =   {'sdk': 'HL2SDK-EYE',      'ext': '2.eye',   'def': '5',
+		                         'name': 'EYE',            'platform': ['windows'],
 		                         'dir': 'hl2sdk-eye'}
-		self.possibleSdks['csgo'] =  {'sdk': 'HL2SDKCSGO',     'ext': '2.csgo',  'def': '12',
+		self.possibleSdks['csgo'] =  {'sdk': 'HL2SDKCSGO',     'ext': '2.csgo',   'def': '15',
 		                         'name': 'CSGO',           'platform': ['windows', 'linux', 'darwin'],
 		                         'dir': 'hl2sdk-csgo'}
-		self.possibleSdks['dota'] =  {'sdk': 'HL2SDKDOTA',     'ext': '2.dota',  'def': '13',
+		self.possibleSdks['dota'] =  {'sdk': 'HL2SDKDOTA',     'ext': '2.dota',   'def': '16',
 		                         'name': 'DOTA',           'platform': ['windows'],
 		                         'dir': 'hl2sdk-dota'}
-		# self.possibleSdks['portal2'] =  {'sdk': 'HL2SDK-PORTAL2',     'ext': '2.portal2',  'def': '11',
+		# self.possibleSdks['portal2'] =  {'sdk': 'HL2SDK-PORTAL2',     'ext': '2.portal2',  'def': '14',
 		#                        'name': 'PORTAL2',           'platform': ['windows'],
 		#                        'dir': 'hl2sdk-portal2'}
 		
@@ -260,7 +269,7 @@ class MMS:
 			else:
 				staticLibs = os.path.join(sdkPath, 'lib', 'linux')
 			workFolder = os.path.join(AMBuild.outputFolder, job.workFolder)
-			if sdk in ['ep2v', 'css', 'l4d2']:
+			if sdk in ['css', 'hl2dm', 'dods', 'tf2', 'l4d2']:
 				libs = ['tier1_i486.a', 'libvstdlib_srv.so', 'libtier0_srv.so']
 				for lib in libs:
 					link = os.path.join(workFolder, lib)
@@ -269,7 +278,7 @@ class MMS:
 						os.lstat(link)
 					except:
 						job.AddCommand(SymlinkCommand(link, target))
-			elif sdk in ['l4d', 'csgo']:
+			elif sdk in ['l4d', 'nd', 'csgo']:
 				libs = ['tier1_i486.a', 'libvstdlib.so', 'libtier0.so']
 				if sdk == 'csgo':
 					libs.insert(0, 'interfaces_i486.a')
@@ -328,7 +337,7 @@ class MMS:
 		
 		# We don't build for Portal 2 (yet?, ever?), but using this define in code as 
 		# it saves trouble if we ever need to
-		compiler['CDEFINES'].append('SE_PORTAL2=11')
+		compiler['CDEFINES'].append('SE_PORTAL2=14')
 
 		paths = [['public'], ['public', 'engine'], ['public', 'mathlib'], ['public', 'vstdlib'],
 						 ['public', 'tier0'], ['public', 'tier1']]
@@ -366,10 +375,10 @@ class MMS:
 		if not noLink:
 			if AMBuild.target['platform'] == 'linux':
 				compiler['POSTLINKFLAGS'][0:0] = ['-lm']
-				if sdk in ['ep2v', 'css', 'l4d2']:
+				if sdk in ['css', 'hl2dm', 'dods', 'tf2', 'l4d2']:
 					compiler['POSTLINKFLAGS'][0:0] = ['libtier0_srv.so']
 					compiler['POSTLINKFLAGS'][0:0] = ['libvstdlib_srv.so']
-				elif sdk in ['l4d', 'csgo']:
+				elif sdk in ['l4d', 'nd', 'csgo']:
 					compiler['POSTLINKFLAGS'][0:0] = ['libtier0.so']
 					compiler['POSTLINKFLAGS'][0:0] = ['libvstdlib.so']
 				else:
diff --git a/core/ISmmPluginExt.h b/core/ISmmPluginExt.h
index b9c3339..be76e89 100644
--- a/core/ISmmPluginExt.h
+++ b/core/ISmmPluginExt.h
@@ -48,7 +48,7 @@ enum
 #define SOURCE_ENGINE_ORANGEBOX			3				/**< Orange Box Source Engine (third major SDK) */
 #define SOURCE_ENGINE_LEFT4DEAD			4				/**< Left 4 Dead */
 #define SOURCE_ENGINE_DARKMESSIAH		5				/**< Dark Messiah Multiplayer (based on original engine) */
-#define SOURCE_ENGINE_ORANGEBOXVALVE	6				/**< Orange Box Source Engine for Valve games (TF2/DOD:S/HL2DM) */
+#define SOURCE_ENGINE_ORANGEBOXVALVE_DEPRECATED	6				/**< Orange Box Source Engine for Valve games (TF2/DOD:S/HL2DM) */
 #define SOURCE_ENGINE_LEFT4DEAD2		7				/**< Left 4 Dead 2 */
 #define SOURCE_ENGINE_ALIENSWARM		8				/**< Alien Swarm */
 #define SOURCE_ENGINE_BLOODYGOODTIME	9				/**< Bloody Good Time */
@@ -57,6 +57,10 @@ enum
 #define SOURCE_ENGINE_CSGO				12				/**< Counter-Strike: Global Offensive */
 #define SOURCE_ENGINE_CSS				13				/**< Counter-Strike: Source (sometimes older version of Orange Box Valve) */
 #define SOURCE_ENGINE_DOTA				14				/**< Dota 2 */
+#define SOURCE_ENGINE_HL2DM				15				/**< Half-Life 2 Deathmatch */
+#define SOURCE_ENGINE_DODS				16				/**< Day of Defeat: Source */
+#define SOURCE_ENGINE_TF2				17				/**< Team Fortress 2 */
+#define SOURCE_ENGINE_NUCLEARDAWN		18				/**< Nuclear Dawn */
 
 #define METAMOD_PLAPI_VERSION			15				/**< Version of this header file */
 #define METAMOD_PLAPI_NAME				"ISmmPlugin"	/**< Name of the plugin interface */
diff --git a/core/metamod_console.cpp b/core/metamod_console.cpp
index 10a2a0b..2bb0dc5 100644
--- a/core/metamod_console.cpp
+++ b/core/metamod_console.cpp
@@ -117,14 +117,20 @@ bool Command_Meta(IMetamodSourceCommandInfo *info)
 			CONMSG("  Engine: Alien Swarm (2010)\n");
 #elif SOURCE_ENGINE == SE_LEFT4DEAD2
 			CONMSG("  Engine: Left 4 Dead 2 (2009)\n");
+#elif SOURCE_ENGINE == SE_NUCLEARDAWN
+			CONMSG("  Engine: Nuclear Dawn (2011)\n");
 #elif SOURCE_ENGINE == SE_LEFT4DEAD
 			CONMSG("  Engine: Left 4 Dead (2008)\n");
 #elif SOURCE_ENGINE == SE_ORANGEBOX
 			CONMSG("  Engine: Episode 2 (Orange Box, 2007)\n");
 #elif SOURCE_ENGINE == SE_CSS
-			CONMSG("  Engine: Counter-Strike: Source (Old Valve Orange Box, 2009)\n");
-#elif SOURCE_ENGINE == SE_ORANGEBOXVALVE
-			CONMSG("  Engine: Episode 2 (Valve Orange Box, 2009)\n");
+			CONMSG("  Engine: Counter-Strike: Source (Valve Orange Box)\n");
+#elif SOURCE_ENGINE == SE_HL2DM
+			CONMSG("  Engine: Half-Life 2 Deathmatch (Valve Orange Box)\n");
+#elif SOURCE_ENGINE == SE_DODS
+			CONMSG("  Engine: Day of Defeat: Source (Valve Orange Box)\n");
+#elif SOURCE_ENGINE == SE_TF2
+			CONMSG("  Engine: Team Fortress 2 (Valve Orange Box)\n");
 #elif SOURCE_ENGINE == SE_DARKMESSIAH
 			CONMSG("  Engine: Dark Messiah (2006)\n");
 #elif SOURCE_ENGINE == SE_EYE
diff --git a/core/metamod_plugins.cpp b/core/metamod_plugins.cpp
index 20b9212..f33ff4a 100644
--- a/core/metamod_plugins.cpp
+++ b/core/metamod_plugins.cpp
@@ -489,13 +489,18 @@ CPluginManager::CPlugin *CPluginManager::_Load(const char *file, PluginId source
 				info.pl_path = file_path;
 
 				pl->m_API = fnLoad(&GlobVersionInfo, &info);
-#if SOURCE_ENGINE == SE_ORANGEBOXVALVE
+#if SOURCE_ENGINE == SE_CSS || SOURCE_ENGINE == SE_HL2DM || SOURCE_ENGINE == SE_DODS || SOURCE_ENGINE == SE_TF2
 				/* For plugin compat - try loading again using original OB if OB-Valve has failed */
 				if (pl->m_API == NULL)
 				{
-					GlobVersionInfo.source_engine = SOURCE_ENGINE_ORANGEBOX;
+					GlobVersionInfo.source_engine = SOURCE_ENGINE_ORANGEBOXVALVE_DEPRECATED;
 					pl->m_API = fnLoad(&GlobVersionInfo, &info);
-					GlobVersionInfo.source_engine = SOURCE_ENGINE_ORANGEBOXVALVE;
+					if (pl->m_API == NULL)
+					{
+						GlobVersionInfo.source_engine = SOURCE_ENGINE_ORANGEBOX;
+						pl->m_API = fnLoad(&GlobVersionInfo, &info);
+					}
+					GlobVersionInfo.source_engine = g_Metamod.GetSourceEngineBuild();
 				}
 #endif
 				pl->m_UnloadFn = (METAMOD_FN_UNLOAD)dlsym(pl->m_Lib, "UnloadInterface_MMS");
diff --git a/core/provider/provider_ep2.cpp b/core/provider/provider_ep2.cpp
index 16de59d..71aa0af 100644
--- a/core/provider/provider_ep2.cpp
+++ b/core/provider/provider_ep2.cpp
@@ -377,14 +377,20 @@ int BaseProvider::DetermineSourceEngine(const char *game)
 	return SOURCE_ENGINE_ALIENSWARM;
 #elif SOURCE_ENGINE == SE_LEFT4DEAD2
 	return SOURCE_ENGINE_LEFT4DEAD2;
+#elif SOURCE_ENGINE == SE_NUCLEARDAWN
+	return SOURCE_ENGINE_NUCLEARDAWN;
 #elif SOURCE_ENGINE == SE_LEFT4DEAD
 	return SOURCE_ENGINE_LEFT4DEAD;
 #elif SOURCE_ENGINE == SE_ORANGEBOX
 	return SOURCE_ENGINE_ORANGEBOX;
 #elif SOURCE_ENGINE == SE_CSS
 	return SOURCE_ENGINE_CSS;
-#elif SOURCE_ENGINE == SE_ORANGEBOXVALVE
-	return SOURCE_ENGINE_ORANGEBOXVALVE;
+#elif SOURCE_ENGINE == SE_HL2DM
+	return SOURCE_ENGINE_HL2DM;
+#elif SOURCE_ENGINE == SE_DODS
+	return SOURCE_ENGINE_DODS;
+#elif SOURCE_ENGINE == SE_TF2
+	return SOURCE_ENGINE_TF2;
 #elif SOURCE_ENGINE == SE_DARKMESSIAH
 	return SOURCE_ENGINE_DARKMESSIAH;
 #elif SOURCE_ENGINE == SE_EYE
diff --git a/loader/loader.cpp b/loader/loader.cpp
index 6b1519c..2ea5692 100644
--- a/loader/loader.cpp
+++ b/loader/loader.cpp
@@ -81,6 +81,10 @@ static const char *backend_names[] =
 	"2.portal2",
 	"2.csgo",
 	"2.dota",
+	"2.hl2dm",
+	"2.dods",	
+	"2.tf2",
+	"2.nd",
 };
 
 #if defined _WIN32
@@ -285,7 +289,14 @@ mm_DetermineBackend(QueryValveInterface engineFactory, const char *game_name)
 		}
 		else if (engineFactory("VPrecacheSystem001", NULL) != NULL)
 		{
-			return MMBackend_Left4Dead2;
+			if (strcmp(game_name, "nucleardawn") == 0)
+			{
+				return MMBackend_NuclearDawn;
+			}
+			else
+			{
+				return MMBackend_Left4Dead2;
+			}
 		}
 		return MMBackend_Left4Dead;
 	}
@@ -316,9 +327,17 @@ mm_DetermineBackend(QueryValveInterface engineFactory, const char *game_name)
 				{
 					return MMBackend_CSS;
 				}
-				else
+				else if (strcmp(game_name, "tf") == 0)
 				{
-					return MMBackend_Episode2Valve;
+					return MMBackend_TF2;
+				}
+				else if (strcmp(game_name, "dod") == 0)
+				{
+					return MMBackend_DODS;
+				}
+				else if (strcmp(game_name, "hl2mp") == 0)
+				{
+					return MMBackend_HL2DM;
 				}
 			}
 		}
diff --git a/loader/loader.h b/loader/loader.h
index 0a21686..e5a54cd 100644
--- a/loader/loader.h
+++ b/loader/loader.h
@@ -86,13 +86,17 @@ enum MetamodBackend
 	MMBackend_BloodyGoodTime,
 	MMBackend_EYE,
 	MMBackend_CSS,
-	MMBackend_Episode2Valve,
+	MMBackend_Episode2Valve_OBSOLETE,
 	MMBackend_Left4Dead,
 	MMBackend_Left4Dead2,
 	MMBackend_AlienSwarm,
 	MMBackend_Portal2,
 	MMBackend_CSGO,
 	MMBackend_DOTA,
+	MMBackend_HL2DM,
+	MMBackend_DODS,
+	MMBackend_TF2,
+	MMBackend_NuclearDawn,
 	MMBackend_UNKNOWN
 };
 
diff --git a/loader/serverplugin.cpp b/loader/serverplugin.cpp
index be4f17c..014f575 100644
--- a/loader/serverplugin.cpp
+++ b/loader/serverplugin.cpp
@@ -105,7 +105,8 @@ public:
 		void **this_vtable;
 		this_vtable = (void **)*(void **)this;
 
-		if (mm_backend >= MMBackend_Episode2)
+		if (mm_backend != MMBackend_Episode1
+			&& mm_backend != MMBackend_DarkMessiah)
 		{
 			/* We need to insert the right type of call into this vtable */
 			void **vtable_src;
@@ -133,7 +134,10 @@ public:
 		}
 
 		/* AS inserted ClientFullyConnect into vtable, so move entries up on older engines */
-		if (mm_backend < MMBackend_AlienSwarm)
+		if (mm_backend != MMBackend_AlienSwarm
+			&& mm_backend != MMBackend_Portal2
+			&& mm_backend != MMBackend_CSGO
+			&& mm_backend != MMBackend_DOTA)
 		{
 			SourceHook::MemFuncInfo mfp_fconnect;
 			mfp_fconnect.isVirtual = false;