[Scummvm-git-logs] scummvm master -> a8a4c25361f17f44714d65a152664ccac6e9bccb

sev- sev at scummvm.org
Sat Oct 3 12:59:04 UTC 2020


This automated email contains information about 200 new commits which have been
pushed to the 'scummvm' repo located at https://github.com/scummvm/scummvm .

Summary:
a8d5168a35 PLUGINS: Add a ease-use macro - PLUGIN_ENABLED
365b1101f3 CONFIGURE: Add static-detect-plugins array to be added in plugin_tables.h
28dc54940f BUILD: MAKEFILE: Introduce DETECT_OBJS variable. Executable depends on it.
6689fa740a BASE: PLUGINS: Add a new type of plugin - MetaEngine
09c1e1e07d BASE: Change how game detection works.
f07bdb100e BASE: PLUGINS: Implement unloadPluginsExcept correctly
943df64b32 ENGINES: Change behaviour of EngineMan::getPlugins.
24ee4c7559 ENGINES: ME & AME: Add new classes related to ME & AME.
09a16347de ENGINES: Move createInstance from ME to MetaEngineConnect class
e69d9c98a4 ENGINES: AME: Move the subclass implemented method createInstance out of AME into AMEConnect.
575e77522a BASE: MAIN: Change how running games works.
a73858a3df ENGINES: MEC & AMEC: Provide notes for getName().
f2dd03e7d8 BASE: PLUGINS: Implement a getEngineId for PluginObjects, return nullptr by default.
50e9f0d875 BASE: PLUGINS: Add helper methods which match MetaEngine to Engine & vice-versa
39f5c93c5c BASE: PLUGINS: Bump PLUGIN_TYPE_ENGINE_VERSION to 2
9c67225293 COMMON: ERROR: Add kMetaEnginePluginNotFound
ce80c0c730 ENGINES: Add a helper method - getMetaEngineConnect().
01efb65931 ENGINES: METAENGINE: Shift save/load related content to MetaEngineConnect
73cc973ad7 BASE: ENGINES: Change saveload code to adapt to the new MEC class.
bdafdf220d BASE: PLUGINS: Deprecate improper usage of unloadPluginsExcept
9353e339c6 BASE: MAIN: Proper usage of unloadPluginsExcept before running a game.
5d3292d844 CONFIGURE: Update to properly support statically linked ScummVM.
fd1e333100 ENGINES: METAENGINE: Move initKeymaps into MetaEngineConnect.
0cc8719417 BASE: ENGINES: Adapt to keymaps moving to engine plugins
1616d7d515 ENGINES: ME & MEC: Move achievements-related code to MetaEngineConnect
978901cc2f PLUMBERS: Split detection code & adapt to new plugins.
9c6c628ae6 AGI: Move some common code to detection.h
fa36701425 AGI: Split detection features & adapt to new plugins.
d10eb35dfe SCUMM: Move obsoleteGameIDsTable from detection_tables to a common header
dc4672e294 SCUMM: Split detection features & adapt to new plugins.
4c1a03845f SCUMM: Refactoring, remove detection.o dependency from modules.
6a3b7b6722 SKY: Split detection features & adapt to new plugins.
cdf4261328 DREAMWEB: Move common struct to detection.h
5161f46f98 DREAMWEB: Split detection code & adapt to new plugins.
14edaf3d03 DRASCULA: Split detection code & adapt to new plugins
141edd7eb8 LURE: Split detection code & adapt to new plugins.
467ca35a37 SWORD1: Split detection code & adapt to new plugins.
a21da27bf1 SWORD2: Refactoring of code, split detection code, adapt to new plugins.
0880ab9357 SWORD25: Split detection code & adapt to new plugins.
c2428c7a8f ADL: Split detection code & adapt to new plugins.
d57f84205c ADL: Seperate detection.h into two headers to improve dependencies
0a14511547 ADL: Remove unneeded functions from detection & move to metaengine.
4b377af8c6 QUEEN: Split detection code & adapt to new plugins.
0d61c5bd4b CGE: Split detection code & adapt to new plugins.
4ef8eab545 CGE2: Split detection code & adapt to new plugins.
48751160f9 ACCESS: Move common enum to detection_enums.h
c5325c68c9 ACCESS: Split detection code & adapt to new plugins.
bbed423569 ZVISION: Move common enums to detection_enums header file.
c7dc3d6118 ZVISION: Split detection code & adapt to new plugins.
76cb0351e0 AGOS: Move common enum from agos.h to new header file
5850987077 AGOS: Move some common detection related enums from intern.h -> intern_detection.h
2f6453100b AGOS: Split detection code & adapt to new plugins.
bd9514ffa8 GOB: Remove gob engine file dependencies from dataio.cpp
9b774c6b6f GOB: Move detection-related enums from gob.h -> detection/detection_enums.h
ce07bd711f GOB: Split detection code & adapt to new plugins.
7bdc910cc8 COMPOSER: Split detection features & adapt to new plugins.
b027c8f11e DM: Move common-game & detection code to header files from dm.h
26c475b784 DM: Split detection features & adapt to new plugins.
8eb9ae7c98 DRACI: Split detection features & adapt to new plugins.
794909c7fc DRAGONS: Move common game-detection code to new header files.
cf69fce865 DRAGONS: Split detection features & adapt to new plugins.
1c06bc6e75 GNAP: Split detection features & adapt to new plugins.
854a499307 GRIFFON: Split detection features & adapt to new plugins.
563cef1071 GROOVIE: Split detection features & adapt to new plugins.
509fd69827 GROOVIE: Solve missing header dependencies.
eb78152664 HDB: Split detection features & adapt to new plugins.
eaa1ef09a5 HOPKINS: Split detection features & adapt to new plugins.
d02d53e9a3 HUGO: Move common game-detection related enums to new header file.
242e01bb02 HUGO: Split detection features & adapt to new plugins.
fe37efbca2 ILLUSIONS: Split detection features & adapt to new plugins.
033ad0baa1 KINGDOM: Split detection features & adapt to new plugins.
1d6f402540 KYRA: Move common game/detection related enums to new header
846336cb31 KYRA: Split detection features & adapt to new plugins.
0fbfa709a2 LAB: Split detection features & adapt to new plugins.
06cb6c50e6 LASTEXPRESS: Split detection features & adapt to new plugins.
5593b47e88 LILLIPUT: Split detection features & adapt to new plugins.
985faf8d8c MACVENTURE: Split detection features & adapt to new plugins.
53131399f9 MADE: Move common game/detection related code into new header files
70ba16f857 MADE: Split detection features & adapt to new plugins.
d338d4c7d4 MADS: Split detection features & adapt to new plugins.
394aa54b7b MORTEVIELLE: Split detection features & adapt to new plugins.
056f26402a MUTATIONOFJB: Split detection features & adapt to new plugins.
fbac5798fb NEVERHOOD: Split detection features & adapt to new plugins.
d3f164698a PARALLACTION: Split detection features & adapt to new plugins.
8f751aa359 PEGASUS: Split detection features & adapt to new plugins.
556aa7ef7c PETKA: Split detection features & adapt to new plugins.
0816e46ba6 PINK: Split detection features & adapt to new plugins.
4458a2e243 PRINCE: Split detection features & adapt to new plugins.
e29f02597c SHERLOCK: Split detection features & adapt to new plugins.
af47301cca SLUDGE: Split detection features & adapt to new plugins.
65f13a0b26 STARTREK: Split detection features & adapt to new plugins.
c7d7d18ad2 SUPERNOVA: Split detection features & adapt to new plugins.
2aca677fcc TEENAGENT: Split detection features & adapt to new plugins.
31b35628f2 TESTBED: Split detection features & adapt to new plugins.
b1be077085 TINSEL: Split detection features & adapt to new plugins.
dae6013369 TITANIC: Split detection features & adapt to new plugins.
2360e21dd1 TOLTECS: Split detection features & adapt to new plugins.
02c71c91f5 TONY: Split detection features & adapt to new plugins.
cf5581f27f TOON: Split detection features & adapt to new plugins.
d69a9b519f TOUCHE: Split detection features & adapt to new plugins.
d001efc534 TSAGE: Split detection features & adapt to new plugins.
7c7263564b TUCKER: Split detection features & adapt to new plugins.
52cdf07671 VOYEUR: Split detection features & adapt to new plugins.
46f1ba1f1f WAGE: Split detection features & adapt to new plugins.
9208a65a1f AVALANCHE: Split detection features & adapt to new plugins.
c4ba47a65d BBVS: Split detection features & adapt to new plugins.
de141e7826 BLADERUNNER: Split detection features & adapt to new plugins.
6ade053c01 CHEWY: Split detection features & adapt to new plugins.
ec3ccf5eb0 CINE: Split detection features & adapt to new plugins.
2712bccff6 CRUISE: Split detection features & adapt to new plugins.
fb458421cf CRYO: Split detection features & adapt to new plugins.
e9ad5efad1 CRYOMNI3D: Split detection features & adapt to new plugins.
7944a7b039 DIRECTOR: Split detection features & adapt to new plugins.
30794432ab FULLPIPE: Split detection features & adapt to new plugins.
a4739197da SAGA: Move some shared defines between engine/game detection to a new header
95bc4c0994 SAGA: Move common engine/game-detection related enums into a new header.
d8c82faf27 SAGA: Split detection features & adapt to new plugins.
cd87a9150e XEEN: Split detection features & adapt to new plugins.
30d2d9167e ENGINES: ME: Mark destructor as virtual
395f590554 ENGINES: AMEC: Add some fallback detection-related functionality.
57b5a93f47 WINTERMUTE: Move engine/game-detection common enum to new header
b4044c87e7 WINTERMUTE: Move game/engine common enums from /base to a common enum
0b9df04112 WINTERMUTE: Rename game_description.h -> detection.h
c9f2c50380 WINTERMUTE: Split detection features & adapt to new plugins.
e644782294 SCI: Move graphics helpers/detection related enums into a new header
aa353cc4fb SCI: Move engine/detection common enums to new header.
255af8a0eb SCI: Split detection features & adapt to new plugins.
81ba5d5627 ENGINES: ME & MEC: Allow MEC to build engine options widget.
8c324fab42 MOHAWK: RIVEN: Move shared graphics/detection enum to new header.
2113bbcd9c MOHAWK: RIVEN: Move shared detection/riven code from engine to a new MetaEngine class.
65320b26a6 MOHAWK: MYST: Move common myst engine/detection code to new class.
b4a0fcca6c MOHAWK: Dialogs: Use the new classes to help in dialogs correctly.
45ad55df2d MOHAWK: Move shared engine/detection enums to new header file.
52a420f4b1 MOHAWK: Split detection features & adapt to new plugins.
53c772aebb ULTIMA: Split detection features & adapt to new plugins.
27d16ba9c5 GLK: Move game-description struct into a header file from glk.h.
92839dce1c GLK: Split detection features & adapt to new plugins.
84ddd3ac88 BASE: PLUGINS: Remove comments referring to old game detection
8b43e79695 GUI: Fix namespaces for saveload dialogs when cloud is enabled.
53f08789eb BASE: PLUGINS: Restore functionalities of uncached plugin manager for the new changes.
7fe1eb330d DREAMWEB: Remove redundant and unreachable return statement
fa8aa6e9f4 AGI: Move detection related code to a new folder, add AGI-Detection module.
ff74297940 PLUMBERS: Move detection related code to a new folder, add new Detection module.
05e170415c CONFIGURE: TEMP: Add support to build detection features as dynamic.
74149fe7cd BASE: DETECTION: Add a new module detection.
408158edc9 BASE: PLUGINS: Add a new type of plugin - DETECTION.
b78534dcb0 BASE: PLUGINS: Seperate declaration/definition of StaticPlugins.
8dfaf6cc0e BASE: PLUGINS: Add support for detection plugins to be loaded on demand.
5f5363f03b BASE: MAIN: Load/Unload detection plugin for UncachedPluginMan as/when needed.
e16ec08d8b BASE: DETECTION: Use correct header file
8189a05316 ENGINES: ALL: Adapt to changes for new plugins by defining a new detection module
78dd712a1c PARALLACTION: Adapt to new detection modules and misc changes.
2ee4cd2878 CONFIGURE: Add functionality for detection modules for each engine
11f46399b6 GIT: Add detection_tables header to .gitignore
7615f37698 BASE: PLUGINS: Add detection tables header file when getting static plugins.
fea29b04ac BASE: PLUGINS: Add a plugin suffix only if it is available
f3b9477893 ENGINES: ALL: Add header guards for the new detection-header files.
274b8a51a1 TONY: Match consistency with other engines & move enums to new header.
29ceb07959 ENGINES: ALL: Revert detection submodule to be directly present in the engine directory
e64446e4ce CONFIGURE: Remove detection submodules written to engines.mk
911e0e4f3c GIT: Rename detection_tables inside gitignore which is now present inside engines subdirectory
6735c46c41 MAKEFILES: Add a variable which helps in deciding if rules.mk should be used or not
ac900a06b8 BASE: PLUGINS: Use engines/detection_table header for static plugins
4f55c1b689 DIRECTOR & KYRA: MODULES: Use workarounds to skip warnings.
1d3e4d2800 MOHAWK: Do not create additional folders for riven & myst metaengines.
0cbff637d4 MAKEFILES: Include all detection objects while keeping the rest as-is.
867e6c4e21 CONFIGURE: Improve enabling of detection as static/dynamic
81d2bb8f11 ENGINES: DETECTION: Shift detection files to live inside engines subdirectory
11615faca8 MAKEFILES: Include dynamic building detection module if requested
ba5368542f BASE: PLUGINS: Update header file & use DETECTION_STATIC def check to build static detection features.
a56dc094b9 ENGINES: ALL: Move detection_enums -> detection.h
973526a4d3 BBVS: Fix compilation
2c2f21b0cd NEVERHOOD: Fix compilation
ceabaf3b0d BASE: Added override keywords
32799c1ee8 SCUMM: Fix naming for ScummMetaEngineConnect
9eb564b89f SCI: Move common enum -> detection.h
102b22f4a8 SCI: Fix naming for SciMetaEngineConnect
6679c7e72e GLK: Fix modules to build
a9841622e0 ENGINES: DETECTION: Use inheritance hierarchy and mimic existing plugins.
e08748866e SCI & WINTERMUTE: Fix unsafe code for fallbackDetect
13f2a0afb0 SCUMM: DETECTION: Remove sneaky main engine headers.
9624bfeb15 SCUMM: Move common detection/engine enums into detection.h
1b3eec4252 SCI: Assign proper naming for building options widget
de56694f53 DEVTOOLS: CREATE_PROJECT: Support static detection features
abedaaa5aa ENGINES: Don't allow dynamic detection to be exposed when using static-detection.
0b2428e7c5 NEVERHOOD: Temporarily rename module -> module_scene.cpp
f4d4283f79 QUEEN: Add missing newline at EOF in modules.mk
58a9de8092 DEVTOOLS: CREATE_PROJECT: Use map instead of unordered_map
a9fd54cffd GLK: Fix missing header files to create engines
73af65eedb GRIFFON: Add missing header for translations
2f05960913 BUILD: MAKEFILES: Rename USE_RULES -> LOAD_RULES_MK
02730ee176 BUILD: MAKEFILES: Improve syntax of if checks
c48719404a BASE: PLUGINS: Rename plugin matching helpers
71a820caff ENGINES: Begin class renaming of ME & AME
d26bbe521c ENGINES: ALL: Finish renaming ME & AME classes
992abce74a ENGINES: Rename getMetaEngine helpers
e3e8e81815 ENGINES: METAENGINE: Improve comments
41af1b63a9 BASE: PLUGINS: Improve fb detection for Sci & Wintermute
ffa69bfb26 GUI: debug statements related to plugins matching -> level 9.
a8a4c25361 PLUGINS: Rename detection plugin


Commit: a8d5168a35eb541c24e19bf1ab42b58746269734
    https://github.com/scummvm/scummvm/commit/a8d5168a35eb541c24e19bf1ab42b58746269734
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PLUGINS: Add a ease-use macro - PLUGIN_ENABLED

Changed paths:
    base/internal_plugins.h


diff --git a/base/internal_plugins.h b/base/internal_plugins.h
index 1af1607022..6eb98e747f 100644
--- a/base/internal_plugins.h
+++ b/base/internal_plugins.h
@@ -17,3 +17,5 @@
 #else
 	#define PLUGIN_ENABLED_DYNAMIC(ID) 0
 #endif
+
+#define PLUGIN_ENABLED(ID) (ENABLE_##ID)


Commit: 365b1101f3fb474337f5f64105a40533d7ee058f
    https://github.com/scummvm/scummvm/commit/365b1101f3fb474337f5f64105a40533d7ee058f
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CONFIGURE: Add static-detect-plugins array to be added in plugin_tables.h

- Currently, it is empty.
- After I enable engines one by to one to use detection statically, I will add them to the static_detect_engines array.

Changed paths:
    configure


diff --git a/configure b/configure
index ac158ae50f..cc6c2ad4dd 100755
--- a/configure
+++ b/configure
@@ -6160,6 +6160,8 @@ EOF
 	fi
 done
 
+declare -a static_detect_engines=()
+
 echo "Creating engines/plugins_table.h"
 cat > engines/plugins_table.h << EOF
 /* This file is automatically generated by configure */
@@ -6170,6 +6172,17 @@ EOF
 for engine in $_sorted_engines; do
 	if test "`get_engine_sub $engine`" = "no" ; then
 		j=`echo $engine | tr '[:lower:]' '[:upper:]'`
+		for eng in "${static_detect_engines[@]}"; do
+			if [ $j == $eng ]; then
+				cat >> engines/plugins_table.h << EOF
+#if PLUGIN_ENABLED($j)
+LINK_PLUGIN($j)
+#endif
+EOF
+				continue 2
+			fi
+		done
+		
 		cat >> engines/plugins_table.h << EOF
 #if PLUGIN_ENABLED_STATIC($j)
 LINK_PLUGIN($j)


Commit: 28dc54940fbed20a9d2e4f50bb6c174f0666510e
    https://github.com/scummvm/scummvm/commit/28dc54940fbed20a9d2e4f50bb6c174f0666510e
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BUILD: MAKEFILE: Introduce DETECT_OBJS variable. Executable depends on it.

Note: No detection objects added currently. It's just an empty variable uptill now.
- These DETECT_OBJS will be seen in action in the new commits
- They contain engine_name/detection.o
- They have MetaEngine code, which has detection features.
- This way, Executable will have linked against the detection.o files
- Detection.cpp files will be individually compilable and not dependent on engine

Changed paths:
    Makefile
    Makefile.common


diff --git a/Makefile b/Makefile
index 65c4f14f10..7d59044032 100644
--- a/Makefile
+++ b/Makefile
@@ -15,6 +15,9 @@ DEPDIR      := .deps
 MODULES     :=
 MODULE_DIRS :=
 
+# All game detection-related object files for engines
+DETECT_OBJS :=
+
 # Load the make rules generated by configure
 -include config.mk
 
diff --git a/Makefile.common b/Makefile.common
index 38c3030527..b4482a9143 100644
--- a/Makefile.common
+++ b/Makefile.common
@@ -86,7 +86,7 @@ endif
 endif
 
 # The build rule for the ScummVM executable
-$(EXECUTABLE): $(OBJS)
+$(EXECUTABLE): $(OBJS) $(DETECT_OBJS)
 	$(QUIET_LINK)$(LD) $(LDFLAGS) $(PRE_OBJS_FLAGS) $+ $(POST_OBJS_FLAGS) $(LIBS) -o $@
 
 ifdef SPLIT_DWARF
@@ -99,7 +99,7 @@ distclean: clean clean-devtools
 
 clean:
 	$(RM_REC) $(DEPDIRS)
-	$(RM) $(OBJS) $(EXECUTABLE)
+	$(RM) $(OBJS) $(DETECT_OBJS) $(EXECUTABLE)
 ifdef SPLIT_DWARF
 	$(RM) $(OBJS:.o=.dwo)
 	$(RM) $(EXECUTABLE).dwp


Commit: 6689fa740ab8163e973496a2ec1aecd7136b6de5
    https://github.com/scummvm/scummvm/commit/6689fa740ab8163e973496a2ec1aecd7136b6de5
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Add a new type of plugin - MetaEngine

- MetaEngines will now always go to the executable.
- But, because they still live in engine projects and are connected via a macro, they will need to be differentiated from Engines.
- This macro, and it's use in future will help in that.

Changed paths:
    base/plugins.cpp
    base/plugins.h


diff --git a/base/plugins.cpp b/base/plugins.cpp
index a82d32bf1c..b2b84ff072 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -33,6 +33,7 @@
 // Plugin versioning
 
 int pluginTypeVersions[PLUGIN_TYPE_MAX] = {
+	PLUGIN_TYPE_METAENGINE_VERSION,
 	PLUGIN_TYPE_ENGINE_VERSION,
 	PLUGIN_TYPE_MUSIC_VERSION,
 };
diff --git a/base/plugins.h b/base/plugins.h
index ccb1acf3fb..b0607dd0e0 100644
--- a/base/plugins.h
+++ b/base/plugins.h
@@ -60,7 +60,8 @@
 #define PLUGIN_VERSION 1
 
 enum PluginType {
-	PLUGIN_TYPE_ENGINE = 0,
+	PLUGIN_TYPE_METAENGINE = 0,
+	PLUGIN_TYPE_ENGINE,
 	PLUGIN_TYPE_MUSIC,
 	/* PLUGIN_TYPE_SCALER, */	// TODO: Add graphics scaler plugins
 
@@ -69,6 +70,7 @@ enum PluginType {
 
 // TODO: Make the engine API version depend on ScummVM's version
 // because of the backlinking (posibly from the checkout revision)
+#define PLUGIN_TYPE_METAENGINE_VERSION 1
 #define PLUGIN_TYPE_ENGINE_VERSION 1
 #define PLUGIN_TYPE_MUSIC_VERSION 1
 


Commit: 09c1e1e07d0675ce6114f67bc16c5b851a866e74
    https://github.com/scummvm/scummvm/commit/09c1e1e07d0675ce6114f67bc16c5b851a866e74
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: Change how game detection works.

- Do NOT use pluginMan and load plugins, etc, etc.
- Get MetaEngines from memory, since they're always built in statically.
- Use detectGames method to detect games.

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index b2b84ff072..ee13ab0c2f 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -543,6 +543,10 @@ DetectionResults EngineManager::detectGames(const Common::FSList &fslist) const
 	DetectedGames candidates;
 	PluginList plugins;
 	PluginList::const_iterator iter;
+
+	/**
+	 * Reference to old detection of games.
+	 * PLUGINS TODO: Remove at end.
 	PluginMan.loadFirstPlugin();
 	do {
 		plugins = getPlugins();
@@ -560,6 +564,24 @@ DetectionResults EngineManager::detectGames(const Common::FSList &fslist) const
 
 		}
 	} while (PluginMan.loadNextPlugin());
+	 */
+
+	// MetaEngines are always loaded into memory, so, get them and
+	// run detection for all of them.
+	plugins = getPlugins(PLUGIN_TYPE_METAENGINE);
+
+	// Iterate over all known games and for each check if it might be
+	// the game in the presented directory.
+	for (iter = plugins.begin(); iter != plugins.end(); ++iter) {
+		const MetaEngine &metaEngine = (*iter)->get<MetaEngine>();
+		DetectedGames engineCandidates = metaEngine.detectGames(fslist);
+
+		for (uint i = 0; i < engineCandidates.size(); i++) {
+			engineCandidates[i].path = fslist.begin()->getParent().getPath();
+			engineCandidates[i].shortPath = fslist.begin()->getParent().getDisplayName();
+			candidates.push_back(engineCandidates[i]);
+		}
+	}
 
 	return DetectionResults(candidates);
 }


Commit: f07bdb100ecbccf7a54084ea67c7994251953add
    https://github.com/scummvm/scummvm/commit/f07bdb100ecbccf7a54084ea67c7994251953add
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Implement unloadPluginsExcept correctly

- The new implementation matchs a plugin from type MetaEngine to an Engine, and unloads every else ENGINE.

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index ee13ab0c2f..54ae118f24 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -420,15 +420,81 @@ void PluginManager::unloadAllPlugins() {
 
 void PluginManager::unloadPluginsExcept(PluginType type, const Plugin *plugin, bool deletePlugin /*=true*/) {
 	Plugin *found = NULL;
-	for (PluginList::iterator p = _pluginsInMem[type].begin(); p != _pluginsInMem[type].end(); ++p) {
-		if (*p == plugin) {
-			found = *p;
-		} else {
-			(*p)->unloadPlugin();
-			if (deletePlugin)
-				delete *p;
+
+	// If someone calls this function with a nullptr Plugin, we clear everything, and no need to search
+	// for individual plugin.
+	if (plugin) {
+
+		if (type != plugin->getType() && type != PLUGIN_TYPE_ENGINE) {
+			warning("Plugins: unloadPluginExcept: mismatching type of plugins requested to unload. Operation not carried out.");
+			return;
+		}
+
+		Common::String enginePluginTitle("");
+		bool toDelete = false;
+
+		if (type == PLUGIN_TYPE_ENGINE) {
+			/**
+			 * We've got in a plugin of type MetaEngine, and we want to keep
+			 * the relevant plugin of Engine type in memory.
+			 * To do this, we first construct a name from the given MetaEngine.
+			 */
+
+#ifdef PLUGIN_PREFIX
+			enginePluginTitle += PLUGIN_PREFIX;
+#endif
+
+			enginePluginTitle += Common::String(plugin->getEngineId());
+
+#ifdef PLUGIN_SUFFIX
+			enginePluginTitle += PLUGIN_SUFFIX;
+#endif
+		}
+
+		for (PluginList::iterator p = _pluginsInMem[type].begin(); p != _pluginsInMem[type].end(); ++p) {
+			if (type == PLUGIN_TYPE_ENGINE) {
+				Common::String enginePluginFilename((*p)->getFileName());
+
+				/**
+				 * Take the ending of the filename, and subtract it with the size of enginePluginTitle.
+				 * This should effectively cancel out directory names and exactly leave the plugin filename
+				 * ONLY for the one we require. That's why we do a equals call.
+				 * Example: We got the request to unload engine of AGI, and were given a AGIMetaEngine.
+				 * So, plugins/agi.dll will beome agi.dll (fetched by getFileName) and will try
+				 * to match to our generated enginePluginTitle from the plugin we got. (A metaengine type plugin)
+				 * This will then pass the check and be the only one loaded in memory.
+				 */
+				if (enginePluginFilename.size() > enginePluginTitle.size()) {
+					Common::String::const_iterator beginItr = enginePluginFilename.end() - enginePluginTitle.size();
+					Common::String strippedFileName(beginItr, enginePluginFilename.end());
+
+					if (strippedFileName.equalsIgnoreCase(enginePluginTitle)) {
+						found = *p;
+					} else {
+						toDelete = true;
+					}
+				} else {
+					toDelete = true;
+				}
+			} else {
+				// The type is something other than a engine type.
+				if (*p == plugin) {
+					found = *p;
+				} else {
+					toDelete = true;
+				}
+			}
+
+			if (toDelete) {
+				(*p)->unloadPlugin();
+				if (deletePlugin) {
+					delete *p;
+				}
+				toDelete = false;
+			}
 		}
 	}
+
 	_pluginsInMem[type].clear();
 	if (found != NULL) {
 		_pluginsInMem[type].push_back(found);


Commit: 943df64b329d1fc4ddfa6f6cc711a76b3887d528
    https://github.com/scummvm/scummvm/commit/943df64b329d1fc4ddfa6f6cc711a76b3887d528
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: Change behaviour of EngineMan::getPlugins.

- Changed so we can get any type of plugins.
- This used to always return PLUGIN_TYPE_ENGINE.
- Because now we can differentiate between engines and metaengine, this must be changed.
- For now, return METAENGINE by default

Changed paths:
    base/plugins.cpp
    engines/metaengine.h


diff --git a/base/plugins.cpp b/base/plugins.cpp
index 54ae118f24..441fddc79e 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -652,8 +652,8 @@ DetectionResults EngineManager::detectGames(const Common::FSList &fslist) const
 	return DetectionResults(candidates);
 }
 
-const PluginList &EngineManager::getPlugins() const {
-	return PluginManager::instance().getPlugins(PLUGIN_TYPE_ENGINE);
+const PluginList &EngineManager::getPlugins(const PluginType fetchPluginType) const {
+	return PluginManager::instance().getPlugins(fetchPluginType);
 }
 
 namespace {
diff --git a/engines/metaengine.h b/engines/metaengine.h
index 7e9657b7cf..64248bf81a 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -416,8 +416,14 @@ public:
 	/** Find a plugin by its engine ID */
 	const Plugin *findPlugin(const Common::String &engineId) const;
 
-	/** Get the list of all engine plugins */
-	const PluginList &getPlugins() const;
+	/**
+	 * Get the list of all plugins for the type specified.
+	 * By default, it will get METAENGINES, for now.
+	 * If usage of actual engines never occurs, we can skip
+	 * the default arguments, and always have it return
+	 * PLUGIN_TYPE_METAENGINE.
+	 */
+	const PluginList &getPlugins(const PluginType fetchPluginType = PLUGIN_TYPE_METAENGINE) const;
 
 	/** Find a target */
 	QualifiedGameDescriptor findTarget(const Common::String &target, const Plugin **plugin = NULL) const;


Commit: 24ee4c7559701f71366f95708b46d3be0fa9c0ae
    https://github.com/scummvm/scummvm/commit/24ee4c7559701f71366f95708b46d3be0fa9c0ae
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: ME & AME: Add new classes related to ME & AME.

- MetaEngineConnect
- AdvancedMetaEngineConnect
- These classes will have "bridge" functions, see comments for more info.

Changed paths:
    engines/advancedDetector.h
    engines/metaengine.h


diff --git a/engines/advancedDetector.h b/engines/advancedDetector.h
index 941f59d497..9be9d8e958 100644
--- a/engines/advancedDetector.h
+++ b/engines/advancedDetector.h
@@ -322,4 +322,10 @@ protected:
 	friend class FileMapArchive; // for FileMap
 };
 
+/**
+ * A MetaEngineConnect implementation of AdvancedMetaEngine.
+ */
+class AdvancedMetaEngineConnect : public MetaEngineConnect {
+};
+
 #endif
diff --git a/engines/metaengine.h b/engines/metaengine.h
index 64248bf81a..f172c91904 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -99,7 +99,8 @@ struct ExtendedSavegameHeader {
  * Every engine "plugin" provides a hook to get an instance of a MetaEngine
  * subclass for that "engine plugin". E.g. SCUMM povides ScummMetaEngine.
  * This is then in turn used by the frontend code to detect games,
- * and instantiate actual Engine objects.
+ * and other useful functionality. To instantiate actual Engine objects,
+ * See the class MetaEngineConnect below.
  */
 class MetaEngine : public PluginObject {
 private:
@@ -401,6 +402,20 @@ public:
 	//@}
 };
 
+/**
+ * A MetaEngineConnect is another factory for Engine instances, and is very
+ * similiar to meta engines. This class, however, composes of bridged functionalities
+ * that can be used to connect an actual Engine with a MetaEngine.
+ * Every engine "plugin" provides a hook to get an instance of MetaEngineConnector subclass
+ * for that "engine plugin.". E.g. SCUMM provides a ScummMetaEngineConnect.
+ * This is then in turn used for things like instantiating engine objects, listing savefiles,
+ * querying save metadata, etc.
+ * Since engine plugins can be used a external runtime libraries, these can live and build inside
+ * the engine, while a MetaEngine will always build into the executable to be able to detect code.
+ */
+class MetaEngineConnect : public PluginObject {
+};
+
 /**
  * Singleton class which manages all Engine plugins.
  */


Commit: 09a16347deb30e406cdab4494d3dbb24cd0008b8
    https://github.com/scummvm/scummvm/commit/09a16347deb30e406cdab4494d3dbb24cd0008b8
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: Move createInstance from ME to MetaEngineConnect class

Changed paths:
    engines/metaengine.h


diff --git a/engines/metaengine.h b/engines/metaengine.h
index f172c91904..32e6af3645 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -130,18 +130,6 @@ public:
 	 */
 	virtual DetectedGames detectGames(const Common::FSList &fslist) const = 0;
 
-	/**
-	 * Tries to instantiate an engine instance based on the settings of
-	 * the currently active ConfMan target. That is, the MetaEngine should
-	 * query the ConfMan singleton for the target, gameid, path etc. data.
-	 *
-	 * @param syst	Pointer to the global OSystem object
-	 * @param engine	Pointer to a pointer which the MetaEngine sets to
-	 *					the newly create Engine, or 0 in case of an error
-	 * @return		a Common::Error describing the error which occurred, or kNoError
-	 */
-	virtual Common::Error createInstance(OSystem *syst, Engine **engine) const = 0;
-
 	/**
 	 * Return a list of all save states associated with the given target.
 	 *
@@ -414,6 +402,19 @@ public:
  * the engine, while a MetaEngine will always build into the executable to be able to detect code.
  */
 class MetaEngineConnect : public PluginObject {
+public:
+	/**
+	 * Tries to instantiate an engine instance based on the settings of
+	 * the currently active ConfMan target. That is, the MetaEngine should
+	 * query the ConfMan singleton for the target, gameid, path etc. data.
+	 *
+	 * @param syst	Pointer to the global OSystem object
+	 * @param engine	Pointer to a pointer which the MetaEngine sets to
+	 *					the newly create Engine, or 0 in case of an error
+	 * @return		a Common::Error describing the error which occurred, or kNoError
+	 */
+	virtual Common::Error createInstance(OSystem *syst, Engine **engine) const = 0;
+
 };
 
 /**


Commit: e69d9c98a4caab485a70b1b6231f5a8fafda6d41
    https://github.com/scummvm/scummvm/commit/e69d9c98a4caab485a70b1b6231f5a8fafda6d41
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: AME: Move the subclass implemented method createInstance out of AME into AMEConnect.

- We have a default createInstance method overridden from MetaEngine from before in AME.
- So, just leave that as-is, and call the child class's function from there.
- Lastly, in AMEC - the generic createInstance is called, so we redirect it to call the one in the MetaEngine.
- Then, games can be run normally.

Changed paths:
    engines/advancedDetector.cpp
    engines/advancedDetector.h


diff --git a/engines/advancedDetector.cpp b/engines/advancedDetector.cpp
index 58b162805a..d48ff83da4 100644
--- a/engines/advancedDetector.cpp
+++ b/engines/advancedDetector.cpp
@@ -348,10 +348,23 @@ Common::Error AdvancedMetaEngine::createInstance(OSystem *syst, Engine **engine)
 
 	debug(2, "Running %s", gameDescriptor.description.c_str());
 	initSubSystems(agdDesc.desc);
-	if (!createInstance(syst, engine, agdDesc.desc))
-		return Common::kNoGameDataFoundError;
-	else
-		return Common::kNoError;
+
+	PluginList pl = EngineMan.getPlugins(PLUGIN_TYPE_ENGINE);
+	Plugin *plugin = nullptr;
+
+	// By this point of time, we should have only one plugin in memory.
+	if (pl.size() == 1) {
+		plugin = pl[0];
+	}
+
+	if (plugin) {
+		// Call child class's createInstanceMethod.
+		if (plugin->get<AdvancedMetaEngineConnect>().createInstance(syst, engine, agdDesc.desc)) {
+			return Common::Error(Common::kNoError);
+		}
+	}
+
+	return Common::Error(Common::kNoGameDataFoundError);
 }
 
 void AdvancedMetaEngine::composeFileHashMap(FileMap &allFiles, const Common::FSList &fslist, int depth, const Common::String &parentName) const {
@@ -632,3 +645,15 @@ void AdvancedMetaEngine::initSubSystems(const ADGameDescription *gameDesc) const
 	}
 #endif
 }
+
+Common::Error AdvancedMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+	PluginList pl = PluginMan.getPlugins(PLUGIN_TYPE_ENGINE);
+	if (pl.size() == 1) {
+		Plugin *metaEnginePlugin = PluginMan.giveMetaEngineFromEngine(pl[0]);
+		if (metaEnginePlugin) {
+			return metaEnginePlugin->get<AdvancedMetaEngine>().createInstance(syst, engine);
+		}
+	}
+
+	return Common::Error();
+}
diff --git a/engines/advancedDetector.h b/engines/advancedDetector.h
index 9be9d8e958..ef4bd9d6b8 100644
--- a/engines/advancedDetector.h
+++ b/engines/advancedDetector.h
@@ -258,14 +258,16 @@ public:
 
 	DetectedGames detectGames(const Common::FSList &fslist) const override;
 
-	virtual Common::Error createInstance(OSystem *syst, Engine **engine) const override;
+	/**
+	 * A generic createInstance.
+	 * For instantiating engine objects, this method is called first,
+	 * and then the subclass implemented createInstance is called from within.
+	 */
+	Common::Error createInstance(OSystem *syst, Engine **engine) const;
 
 	virtual const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
 
 protected:
-	// To be implemented by subclasses
-	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const = 0;
-
 	typedef Common::HashMap<Common::String, Common::FSNode, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> FileMap;
 
 	/**
@@ -326,6 +328,21 @@ protected:
  * A MetaEngineConnect implementation of AdvancedMetaEngine.
  */
 class AdvancedMetaEngineConnect : public MetaEngineConnect {
+public:
+	/**
+	 * Base createInstance for AMEC.
+	 * The AME provides a default createInstance which is called first, so we should invoke that
+	 * first.
+	 * By the point of time we call this, we assume that we only have one
+	 * plugin engine loaded in memory.
+	 */
+	virtual Common::Error createInstance(OSystem *syst, Engine **engine) const override;
+
+	/**
+	 * To be implemented by subclasses, which is called after we call the base
+	 * createInstance function above.
+	 */
+	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const = 0;
 };
 
 #endif


Commit: 575e77522ab94328d13a9583707dbd562d11a78a
    https://github.com/scummvm/scummvm/commit/575e77522ab94328d13a9583707dbd562d11a78a
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: MAIN: Change how running games works.

- In runGame(), in main.cpp, we get a plugin of type MetaEngine.
- This MetaEngine cannot createInstances, but it just a helper class.
- Connect a MetaEngine class with it's factory class - MetaEngineConnect.
- Then, simply call the method.

Changed paths:
    base/main.cpp


diff --git a/base/main.cpp b/base/main.cpp
index e378887f82..eb7f6ef419 100644
--- a/base/main.cpp
+++ b/base/main.cpp
@@ -187,7 +187,15 @@ static Common::Error runGame(const Plugin *plugin, OSystem &system, const Common
 		// need to set this up before instance creation.
 		metaEngine.registerDefaultSettings(target);
 
-		err = metaEngine.createInstance(&system, &engine);
+		// Right now we have a MetaEngine plugin. We must find the matching engine plugin to
+		// call createInstance and other connecting functions.
+		Plugin *enginePluginToLaunchGame = PluginMan.giveEngineFromMetaEngine(plugin);
+
+		if (enginePluginToLaunchGame) {
+			err = enginePluginToLaunchGame->get<MetaEngineConnect>().createInstance(&system, &engine);
+		} else {
+			err = Common::Error(Common::kEnginePluginNotFound);
+		}
 	}
 
 	// Check for errors


Commit: a73858a3df4df21f07fc294f9bc2c667b8442f52
    https://github.com/scummvm/scummvm/commit/a73858a3df4df21f07fc294f9bc2c667b8442f52
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: MEC & AMEC: Provide notes for getName().

- If classes inherting provide the same name here as they did in the relevant MetaEngine, we can easily match a Engine with MetaEngine.

Changed paths:
    engines/advancedDetector.h
    engines/metaengine.h


diff --git a/engines/advancedDetector.h b/engines/advancedDetector.h
index ef4bd9d6b8..d4fd4f686c 100644
--- a/engines/advancedDetector.h
+++ b/engines/advancedDetector.h
@@ -343,6 +343,13 @@ public:
 	 * createInstance function above.
 	 */
 	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const = 0;
+
+	/**
+	 * Provide the engineID here, must match the one from MetaEngine.
+	 *
+	 * @see MetaEngineConnect::getName().
+	 */
+	virtual const char *getName() const = 0;
 };
 
 #endif
diff --git a/engines/metaengine.h b/engines/metaengine.h
index 32e6af3645..f22bb3b04c 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -415,6 +415,15 @@ public:
 	 */
 	virtual Common::Error createInstance(OSystem *syst, Engine **engine) const = 0;
 
+	/**
+	 * Name of the engine plugin.
+	 * Classes inheriting a MetaEngineConnect must provide a engineID here,
+	 * which can then be used to match an Engine with MetaEngine.
+	 * E.g. ScummMetaEngine inherits MetaEngine & provides a engineID of "Scumm".
+	 * 		ScummMetaEngineConnect inherits MetaEngineConnect & provides the name "Scumm".
+	 * This way, we can easily match a Engine with a MetaEngine.
+	 */
+	virtual const char *getName() const = 0;
 };
 
 /**


Commit: f2dd03e7d8ef4c48faf1b480a0b3a88374771f3d
    https://github.com/scummvm/scummvm/commit/f2dd03e7d8ef4c48faf1b480a0b3a88374771f3d
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Implement a getEngineId for PluginObjects, return nullptr by default.

- See comments.

Changed paths:
    base/plugins.cpp
    base/plugins.h


diff --git a/base/plugins.cpp b/base/plugins.cpp
index 441fddc79e..f07e67e7b5 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -49,6 +49,14 @@ const char *Plugin::getName() const {
 	return _pluginObject->getName();
 }
 
+const char *Plugin::getEngineId() const {
+	if (_type == PLUGIN_TYPE_METAENGINE) {
+		return _pluginObject->getEngineId();
+	}
+
+	return nullptr;
+}
+
 class StaticPlugin : public Plugin {
 public:
 	StaticPlugin(PluginObject *pluginobject, PluginType type) {
diff --git a/base/plugins.h b/base/plugins.h
index b0607dd0e0..159b17bc58 100644
--- a/base/plugins.h
+++ b/base/plugins.h
@@ -152,6 +152,18 @@ public:
 
 	/** Returns the name of the plugin. */
 	virtual const char *getName() const = 0;
+
+	/**
+	 * Returns the engine id of the plugin, if implemented.
+	 * This mostly has the use with MetaEngines, but if another
+	 * type of plugins request this, we return a nullptr.
+	 * This is used because MetaEngines are now available in the
+	 * executable, and querying this we can match a MetaEngine
+	 * with it's related engine.
+	 */
+	virtual const char *getEngineId() const {
+		return nullptr;
+	}
 };
 
 /**
@@ -182,6 +194,7 @@ public:
 	 **/
 	PluginType getType() const;
 	const char *getName() const;
+	const char *getEngineId() const;
 
 	template <class T>
 	T &get() const {


Commit: 50e9f0d87585bb99bff6442d661b9c971575d5d1
    https://github.com/scummvm/scummvm/commit/50e9f0d87585bb99bff6442d661b9c971575d5d1
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Add helper methods which match MetaEngine to Engine & vice-versa

Changed paths:
    base/plugins.cpp
    base/plugins.h


diff --git a/base/plugins.cpp b/base/plugins.cpp
index f07e67e7b5..7d5e80aaeb 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -266,6 +266,65 @@ void PluginManager::addPluginProvider(PluginProvider *pp) {
 	_providers.push_back(pp);
 }
 
+Plugin *PluginManager::giveEngineFromMetaEngine(const Plugin *plugin) {
+	assert(plugin->getType() == PLUGIN_TYPE_METAENGINE);
+
+	PluginList pl = PluginMan.getPlugins(PLUGIN_TYPE_ENGINE);
+	Plugin *enginePlugin = nullptr;
+
+	// Use the engineID from MetaEngine for comparasion.
+	Common::String metaEnginePluginName = plugin->getEngineId();
+
+	// Iterate over all engine plugins.
+	for (PluginList::const_iterator itr = pl.begin(); itr != pl.end(); itr++) {
+		// The getName() provides a name which is similiar to getEngineId.
+		// Because engines are engines themselves, this function is simply named getName.
+		Common::String enginePluginName((*itr)->getName());
+
+		if (metaEnginePluginName.equalsIgnoreCase(enginePluginName)) {
+			enginePlugin = (*itr);
+			break;
+		}
+	}
+
+	if (enginePlugin) {
+		warning("MetaEngine: %s \t matched to \t Engine: %s", plugin->getName(), enginePlugin->getFileName());
+		return enginePlugin;
+	}
+
+	warning("MetaEngine: %s couldn't find a match for an engine plugin.", plugin->getName());
+	return nullptr;
+}
+
+Plugin *PluginManager::giveMetaEngineFromEngine(const Plugin *plugin) {
+	assert(plugin->getType() == PLUGIN_TYPE_ENGINE);
+
+	Plugin *metaEngine = nullptr;
+
+	PluginList pl = PluginMan.getPlugins(PLUGIN_TYPE_METAENGINE);
+
+	// This will return a name of the Engine plugin, which will be identical to
+	// a getEngineID from a relevant MetaEngine.
+	Common::String enginePluginName(plugin->getName());
+
+	for (PluginList::const_iterator itr = pl.begin(); itr != pl.end(); itr++) {
+		Common::String metaEngineName = (*itr)->getEngineId();
+
+		if (metaEngineName.equalsIgnoreCase(enginePluginName)) {
+			metaEngine = (*itr);
+			break;
+		}
+	}
+
+	if (metaEngine) {
+		warning("Engine: %s matched to MetaEngine: %s", plugin->getFileName(), metaEngine->getName());
+		return metaEngine;
+	}
+
+	warning("Engine: %s couldn't find a match for an MetaEngine plugin.", plugin->getFileName());
+	return nullptr;
+}
+
 /**
  * This should only be called once by main()
  **/
diff --git a/base/plugins.h b/base/plugins.h
index 159b17bc58..043289fc36 100644
--- a/base/plugins.h
+++ b/base/plugins.h
@@ -326,6 +326,30 @@ public:
 
 	void addPluginProvider(PluginProvider *pp);
 
+	/**
+	 * A method which takes in a plugin of type ENGINE,
+	 * and returns the appropriate & matching METAENGINE.
+	 * It uses the Engine plugin's getName method, which is an identifier,
+	 * and then tries to matches it with each plugin present in memory.
+	 *
+	 * @param A plugin of type ENGINE.
+	 *
+	 * @return A plugin of type METAENGINE.
+	 */
+	Plugin *giveMetaEngineFromEngine(const Plugin *plugin);
+
+	/**
+	 * A method which takes in a plugin of type METAENGINE,
+	 * and returns the appropriate & matching ENGINE.
+	 * It uses the MetaEngine's getEngineID to reconstruct the name
+	 * of engine plugin, and then tries to matches it with each plugin in memory.
+	 *
+	 * @param A plugin of type METAENGINE.
+	 *
+	 * @return A plugin of type ENGINE.
+	 */
+	Plugin *giveEngineFromMetaEngine(const Plugin *plugin);
+
 	// Functions used by the uncached PluginManager
 	virtual void init()	{}
 	virtual void loadFirstPlugin() {}


Commit: 39f5c93c5c328f9afe632aafa31763eb3e7be198
    https://github.com/scummvm/scummvm/commit/39f5c93c5c328f9afe632aafa31763eb3e7be198
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Bump PLUGIN_TYPE_ENGINE_VERSION to 2

- Because of the many changes happening to engine classes, it would be a good idea to update the version, something similiar was done with themes.

Changed paths:
    base/plugins.h


diff --git a/base/plugins.h b/base/plugins.h
index 043289fc36..9f2674b33f 100644
--- a/base/plugins.h
+++ b/base/plugins.h
@@ -71,7 +71,7 @@ enum PluginType {
 // TODO: Make the engine API version depend on ScummVM's version
 // because of the backlinking (posibly from the checkout revision)
 #define PLUGIN_TYPE_METAENGINE_VERSION 1
-#define PLUGIN_TYPE_ENGINE_VERSION 1
+#define PLUGIN_TYPE_ENGINE_VERSION 2
 #define PLUGIN_TYPE_MUSIC_VERSION 1
 
 extern int pluginTypeVersions[PLUGIN_TYPE_MAX];


Commit: 9c67225293e002b74d05a5244254d23d1f61ce4e
    https://github.com/scummvm/scummvm/commit/9c67225293e002b74d05a5244254d23d1f61ce4e
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
COMMON: ERROR: Add kMetaEnginePluginNotFound

Changed paths:
    common/error.h


diff --git a/common/error.h b/common/error.h
index 00495e06b2..90bc12ae67 100644
--- a/common/error.h
+++ b/common/error.h
@@ -60,7 +60,12 @@ enum ErrorCode {
 	kWritingFailed,				///< Failure to write data -- disk full?
 
 	// The following are used by --list-saves
-	kEnginePluginNotFound,		///< Failed to find plugin to handle target
+
+	// Failed to find a MetaEnginePlugin. This should never happen, because all MetaEngines must always
+	// be built into the executable, regardless if the engine plugins are present or not.
+	kMetaEnginePluginNotFound,	///< See comment above
+
+	kEnginePluginNotFound,		///< Failed to find a Engine plugin to handle target
 	kEnginePluginNotSupportSaves,	///< Failed if plugin does not support listing save states
 
 	kUserCanceled,			///< User has canceled the launching of the game


Commit: ce80c0c730b048baf47d7fcb6a48468bcd4ec97b
    https://github.com/scummvm/scummvm/commit/ce80c0c730b048baf47d7fcb6a48468bcd4ec97b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: Add a helper method - getMetaEngineConnect().

- Get a metaEngine plugin by querying the ConfMan.
- Next, use this MetaEngine to find a matching enginePlugin.
- Return the enginePlugin.

Changed paths:
    engines/engine.cpp
    engines/engine.h


diff --git a/engines/engine.cpp b/engines/engine.cpp
index 29daa66ecd..fd5add4f9d 100644
--- a/engines/engine.cpp
+++ b/engines/engine.cpp
@@ -871,6 +871,16 @@ MetaEngine &Engine::getMetaEngine() {
 	return plugin->get<MetaEngine>();
 }
 
+MetaEngineConnect &Engine::getMetaEngineConnect() {
+	const Plugin *metaEnginePlugin = EngineMan.findPlugin(ConfMan.get("engineid"));
+	assert(metaEnginePlugin);
+
+	const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+	assert(enginePlugin);
+
+	return enginePlugin->get<MetaEngineConnect>();
+}
+
 PauseToken::PauseToken() : _engine(nullptr) {}
 
 PauseToken::PauseToken(Engine *engine) : _engine(engine) {}
diff --git a/engines/engine.h b/engines/engine.h
index a5dde6b0b0..7a7402e055 100644
--- a/engines/engine.h
+++ b/engines/engine.h
@@ -32,6 +32,7 @@
 
 class OSystem;
 class MetaEngine;
+class MetaEngineConnect;
 
 namespace Audio {
 class Mixer;
@@ -379,6 +380,7 @@ public:
 	static bool shouldQuit();
 
 	static MetaEngine &getMetaEngine();
+	static MetaEngineConnect &getMetaEngineConnect();
 
 	/**
 	 * Pause the engine. This should stop any audio playback


Commit: 01efb65931ba641706c17d2d64160264c9f0e6f3
    https://github.com/scummvm/scummvm/commit/01efb65931ba641706c17d2d64160264c9f0e6f3
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: METAENGINE: Shift save/load related content to MetaEngineConnect

- These include various functions and functionalities related to save/load.
- These are shifted, because the MEC class will house things that can be dynamic in nature.
- The MetaEngine class is fully & only dependent on ScummVM code, so it can always be built into executable.

Changed paths:
    engines/metaengine.cpp
    engines/metaengine.h


diff --git a/engines/metaengine.cpp b/engines/metaengine.cpp
index 2a8bc127bf..4cc02fa33d 100644
--- a/engines/metaengine.cpp
+++ b/engines/metaengine.cpp
@@ -37,7 +37,7 @@
 #include "graphics/managed_surface.h"
 #include "graphics/thumbnail.h"
 
-Common::String MetaEngine::getSavegameFile(int saveGameIdx, const char *target) const {
+Common::String MetaEngineConnect::getSavegameFile(int saveGameIdx, const char *target) const {
 	if (saveGameIdx == kSavegameFilePattern) {
 		// Pattern requested
 		const char *pattern = hasFeature(kSavesUseExtendedFormat) ? "%s.###" : "%s.s##";
@@ -128,7 +128,7 @@ Common::KeymapArray MetaEngine::initKeymaps(const char *target) const {
 	return Keymap::arrayOf(engineKeyMap);
 }
 
-bool MetaEngine::hasFeature(MetaEngineFeature f) const {
+bool MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave) ||
@@ -140,7 +140,7 @@ bool MetaEngine::hasFeature(MetaEngineFeature f) const {
 		(f == kSavesUseExtendedFormat);
 }
 
-void MetaEngine::appendExtendedSave(Common::OutSaveFile *saveFile, uint32 playtime,
+void MetaEngineConnect::appendExtendedSave(Common::OutSaveFile *saveFile, uint32 playtime,
 		Common::String desc, bool isAutosave) {
 	ExtendedSavegameHeader header;
 
@@ -172,7 +172,7 @@ void MetaEngine::appendExtendedSave(Common::OutSaveFile *saveFile, uint32 playti
 	saveFile->finalize();
 }
 
-void MetaEngine::saveScreenThumbnail(Common::OutSaveFile *saveFile) {
+void MetaEngineConnect::saveScreenThumbnail(Common::OutSaveFile *saveFile) {
 	// Create a thumbnail surface from the screen
 	Graphics::Surface thumb;
 	::createThumbnailFromScreen(&thumb);
@@ -182,7 +182,7 @@ void MetaEngine::saveScreenThumbnail(Common::OutSaveFile *saveFile) {
 	thumb.free();
 }
 
-void MetaEngine::parseSavegameHeader(ExtendedSavegameHeader *header, SaveStateDescriptor *desc) {
+void MetaEngineConnect::parseSavegameHeader(ExtendedSavegameHeader *header, SaveStateDescriptor *desc) {
 	int day = (header->date >> 24) & 0xFF;
 	int month = (header->date >> 16) & 0xFF;
 	int year = header->date & 0xFFFF;
@@ -195,14 +195,14 @@ void MetaEngine::parseSavegameHeader(ExtendedSavegameHeader *header, SaveStateDe
 	desc->setDescription(header->description);
 }
 
-void MetaEngine::fillDummyHeader(ExtendedSavegameHeader *header) {
+void MetaEngineConnect::fillDummyHeader(ExtendedSavegameHeader *header) {
 	// This is wrong header, perhaps it is original savegame. Thus fill out dummy values
 	header->date = (20 << 24) | (9 << 16) | 2016;
 	header->time = (9 << 8) | 56;
 	header->playtime = 0;
 }
 
-WARN_UNUSED_RESULT bool MetaEngine::readSavegameHeader(Common::InSaveFile *in, ExtendedSavegameHeader *header, bool skipThumbnail) {
+WARN_UNUSED_RESULT bool MetaEngineConnect::readSavegameHeader(Common::InSaveFile *in, ExtendedSavegameHeader *header, bool skipThumbnail) {
 	uint oldPos = in->pos();
 
 	in->seek(-4, SEEK_END);
@@ -260,11 +260,11 @@ WARN_UNUSED_RESULT bool MetaEngine::readSavegameHeader(Common::InSaveFile *in, E
 }
 
 
-///////////////////////////////////////
-// MetaEngine default implementations
-///////////////////////////////////////
+//////////////////////////////////////////////
+// MetaEngineConnect default implementations
+//////////////////////////////////////////////
 
-SaveStateList MetaEngine::listSaves(const char *target) const {
+SaveStateList MetaEngineConnect::listSaves(const char *target) const {
 	if (!hasFeature(kSavesUseExtendedFormat))
 		return SaveStateList();
 
@@ -305,7 +305,7 @@ SaveStateList MetaEngine::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateList MetaEngine::listSaves(const char *target, bool saveMode) const {
+SaveStateList MetaEngineConnect::listSaves(const char *target, bool saveMode) const {
 	SaveStateList saveList = listSaves(target);
 	int autosaveSlot = ConfMan.getInt("autosave_period") ? getAutosaveSlot() : -1;
 	if (!saveMode || autosaveSlot == -1)
@@ -354,14 +354,14 @@ GUI::OptionsContainerWidget *MetaEngine::buildEngineOptionsWidget(GUI::GuiObject
 	return new GUI::ExtraGuiOptionsWidget(boss, name, target, engineOptions);
 }
 
-void MetaEngine::removeSaveState(const char *target, int slot) const {
+void MetaEngineConnect::removeSaveState(const char *target, int slot) const {
 	if (!hasFeature(kSavesUseExtendedFormat))
 		return;
 
 	g_system->getSavefileManager()->removeSavefile(getSavegameFile(slot, target));
 }
 
-SaveStateDescriptor MetaEngine::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor MetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
 	if (!hasFeature(kSavesUseExtendedFormat))
 		return SaveStateDescriptor();
 
diff --git a/engines/metaengine.h b/engines/metaengine.h
index f22bb3b04c..9089a2def9 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -103,11 +103,6 @@ struct ExtendedSavegameHeader {
  * See the class MetaEngineConnect below.
  */
 class MetaEngine : public PluginObject {
-private:
-	/**
-	 * Converts the current screen contents to a thumbnail, and saves it
-	 */
-	static void saveScreenThumbnail(Common::OutSaveFile *saveFile);
 public:
 	virtual ~MetaEngine() {}
 
@@ -130,46 +125,6 @@ public:
 	 */
 	virtual DetectedGames detectGames(const Common::FSList &fslist) const = 0;
 
-	/**
-	 * Return a list of all save states associated with the given target.
-	 *
-	 * The returned list is guaranteed to be sorted by slot numbers. That
-	 * means smaller slot numbers are always stored before bigger slot numbers.
-	 *
-	 * The caller has to ensure that this (Meta)Engine is responsible
-	 * for the specified target (by using findGame on it respectively
-	 * on the associated gameid from the relevant ConfMan entry, if present).
-	 *
-	 * The default implementation returns an empty list.
-	 *
-	 * @note MetaEngines must indicate that this function has been implemented
-	 *       via the kSupportsListSaves feature flag.
-	 *
-	 * @param target	name of a config manager target
-	 * @return			a list of save state descriptors
-	 */
-	virtual SaveStateList listSaves(const char *target) const;
-
-	/**
-	 * Return a list of all save states associated with the given target.
-	 *
-	 * This is a wrapper around the basic listSaves virtual method, but which
-	 * has some extra logic for autosave handling
-	 *
-	 * @param target	name of a config manager target
-	 * @param saveMode	If true, getting the list for a save dialog
-	 * @return			a list of save state descriptors
-	 */
-	SaveStateList listSaves(const char *target, bool saveMode) const;
-
-	/**
-	 * Returns the slot number being used for autosaves.
-	 * @note	This should match the engine getAutosaveSlot() method
-	 */
-	virtual int getAutosaveSlot() const {
-		return 0;
-	}
-
 	/**
 	 * Return a list of extra GUI options for the specified target.
 	 * If no target is specified, all of the available custom GUI options are
@@ -224,6 +179,92 @@ public:
 		return Common::AchievementsInfo();
 	}
 
+	/**
+	 * Return the keymap used by the target.
+	 */
+	virtual Common::Array<Common::Keymap *> initKeymaps(const char *target) const;
+};
+
+/**
+ * A MetaEngineConnect is another factory for Engine instances, and is very
+ * similiar to meta engines. This class, however, composes of bridged functionalities
+ * that can be used to connect an actual Engine with a MetaEngine.
+ * Every engine "plugin" provides a hook to get an instance of MetaEngineConnector subclass
+ * for that "engine plugin.". E.g. SCUMM provides a ScummMetaEngineConnect.
+ * This is then in turn used for things like instantiating engine objects, listing savefiles,
+ * querying save metadata, etc.
+ * Since engine plugins can be used a external runtime libraries, these can live and build inside
+ * the engine, while a MetaEngine will always build into the executable to be able to detect code.
+ */
+class MetaEngineConnect : public PluginObject {
+private:
+	/**
+	 * Converts the current screen contents to a thumbnail, and saves it
+	 */
+	static void saveScreenThumbnail(Common::OutSaveFile *saveFile);
+public:
+	/**
+	 * Name of the engine plugin.
+	 * Classes inheriting a MetaEngineConnect must provide a engineID here,
+	 * which can then be used to match an Engine with MetaEngine.
+	 * E.g. ScummMetaEngine inherits MetaEngine & provides a engineID of "Scumm".
+	 * 		ScummMetaEngineConnect inherits MetaEngineConnect & provides the name "Scumm".
+	 * This way, we can easily match a Engine with a MetaEngine.
+	 */
+	virtual const char *getName() const = 0;
+
+	/**
+	 * Tries to instantiate an engine instance based on the settings of
+	 * the currently active ConfMan target. That is, the MetaEngine should
+	 * query the ConfMan singleton for the target, gameid, path etc. data.
+	 *
+	 * @param syst	Pointer to the global OSystem object
+	 * @param engine	Pointer to a pointer which the MetaEngine sets to
+	 *					the newly create Engine, or 0 in case of an error
+	 * @return		a Common::Error describing the error which occurred, or kNoError
+	 */
+	virtual Common::Error createInstance(OSystem *syst, Engine **engine) const = 0;
+
+	/**
+	 * Return a list of all save states associated with the given target.
+	 *
+	 * The returned list is guaranteed to be sorted by slot numbers. That
+	 * means smaller slot numbers are always stored before bigger slot numbers.
+	 *
+	 * The caller has to ensure that this (Meta)Engine is responsible
+	 * for the specified target (by using findGame on it respectively
+	 * on the associated gameid from the relevant ConfMan entry, if present).
+	 *
+	 * The default implementation returns an empty list.
+	 *
+	 * @note MetaEngines must indicate that this function has been implemented
+	 *       via the kSupportsListSaves feature flag.
+	 *
+	 * @param target	name of a config manager target
+	 * @return			a list of save state descriptors
+	 */
+	virtual SaveStateList listSaves(const char *target) const;
+
+	/**
+	 * Return a list of all save states associated with the given target.
+	 *
+	 * This is a wrapper around the basic listSaves virtual method, but which
+	 * has some extra logic for autosave handling
+	 *
+	 * @param target	name of a config manager target
+	 * @param saveMode	If true, getting the list for a save dialog
+	 * @return			a list of save state descriptors
+	 */
+	SaveStateList listSaves(const char *target, bool saveMode) const;
+
+	/**
+	 * Returns the slot number being used for autosaves.
+	 * @note	This should match the engine getAutosaveSlot() method
+	 */
+	virtual int getAutosaveSlot() const {
+		return 0;
+	}
+
 	/**
 	 * Return the maximum save slot that the engine supports.
 	 *
@@ -283,11 +324,6 @@ public:
 		return getSavegameFile(kSavegameFilePattern, target);
 	}
 
-	/**
-	 * Return the keymap used by the target.
-	 */
-	virtual Common::Array<Common::Keymap *> initKeymaps(const char *target) const;
-
 	/** @name MetaEngineFeature flags */
 	//@{
 
@@ -375,55 +411,18 @@ public:
 		kSavesUseExtendedFormat
 	};
 
+	//@}
+
 	/**
 	 * Determine whether the engine supports the specified MetaEngine feature.
 	 * Used by e.g. the launcher to determine whether to enable the "Load" button.
 	 */
 	virtual bool hasFeature(MetaEngineFeature f) const;
 
-	static void appendExtendedSave(Common::OutSaveFile *saveFile, uint32 playtime,
-		Common::String desc, bool isAutosave);
+	static void appendExtendedSave(Common::OutSaveFile *saveFile, uint32 playtime, Common::String desc, bool isAutosave);
 	static void parseSavegameHeader(ExtendedSavegameHeader *header, SaveStateDescriptor *desc);
 	static void fillDummyHeader(ExtendedSavegameHeader *header);
 	static WARN_UNUSED_RESULT bool readSavegameHeader(Common::InSaveFile *in, ExtendedSavegameHeader *header, bool skipThumbnail = true);
-
-	//@}
-};
-
-/**
- * A MetaEngineConnect is another factory for Engine instances, and is very
- * similiar to meta engines. This class, however, composes of bridged functionalities
- * that can be used to connect an actual Engine with a MetaEngine.
- * Every engine "plugin" provides a hook to get an instance of MetaEngineConnector subclass
- * for that "engine plugin.". E.g. SCUMM provides a ScummMetaEngineConnect.
- * This is then in turn used for things like instantiating engine objects, listing savefiles,
- * querying save metadata, etc.
- * Since engine plugins can be used a external runtime libraries, these can live and build inside
- * the engine, while a MetaEngine will always build into the executable to be able to detect code.
- */
-class MetaEngineConnect : public PluginObject {
-public:
-	/**
-	 * Tries to instantiate an engine instance based on the settings of
-	 * the currently active ConfMan target. That is, the MetaEngine should
-	 * query the ConfMan singleton for the target, gameid, path etc. data.
-	 *
-	 * @param syst	Pointer to the global OSystem object
-	 * @param engine	Pointer to a pointer which the MetaEngine sets to
-	 *					the newly create Engine, or 0 in case of an error
-	 * @return		a Common::Error describing the error which occurred, or kNoError
-	 */
-	virtual Common::Error createInstance(OSystem *syst, Engine **engine) const = 0;
-
-	/**
-	 * Name of the engine plugin.
-	 * Classes inheriting a MetaEngineConnect must provide a engineID here,
-	 * which can then be used to match an Engine with MetaEngine.
-	 * E.g. ScummMetaEngine inherits MetaEngine & provides a engineID of "Scumm".
-	 * 		ScummMetaEngineConnect inherits MetaEngineConnect & provides the name "Scumm".
-	 * This way, we can easily match a Engine with a MetaEngine.
-	 */
-	virtual const char *getName() const = 0;
 };
 
 /**


Commit: 73cc973ad7000317a5f918a67a784ab3202e7580
    https://github.com/scummvm/scummvm/commit/73cc973ad7000317a5f918a67a784ab3202e7580
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: ENGINES: Change saveload code to adapt to the new MEC class.

- MEC: MetaEngineConnect.
- How do games handle save/load if MetaEngine (detection) is seperate from MetaEngineConnect (engine factory)?

- Most of the changes are quite similiar. ConfMan finds us the relevant MetaEngine, then simply use the new helpers from PluginMan.
- The new helpers will help convert a relevant MetaEngine into the other format or vice versa.
- Once the matching is complete, simply invoke functions by:
plugin->get<MetaEngineConnect>().engineMethod();
- Refer to previous commits to see the new class changes & notes.

Changed paths:
    base/commandLine.cpp
    engines/engine.cpp
    gui/launcher.cpp
    gui/saveload-dialog.cpp
    gui/saveload-dialog.h
    gui/saveload.cpp
    gui/saveload.h


diff --git a/base/commandLine.cpp b/base/commandLine.cpp
index c52f280a31..d2b8ad3314 100644
--- a/base/commandLine.cpp
+++ b/base/commandLine.cpp
@@ -867,15 +867,18 @@ static Common::Error listSaves(const Common::String &singleTarget) {
 		// the specified game name, or alternatively whether there is a matching game id.
 		Common::String currentTarget;
 		QualifiedGameDescriptor game;
-		const Plugin *plugin = nullptr;
+
+		const Plugin *metaEnginePlugin = nullptr;
+		const Plugin *enginePlugin = nullptr;
+
 		if (ConfMan.hasGameDomain(*i)) {
 			// The name is a known target
 			currentTarget = *i;
 			EngineMan.upgradeTargetIfNecessary(*i);
-			game = EngineMan.findTarget(*i, &plugin);
+			game = EngineMan.findTarget(*i, &metaEnginePlugin);
 		} else if (game = findGameMatchingName(*i), !game.gameId.empty()) {
 			// The name is a known game id
-			plugin = EngineMan.findPlugin(game.engineId);
+			metaEnginePlugin = EngineMan.findPlugin(game.engineId);
 			currentTarget = createTemporaryTarget(game.engineId, game.gameId);
 		} else {
 			return Common::Error(Common::kEnginePluginNotFound, Common::String::format("target '%s'", singleTarget.c_str()));
@@ -884,19 +887,30 @@ static Common::Error listSaves(const Common::String &singleTarget) {
 		// If we actually found a domain, we're going to change the domain
 		ConfMan.setActiveDomain(currentTarget);
 
-		if (!plugin) {
+		if (!metaEnginePlugin) {
 			// If the target was specified, treat this as an error, and otherwise skip it.
 			if (!singleTarget.empty())
-				return Common::Error(Common::kEnginePluginNotFound,
+				return Common::Error(Common::kMetaEnginePluginNotFound,
 				                     Common::String::format("target '%s'", i->c_str()));
-			printf("Plugin could not be loaded for target '%s'\n", i->c_str());
+			printf("MetaEnginePlugin could not be loaded for target '%s'\n", i->c_str());
 			continue;
+		} else {
+			enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+
+			if (!enginePlugin) {
+				// If the target was specified, treat this as an error, and otherwise skip it.
+				if (!singleTarget.empty())
+					return Common::Error(Common::kEnginePluginNotFound,
+				                     	 Common::String::format("target '%s'", i->c_str()));
+				printf("EnginePlugin could not be loaded for target '%s'\n", i->c_str());
+				continue;
+			}
 		}
 
-		const MetaEngine &metaEngine = plugin->get<MetaEngine>();
+		const MetaEngineConnect &metaEngine = enginePlugin->get<MetaEngineConnect>();
 		Common::String qualifiedGameId = buildQualifiedGameName(game.engineId, game.gameId);
 
-		if (!metaEngine.hasFeature(MetaEngine::kSupportsListSaves)) {
+		if (!metaEngine.hasFeature(MetaEngineConnect::kSupportsListSaves)) {
 			// If the target was specified, treat this as an error, and otherwise skip it.
 			if (!singleTarget.empty())
 				// TODO: Include more info about the target (desc, engine name, ...) ???
diff --git a/engines/engine.cpp b/engines/engine.cpp
index fd5add4f9d..dd14db771e 100644
--- a/engines/engine.cpp
+++ b/engines/engine.cpp
@@ -531,7 +531,7 @@ void Engine::saveAutosaveIfEnabled() {
 
 		if (saveFlag) {
 			// First check for an existing savegame in the slot, and if present, if it's an autosave
-			SaveStateDescriptor desc = getMetaEngine().querySaveMetaInfos(
+			SaveStateDescriptor desc = getMetaEngineConnect().querySaveMetaInfos(
 				_targetName.c_str(), getAutosaveSlot());
 			saveFlag = desc.getSaveSlot() == -1 || desc.isAutosave();
 		}
@@ -731,7 +731,7 @@ Common::Error Engine::loadGameState(int slot) {
 	Common::Error result = loadGameStream(saveFile);
 	if (result.getCode() == Common::kNoError) {
 		ExtendedSavegameHeader header;
-		if (MetaEngine::readSavegameHeader(saveFile, &header))
+		if (MetaEngineConnect::readSavegameHeader(saveFile, &header))
 			setTotalPlayTime(header.playtime);
 	}
 
@@ -757,7 +757,7 @@ Common::Error Engine::saveGameState(int slot, const Common::String &desc, bool i
 
 	Common::Error result = saveGameStream(saveFile, isAutosave);
 	if (result.getCode() == Common::kNoError) {
-		MetaEngine::appendExtendedSave(saveFile, getTotalPlayTime() / 1000, desc, isAutosave);
+		MetaEngineConnect::appendExtendedSave(saveFile, getTotalPlayTime() / 1000, desc, isAutosave);
 
 		saveFile->finalize();
 	}
diff --git a/gui/launcher.cpp b/gui/launcher.cpp
index 9135c05814..87f5866bb1 100644
--- a/gui/launcher.cpp
+++ b/gui/launcher.cpp
@@ -469,14 +469,20 @@ void LauncherDialog::loadGame(int item) {
 	EngineMan.upgradeTargetIfNecessary(target);
 
 	// Look for the plugin
-	const Plugin *plugin = nullptr;
-	EngineMan.findTarget(target, &plugin);
-
-	if (plugin) {
-		const MetaEngine &metaEngine = plugin->get<MetaEngine>();
-		if (metaEngine.hasFeature(MetaEngine::kSupportsListSaves) &&
-			metaEngine.hasFeature(MetaEngine::kSupportsLoadingDuringStartup)) {
-			int slot = _loadDialog->runModalWithPluginAndTarget(plugin, target);
+	const Plugin *metaEnginePlugin = nullptr;
+	const Plugin *enginePlugin = nullptr;
+	EngineMan.findTarget(target, &metaEnginePlugin);
+
+	// If we found a relevant plugin, find the matching engine plugin.
+	if (metaEnginePlugin) {
+		enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+	}
+
+	if (enginePlugin) {
+		const MetaEngineConnect &metaEngineConnect = enginePlugin->get<MetaEngineConnect>();
+		if (metaEngineConnect.hasFeature(MetaEngineConnect::kSupportsListSaves) &&
+			metaEngineConnect.hasFeature(MetaEngineConnect::kSupportsLoadingDuringStartup)) {
+			int slot = _loadDialog->runModalWithPluginAndTarget(enginePlugin, target);
 			if (slot >= 0) {
 				ConfMan.setActiveDomain(_domains[item]);
 				ConfMan.setInt("save_slot", slot, Common::ConfigManager::kTransientDomain);
diff --git a/gui/saveload-dialog.cpp b/gui/saveload-dialog.cpp
index 54a8e2539b..894529233a 100644
--- a/gui/saveload-dialog.cpp
+++ b/gui/saveload-dialog.cpp
@@ -103,7 +103,7 @@ void SaveLoadCloudSyncProgressDialog::handleTickle() {
 #endif
 
 #ifndef DISABLE_SAVELOADCHOOSER_GRID
-SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngine &metaEngine) {
+SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngineConnect &metaEngine) {
 	const Common::String &userConfig = ConfMan.get("gui_saveload_chooser", Common::ConfigManager::kApplicationDomain);
 
 	// Check (and update if necessary) the theme config here. This catches
@@ -114,8 +114,8 @@ SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngine &metaEngine) {
 	g_gui.checkScreenChange();
 
 	if (g_gui.getWidth() >= 640 && g_gui.getHeight() >= 400
-		&& metaEngine.hasFeature(MetaEngine::kSavesSupportMetaInfo)
-		&& metaEngine.hasFeature(MetaEngine::kSavesSupportThumbnail)
+		&& metaEngine.hasFeature(MetaEngineConnect::kSavesSupportMetaInfo)
+		&& metaEngine.hasFeature(MetaEngineConnect::kSavesSupportThumbnail)
 		&& userConfig.equalsIgnoreCase("grid")) {
 		// In case we are 640x400 or higher, this dialog is not in save mode,
 		// the user requested the grid dialog and the engines supports it we
@@ -182,14 +182,14 @@ void SaveLoadChooserDialog::close() {
 	Dialog::close();
 }
 
-int SaveLoadChooserDialog::run(const Common::String &target, const MetaEngine *metaEngine) {
+int SaveLoadChooserDialog::run(const Common::String &target, const MetaEngineConnect *metaEngine) {
 	_metaEngine = metaEngine;
 	_target = target;
-	_delSupport = _metaEngine->hasFeature(MetaEngine::kSupportsDeleteSave);
-	_metaInfoSupport = _metaEngine->hasFeature(MetaEngine::kSavesSupportMetaInfo);
-	_thumbnailSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngine::kSavesSupportThumbnail);
-	_saveDateSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngine::kSavesSupportCreationDate);
-	_playTimeSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngine::kSavesSupportPlayTime);
+	_delSupport = _metaEngine->hasFeature(MetaEngineConnect::kSupportsDeleteSave);
+	_metaInfoSupport = _metaEngine->hasFeature(MetaEngineConnect::kSavesSupportMetaInfo);
+	_thumbnailSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngineConnect::kSavesSupportThumbnail);
+	_saveDateSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngineConnect::kSavesSupportCreationDate);
+	_playTimeSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngineConnect::kSavesSupportPlayTime);
 
 	return runIntern();
 }
diff --git a/gui/saveload-dialog.h b/gui/saveload-dialog.h
index aaea785b23..8ff5851ca7 100644
--- a/gui/saveload-dialog.h
+++ b/gui/saveload-dialog.h
@@ -65,7 +65,7 @@ enum SaveLoadChooserType {
 	kSaveLoadDialogGrid = 1
 };
 
-SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngine &metaEngine);
+SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngineConnect &metaEngine);
 #endif // !DISABLE_SAVELOADCHOOSER_GRID
 
 class SaveLoadChooserDialog : protected Dialog {
@@ -91,7 +91,7 @@ public:
 	virtual SaveLoadChooserType getType() const = 0;
 #endif // !DISABLE_SAVELOADCHOOSER_GRID
 
-	int run(const Common::String &target, const MetaEngine *metaEngine);
+	int run(const Common::String &target, const MetaEngineConnect *metaEngine);
 	virtual const Common::U32String &getResultString() const = 0;
 
 protected:
@@ -110,16 +110,16 @@ protected:
 	*/
 	virtual void listSaves();
 
-	const bool				_saveMode;
-	const MetaEngine		*_metaEngine;
-	bool					_delSupport;
-	bool					_metaInfoSupport;
-	bool					_thumbnailSupport;
-	bool					_saveDateSupport;
-	bool					_playTimeSupport;
-	Common::String			_target;
+	const bool					_saveMode;
+	const MetaEngineConnect		*_metaEngine;
+	bool						_delSupport;
+	bool						_metaInfoSupport;
+	bool						_thumbnailSupport;
+	bool						_saveDateSupport;
+	bool						_playTimeSupport;
+	Common::String				_target;
 	bool _dialogWasShown;
-	SaveStateList			_saveList;
+	SaveStateList				_saveList;
 
 #ifndef DISABLE_SAVELOADCHOOSER_GRID
 	ButtonWidget *_listButton;
diff --git a/gui/saveload.cpp b/gui/saveload.cpp
index f37d3ed57d..80680bf934 100644
--- a/gui/saveload.cpp
+++ b/gui/saveload.cpp
@@ -39,7 +39,7 @@ SaveLoadChooser::~SaveLoadChooser() {
 	_impl = nullptr;
 }
 
-void SaveLoadChooser::selectChooser(const MetaEngine &engine) {
+void SaveLoadChooser::selectChooser(const MetaEngineConnect &engine) {
 #ifndef DISABLE_SAVELOADCHOOSER_GRID
 	const SaveLoadChooserType requestedType = getRequestedSaveLoadDialog(engine);
 	if (!_impl || _impl->getType() != requestedType) {
@@ -77,14 +77,24 @@ Common::String SaveLoadChooser::createDefaultSaveDescription(const int slot) con
 
 int SaveLoadChooser::runModalWithCurrentTarget() {
 	const Plugin *plugin = EngineMan.findPlugin(ConfMan.get("engineid"));
+	const Plugin *enginePlugin = nullptr;
 	if (!plugin) {
 		error("SaveLoadChooser::runModalWithCurrentTarget(): Cannot find plugin");
+	} else {
+		enginePlugin = PluginMan.giveEngineFromMetaEngine(plugin);
+
+		if (!enginePlugin) {
+			error("SaveLoadChooser::runModalWithCurrentTarget(): Couldn't match a Engine from the MetaEngine. \
+				You will not be able to see savefiles until you have the necessary plugins.");
+		}
 	}
-	return runModalWithPluginAndTarget(plugin, ConfMan.getActiveDomainName());
+	return runModalWithPluginAndTarget(enginePlugin, ConfMan.getActiveDomainName());
 }
 
 int SaveLoadChooser::runModalWithPluginAndTarget(const Plugin *plugin, const String &target) {
-	selectChooser(plugin->get<MetaEngine>());
+	assert(plugin->getType() == PLUGIN_TYPE_ENGINE);
+
+	selectChooser(plugin->get<MetaEngineConnect>());
 	if (!_impl)
 		return -1;
 
@@ -99,10 +109,10 @@ int SaveLoadChooser::runModalWithPluginAndTarget(const Plugin *plugin, const Str
 
 	int ret;
 	do {
-		ret = _impl->run(target, &plugin->get<MetaEngine>());
+		ret = _impl->run(target, &plugin->get<MetaEngineConnect>());
 #ifndef DISABLE_SAVELOADCHOOSER_GRID
 		if (ret == kSwitchSaveLoadDialog) {
-			selectChooser(plugin->get<MetaEngine>());
+			selectChooser(plugin->get<MetaEngineConnect>());
 		}
 #endif // !DISABLE_SAVELOADCHOOSER_GRID
 	} while (ret < -1);
diff --git a/gui/saveload.h b/gui/saveload.h
index 3a976863d5..5591c04dc4 100644
--- a/gui/saveload.h
+++ b/gui/saveload.h
@@ -40,7 +40,7 @@ protected:
 	const U32String _buttonLabel;
 	const bool _saveMode;
 
-	void selectChooser(const MetaEngine &engine);
+	void selectChooser(const MetaEngineConnect &engine);
 public:
 	SaveLoadChooser(const U32String &title, const U32String &buttonLabel, bool saveMode);
 	~SaveLoadChooser();


Commit: bdafdf220dc4f97d5d861c6b94b9ba78e5166130
    https://github.com/scummvm/scummvm/commit/bdafdf220dc4f97d5d861c6b94b9ba78e5166130
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Deprecate improper usage of unloadPluginsExcept

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index 7d5e80aaeb..c236b4b066 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -491,73 +491,19 @@ void PluginManager::unloadPluginsExcept(PluginType type, const Plugin *plugin, b
 	// If someone calls this function with a nullptr Plugin, we clear everything, and no need to search
 	// for individual plugin.
 	if (plugin) {
-
-		if (type != plugin->getType() && type != PLUGIN_TYPE_ENGINE) {
+		if (type != plugin->getType()) {
 			warning("Plugins: unloadPluginExcept: mismatching type of plugins requested to unload. Operation not carried out.");
 			return;
 		}
 
-		Common::String enginePluginTitle("");
-		bool toDelete = false;
-
-		if (type == PLUGIN_TYPE_ENGINE) {
-			/**
-			 * We've got in a plugin of type MetaEngine, and we want to keep
-			 * the relevant plugin of Engine type in memory.
-			 * To do this, we first construct a name from the given MetaEngine.
-			 */
-
-#ifdef PLUGIN_PREFIX
-			enginePluginTitle += PLUGIN_PREFIX;
-#endif
-
-			enginePluginTitle += Common::String(plugin->getEngineId());
-
-#ifdef PLUGIN_SUFFIX
-			enginePluginTitle += PLUGIN_SUFFIX;
-#endif
-		}
-
 		for (PluginList::iterator p = _pluginsInMem[type].begin(); p != _pluginsInMem[type].end(); ++p) {
-			if (type == PLUGIN_TYPE_ENGINE) {
-				Common::String enginePluginFilename((*p)->getFileName());
-
-				/**
-				 * Take the ending of the filename, and subtract it with the size of enginePluginTitle.
-				 * This should effectively cancel out directory names and exactly leave the plugin filename
-				 * ONLY for the one we require. That's why we do a equals call.
-				 * Example: We got the request to unload engine of AGI, and were given a AGIMetaEngine.
-				 * So, plugins/agi.dll will beome agi.dll (fetched by getFileName) and will try
-				 * to match to our generated enginePluginTitle from the plugin we got. (A metaengine type plugin)
-				 * This will then pass the check and be the only one loaded in memory.
-				 */
-				if (enginePluginFilename.size() > enginePluginTitle.size()) {
-					Common::String::const_iterator beginItr = enginePluginFilename.end() - enginePluginTitle.size();
-					Common::String strippedFileName(beginItr, enginePluginFilename.end());
-
-					if (strippedFileName.equalsIgnoreCase(enginePluginTitle)) {
-						found = *p;
-					} else {
-						toDelete = true;
-					}
-				} else {
-					toDelete = true;
-				}
+			if (*p == plugin) {
+				found = *p;
 			} else {
-				// The type is something other than a engine type.
-				if (*p == plugin) {
-					found = *p;
-				} else {
-					toDelete = true;
-				}
-			}
-
-			if (toDelete) {
 				(*p)->unloadPlugin();
 				if (deletePlugin) {
 					delete *p;
 				}
-				toDelete = false;
 			}
 		}
 	}


Commit: 9353e339c6915574703b5a660aee47336dee3286
    https://github.com/scummvm/scummvm/commit/9353e339c6915574703b5a660aee47336dee3286
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: MAIN: Proper usage of unloadPluginsExcept before running a game.

Changed paths:
    base/main.cpp


diff --git a/base/main.cpp b/base/main.cpp
index eb7f6ef419..de8de6e87e 100644
--- a/base/main.cpp
+++ b/base/main.cpp
@@ -537,12 +537,17 @@ extern "C" int scummvm_main(int argc, const char * const argv[]) {
 
 		EngineMan.upgradeTargetIfNecessary(ConfMan.getActiveDomainName());
 
-		// Try to find a plugin which feels responsible for the specified game.
+		// Try to find a MetaEnginePlugin which feels responsible for the specified game.
 		const Plugin *plugin = detectPlugin();
 		if (plugin) {
-			// Unload all plugins not needed for this game,
-			// to save memory
-			PluginManager::instance().unloadPluginsExcept(PLUGIN_TYPE_ENGINE, plugin);
+			// Unload all plugins not needed for this game, to save memory
+
+			// Right now, we have a MetaEngine plugin, and we want to unload all except Engine.
+			// First, get the relevant Engine plugin from MetaEngine.
+			const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(plugin);
+
+			// Then, pass in the pointer to enginePlugin, with the matching type, so our function behaves as-is.
+			PluginManager::instance().unloadPluginsExcept(PLUGIN_TYPE_ENGINE, enginePlugin);
 
 #ifdef ENABLE_EVENTRECORDER
 			Common::String recordMode = ConfMan.get("record_mode");


Commit: 5d3292d84407f925710ae2269b1bdff50672cba6
    https://github.com/scummvm/scummvm/commit/5d3292d84407f925710ae2269b1bdff50672cba6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CONFIGURE: Update to properly support statically linked ScummVM.

- Since new engine classes cannot provide same ID for the 2 different types of MetaEngines, update the script to adjust for this behaviour.

Changed paths:
    configure


diff --git a/configure b/configure
index cc6c2ad4dd..f19ae8e0d6 100755
--- a/configure
+++ b/configure
@@ -6161,6 +6161,7 @@ EOF
 done
 
 declare -a static_detect_engines=()
+detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
 cat > engines/plugins_table.h << EOF
@@ -6176,13 +6177,18 @@ for engine in $_sorted_engines; do
 			if [ $j == $eng ]; then
 				cat >> engines/plugins_table.h << EOF
 #if PLUGIN_ENABLED($j)
+LINK_PLUGIN(${j}${detectId})
+#endif
+EOF
+				cat >> engines/plugins_table.h << EOF
+#if PLUGIN_ENABLED_STATIC($j)
 LINK_PLUGIN($j)
 #endif
 EOF
 				continue 2
 			fi
 		done
-		
+
 		cat >> engines/plugins_table.h << EOF
 #if PLUGIN_ENABLED_STATIC($j)
 LINK_PLUGIN($j)


Commit: fd1e333100af9f227f032e9134664edf2c973ad1
    https://github.com/scummvm/scummvm/commit/fd1e333100af9f227f032e9134664edf2c973ad1
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: METAENGINE: Move initKeymaps into MetaEngineConnect.

- Used by Sky, for example.

Changed paths:
    engines/metaengine.cpp
    engines/metaengine.h


diff --git a/engines/metaengine.cpp b/engines/metaengine.cpp
index 4cc02fa33d..aff0df47a0 100644
--- a/engines/metaengine.cpp
+++ b/engines/metaengine.cpp
@@ -49,7 +49,7 @@ Common::String MetaEngineConnect::getSavegameFile(int saveGameIdx, const char *t
 	}
 }
 
-Common::KeymapArray MetaEngine::initKeymaps(const char *target) const {
+Common::KeymapArray MetaEngineConnect::initKeymaps(const char *target) const {
 	using namespace Common;
 
 	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "engine-default", _("Default game keymap"));
diff --git a/engines/metaengine.h b/engines/metaengine.h
index 9089a2def9..bbc3ac4120 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -178,11 +178,6 @@ public:
 	virtual const Common::AchievementsInfo getAchievementsInfo(const Common::String &target) const {
 		return Common::AchievementsInfo();
 	}
-
-	/**
-	 * Return the keymap used by the target.
-	 */
-	virtual Common::Array<Common::Keymap *> initKeymaps(const char *target) const;
 };
 
 /**
@@ -324,6 +319,11 @@ public:
 		return getSavegameFile(kSavegameFilePattern, target);
 	}
 
+	/**
+	 * Return the keymap used by the target.
+	 */
+	virtual Common::Array<Common::Keymap *> initKeymaps(const char *target) const;
+
 	/** @name MetaEngineFeature flags */
 	//@{
 


Commit: 0cc8719417c90d2438c9787a225046f926373320
    https://github.com/scummvm/scummvm/commit/0cc8719417c90d2438c9787a225046f926373320
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: ENGINES: Adapt to keymaps moving to engine plugins

- Also improvise usage of MetaEngineConnect in main.cpp a bit.

Changed paths:
    base/main.cpp
    engines/dialogs.cpp
    gui/editgamedialog.cpp


diff --git a/base/main.cpp b/base/main.cpp
index de8de6e87e..942e45caa2 100644
--- a/base/main.cpp
+++ b/base/main.cpp
@@ -179,25 +179,28 @@ static Common::Error runGame(const Plugin *plugin, OSystem &system, const Common
 		err = Common::kPathNotDirectory;
 	}
 
-	// Create the game engine
+	// Create the game's MetaEngine.
 	const MetaEngine &metaEngine = plugin->get<MetaEngine>();
 	if (err.getCode() == Common::kNoError) {
 		// Set default values for all of the custom engine options
 		// Apparently some engines query them in their constructor, thus we
 		// need to set this up before instance creation.
 		metaEngine.registerDefaultSettings(target);
+	}
 
-		// Right now we have a MetaEngine plugin. We must find the matching engine plugin to
-		// call createInstance and other connecting functions.
-		Plugin *enginePluginToLaunchGame = PluginMan.giveEngineFromMetaEngine(plugin);
+	// Right now we have a MetaEngine plugin. We must find the matching engine plugin to
+	// call createInstance and other connecting functions.
+	Plugin *enginePluginToLaunchGame = PluginMan.giveEngineFromMetaEngine(plugin);
 
-		if (enginePluginToLaunchGame) {
-			err = enginePluginToLaunchGame->get<MetaEngineConnect>().createInstance(&system, &engine);
-		} else {
-			err = Common::Error(Common::kEnginePluginNotFound);
-		}
+	if (!enginePluginToLaunchGame) {
+		err = Common::kEnginePluginNotFound;
+		return err;
 	}
 
+	// Create the game's MetaEngineConnect.
+	const MetaEngineConnect &metaEngineConnect = enginePluginToLaunchGame->get<MetaEngineConnect>();
+	err = metaEngineConnect.createInstance(&system, &engine);
+
 	// Check for errors
 	if (!engine || err.getCode() != Common::kNoError) {
 
@@ -287,7 +290,7 @@ static Common::Error runGame(const Plugin *plugin, OSystem &system, const Common
 #endif // USE_TRANSLATION
 
 	// Initialize any game-specific keymaps
-	Common::KeymapArray gameKeymaps = metaEngine.initKeymaps(target.c_str());
+	Common::KeymapArray gameKeymaps = metaEngineConnect.initKeymaps(target.c_str());
 	Common::Keymapper *keymapper = system.getEventManager()->getKeymapper();
 	for (uint i = 0; i < gameKeymaps.size(); i++) {
 		keymapper->addGameKeymap(gameKeymaps[i]);
diff --git a/engines/dialogs.cpp b/engines/dialogs.cpp
index 80c91b52cc..8914b39c42 100644
--- a/engines/dialogs.cpp
+++ b/engines/dialogs.cpp
@@ -274,6 +274,7 @@ ConfigDialog::ConfigDialog() :
 
 	const Common::String &gameDomain = ConfMan.getActiveDomainName();
 	const MetaEngine &metaEngine = g_engine->getMetaEngine();
+	const MetaEngineConnect &metaEngineConnect = g_engine->getMetaEngineConnect();
 
 	// GUI:  Add tab widget
 	GUI::TabWidget *tab = new GUI::TabWidget(this, "GlobalConfig.TabWidget");
@@ -321,7 +322,7 @@ ConfigDialog::ConfigDialog() :
 	// The Keymap tab
 	//
 
-	Common::KeymapArray keymaps = metaEngine.initKeymaps(gameDomain.c_str());
+	Common::KeymapArray keymaps = metaEngineConnect.initKeymaps(gameDomain.c_str());
 	if (!keymaps.empty()) {
 		tab->addTab(_("Keymaps"), "GlobalConfig_KeyMapper");
 		addKeyMapperControls(tab, "GlobalConfig_KeyMapper.", keymaps, gameDomain);
diff --git a/gui/editgamedialog.cpp b/gui/editgamedialog.cpp
index 8ec1563a69..046338bb7b 100644
--- a/gui/editgamedialog.cpp
+++ b/gui/editgamedialog.cpp
@@ -109,10 +109,16 @@ EditGameDialog::EditGameDialog(const String &domain)
 
 	// Retrieve the plugin, since we need to access the engine's MetaEngine
 	// implementation.
-	const Plugin *plugin = nullptr;
-	QualifiedGameDescriptor qgd = EngineMan.findTarget(domain, &plugin);
-	if (!plugin) {
-		warning("Plugin for target \"%s\" not found! Game specific settings might be missing", domain.c_str());
+	const Plugin *metaEnginePlugin = nullptr;
+	const Plugin *enginePlugin = nullptr;
+	QualifiedGameDescriptor qgd = EngineMan.findTarget(domain, &metaEnginePlugin);
+	if (!metaEnginePlugin) {
+		warning("MetaEnginePlugin for target \"%s\" not found!", domain.c_str());
+	} else {
+		enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+		if (!enginePlugin) {
+			warning("Engine Plugin for target \"%s\" not found! Game specific settings might be missing.", domain.c_str());
+		}
 	}
 
 	// GAME: Path to game data (r/o), extra data (r/o), and save data (r/w)
@@ -176,10 +182,10 @@ EditGameDialog::EditGameDialog(const String &domain)
 	// 2) The engine tab (shown only if the engine implements one or there are custom engine options)
 	//
 
-	if (plugin) {
+	if (metaEnginePlugin) {
 		int tabId = tab->addTab(_("Engine"), "GameOptions_Engine");
 
-		const MetaEngine &metaEngine = plugin->get<MetaEngine>();
+		const MetaEngine &metaEngine = metaEnginePlugin->get<MetaEngine>();
 		metaEngine.registerDefaultSettings(_domain);
 		_engineOptions = metaEngine.buildEngineOptionsWidget(tab, "GameOptions_Engine.Container", _domain);
 
@@ -225,8 +231,8 @@ EditGameDialog::EditGameDialog(const String &domain)
 	// The Keymap tab
 	//
 	Common::KeymapArray keymaps;
-	if (plugin) {
-		keymaps = plugin->get<MetaEngine>().initKeymaps(domain.c_str());
+	if (enginePlugin) {
+		keymaps = enginePlugin->get<MetaEngineConnect>().initKeymaps(domain.c_str());
 	}
 
 	if (!keymaps.empty()) {
@@ -333,8 +339,8 @@ EditGameDialog::EditGameDialog(const String &domain)
 	//
 	// 9) The Achievements tab
 	//
-	if (plugin) {
-		const MetaEngine &metaEngine = plugin->get<MetaEngine>();
+	if (metaEnginePlugin) {
+		const MetaEngine &metaEngine = metaEnginePlugin->get<MetaEngine>();
 		Common::AchievementsInfo achievementsInfo = metaEngine.getAchievementsInfo(domain);
 		if (achievementsInfo.descriptions.size() > 0) {
 			tab->addTab(_("Achievements"), "GameOptions_Achievements");


Commit: 1616d7d5158d2e97f16bbf75c2942bb0ee0a5d99
    https://github.com/scummvm/scummvm/commit/1616d7d5158d2e97f16bbf75c2942bb0ee0a5d99
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: ME & MEC: Move achievements-related code to MetaEngineConnect

- Adjust accordingly for dialogs.

Changed paths:
    engines/dialogs.cpp
    engines/metaengine.h
    gui/editgamedialog.cpp


diff --git a/engines/dialogs.cpp b/engines/dialogs.cpp
index 8914b39c42..4bcecad4b7 100644
--- a/engines/dialogs.cpp
+++ b/engines/dialogs.cpp
@@ -331,7 +331,7 @@ ConfigDialog::ConfigDialog() :
 	//
 	// The Achievements tab
 	//
-	Common::AchievementsInfo achievementsInfo = metaEngine.getAchievementsInfo(gameDomain);
+	Common::AchievementsInfo achievementsInfo = metaEngineConnect.getAchievementsInfo(gameDomain);
 	if (achievementsInfo.descriptions.size() > 0) {
 		tab->addTab(_("Achievements"), "GlobalConfig_Achievements");
 		addAchievementsControls(tab, "GlobalConfig_Achievements.", achievementsInfo);
diff --git a/engines/metaengine.h b/engines/metaengine.h
index bbc3ac4120..376e3448bd 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -165,19 +165,6 @@ public:
 	 * @param target   name of a config manager target
 	 */
 	virtual GUI::OptionsContainerWidget *buildEngineOptionsWidget(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const;
-
-	/**
-	 * Return a list of achievement descriptions for the specified target.
-	 *
-	 * The default implementation returns an empty list.
-	 *
-	 * @param target    name of a config manager target
-	 * @return          a list of achievement descriptions for an engine plugin
-	 *                  and target
-	 */
-	virtual const Common::AchievementsInfo getAchievementsInfo(const Common::String &target) const {
-		return Common::AchievementsInfo();
-	}
 };
 
 /**
@@ -413,6 +400,19 @@ public:
 
 	//@}
 
+	/**
+	 * Return a list of achievement descriptions for the specified target.
+	 *
+	 * The default implementation returns an empty list.
+	 *
+	 * @param target    name of a config manager target
+	 * @return          a list of achievement descriptions for an engine plugin
+	 *                  and target
+	 */
+	virtual const Common::AchievementsInfo getAchievementsInfo(const Common::String &target) const {
+		return Common::AchievementsInfo();
+	}
+
 	/**
 	 * Determine whether the engine supports the specified MetaEngine feature.
 	 * Used by e.g. the launcher to determine whether to enable the "Load" button.
diff --git a/gui/editgamedialog.cpp b/gui/editgamedialog.cpp
index 046338bb7b..606c4c305c 100644
--- a/gui/editgamedialog.cpp
+++ b/gui/editgamedialog.cpp
@@ -339,9 +339,9 @@ EditGameDialog::EditGameDialog(const String &domain)
 	//
 	// 9) The Achievements tab
 	//
-	if (metaEnginePlugin) {
-		const MetaEngine &metaEngine = metaEnginePlugin->get<MetaEngine>();
-		Common::AchievementsInfo achievementsInfo = metaEngine.getAchievementsInfo(domain);
+	if (enginePlugin) {
+		const MetaEngineConnect &metaEngineConnect = enginePlugin->get<MetaEngineConnect>();
+		Common::AchievementsInfo achievementsInfo = metaEngineConnect.getAchievementsInfo(domain);
 		if (achievementsInfo.descriptions.size() > 0) {
 			tab->addTab(_("Achievements"), "GameOptions_Achievements");
 			addAchievementsControls(tab, "GameOptions_Achievements.", achievementsInfo);


Commit: 978901cc2f1a6dd3941d9f8479667db99a1ac115
    https://github.com/scummvm/scummvm/commit/978901cc2f1a6dd3941d9f8479667db99a1ac115
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PLUMBERS: Split detection code & adapt to new plugins.

- Detection related code, and the class MetaEngine lives in detection.cpp
- Things which require the engine to be loaded, are in metaengine.cpp - the relevant class is called MetaEngineConnect.
- Update modules for the necessary changes.

Changed paths:
  A engines/plumbers/metaengine.cpp
    configure
    engines/plumbers/detection.cpp
    engines/plumbers/module.mk


diff --git a/configure b/configure
index f19ae8e0d6..f0a79cd3f5 100755
--- a/configure
+++ b/configure
@@ -6160,7 +6160,7 @@ EOF
 	fi
 done
 
-declare -a static_detect_engines=()
+declare -a static_detect_engines=("PLUMBERS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/plumbers/detection.cpp b/engines/plumbers/detection.cpp
index 5b97c3dd14..435b0f1b68 100644
--- a/engines/plumbers/detection.cpp
+++ b/engines/plumbers/detection.cpp
@@ -20,16 +20,10 @@
  *
  */
 
-#include "plumbers/plumbers.h"
-
 #include "base/plugins.h"
 
 #include "engines/advancedDetector.h"
-
-namespace Plumbers {
-const char *PlumbersGame::getGameId() const { return _gameDescription->gameId; }
-Common::Platform PlumbersGame::getPlatform() const { return _gameDescription->platform; }
-}
+#include "engines/game.h"
 
 static const PlainGameDescriptor plumbersGames[] = {
 	{"plumbers", "Plumbers Don't Wear Ties!"},
@@ -84,24 +78,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Plumbers Don't Wear Ties (C) 1993-94 Kirin Entertainment";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool PlumbersMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return false;
-}
-
-bool PlumbersMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc)
-		*engine = new Plumbers::PlumbersGame(syst, desc);
-
-	return desc != nullptr;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(PLUMBERS)
-REGISTER_PLUGIN_DYNAMIC(PLUMBERS, PLUGIN_TYPE_ENGINE, PlumbersMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(PLUMBERS, PLUGIN_TYPE_ENGINE, PlumbersMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(PLUMBERS_DETECTION, PLUGIN_TYPE_METAENGINE, PlumbersMetaEngine);
diff --git a/engines/plumbers/metaengine.cpp b/engines/plumbers/metaengine.cpp
new file mode 100644
index 0000000000..a5c745c122
--- /dev/null
+++ b/engines/plumbers/metaengine.cpp
@@ -0,0 +1,58 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+
+#include "plumbers/plumbers.h"
+
+namespace Plumbers {
+const char *PlumbersGame::getGameId() const { return _gameDescription->gameId; }
+Common::Platform PlumbersGame::getPlatform() const { return _gameDescription->platform; }
+} // End of namespace Plumbers
+
+class PlumbersMetaEngineConnect : public AdvancedMetaEngineConnect {
+	const char *getName() const override {
+		return "plumbers";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+};
+
+bool PlumbersMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc)
+		*engine = new Plumbers::PlumbersGame(syst, desc);
+
+	return desc != nullptr;
+}
+
+bool PlumbersMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return false;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(PLUMBERS)
+	REGISTER_PLUGIN_DYNAMIC(PLUMBERS, PLUGIN_TYPE_ENGINE, PlumbersMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(PLUMBERS, PLUGIN_TYPE_ENGINE, PlumbersMetaEngineConnect);
+#endif
diff --git a/engines/plumbers/module.mk b/engines/plumbers/module.mk
index a8b246548a..63fde172d3 100644
--- a/engines/plumbers/module.mk
+++ b/engines/plumbers/module.mk
@@ -3,7 +3,7 @@ MODULE := engines/plumbers
 MODULE_OBJS = \
 	plumbers.o \
 	console.o \
-	detection.o
+	metaengine.o
 
 # This module can be built as a plugin
 ifeq ($(ENABLE_PLUMBERS), DYNAMIC_PLUGIN)
@@ -12,3 +12,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 9c6c628ae64074d59b74fa34ed5ed64a96eba3f9
    https://github.com/scummvm/scummvm/commit/9c6c628ae64074d59b74fa34ed5ed64a96eba3f9
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
AGI: Move some common code to detection.h

- These structs are necessary for detection, as well as the engine itself.
- So, we move it to a common header file, include it once in both the files.
- This way, we won't have to include agi.h inside detection translation unit, which saves us much junk code going into the executable.

Changed paths:
  A engines/agi/detection.h
    engines/agi/agi.h


diff --git a/engines/agi/agi.h b/engines/agi/agi.h
index e4ed99b0bc..0e9461a41f 100644
--- a/engines/agi/agi.h
+++ b/engines/agi/agi.h
@@ -44,6 +44,7 @@
 #include "agi/picture.h"
 #include "agi/logic.h"
 #include "agi/sound.h"
+#include "agi/detection.h"
 
 namespace Common {
 class RandomSource;
@@ -104,56 +105,6 @@ typedef signed int Err;
 
 #define CMD_BSIZE 12
 
-enum AgiGameID {
-	GID_AGIDEMO,
-	GID_BC,
-	GID_DDP,
-	GID_GOLDRUSH,
-	GID_KQ1,
-	GID_KQ2,
-	GID_KQ3,
-	GID_KQ4,
-	GID_LSL1,
-	GID_MH1,
-	GID_MH2,
-	GID_MIXEDUP,
-	GID_PQ1,
-	GID_SQ1,
-	GID_SQ2,
-	GID_XMASCARD,
-	GID_FANMADE,
-	GID_GETOUTTASQ, // Fanmade
-	GID_MICKEY,     // PreAGI
-	GID_WINNIE,     // PreAGI
-	GID_TROLL       // PreAGI
-};
-
-enum AgiGameType {
-	GType_PreAGI = 0,
-	GType_V1 = 1,
-	GType_V2 = 2,
-	GType_V3 = 3
-};
-
-enum BooterDisks {
-	BooterDisk1 = 0,
-	BooterDisk2 = 1
-};
-
-//
-// GF_OLDAMIGAV20 means that the interpreter is an old Amiga AGI interpreter that
-// uses value 20 for the computer type (v20 i.e. vComputer) rather than the usual value 5.
-//
-enum AgiGameFeatures {
-	GF_AGIMOUSE    = (1 << 0), // this disables "Click-to-walk mouse interface"
-	GF_AGDS        = (1 << 1),
-	GF_AGI256      = (1 << 2), // marks fanmade AGI-256 games
-	GF_MACGOLDRUSH = (1 << 3), // use "grdir" instead of "dir" for volume loading
-	GF_FANMADE     = (1 << 4), // marks fanmade games
-	GF_OLDAMIGAV20 = (1 << 5),
-	GF_2GSOLDSOUND = (1 << 6)
-};
-
 struct AGIGameDescription;
 
 enum {
diff --git a/engines/agi/detection.h b/engines/agi/detection.h
new file mode 100644
index 0000000000..9f6cbb9ae7
--- /dev/null
+++ b/engines/agi/detection.h
@@ -0,0 +1,88 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+
+namespace Agi {
+
+struct AGIGameDescription {
+	ADGameDescription desc;
+
+	int gameID;
+	int gameType;
+	uint32 features;
+	uint16 version;
+};
+
+enum AgiGameType {
+	GType_PreAGI = 0,
+	GType_V1 = 1,
+	GType_V2 = 2,
+	GType_V3 = 3
+};
+
+enum AgiGameID {
+	GID_AGIDEMO,
+	GID_BC,
+	GID_DDP,
+	GID_GOLDRUSH,
+	GID_KQ1,
+	GID_KQ2,
+	GID_KQ3,
+	GID_KQ4,
+	GID_LSL1,
+	GID_MH1,
+	GID_MH2,
+	GID_MIXEDUP,
+	GID_PQ1,
+	GID_SQ1,
+	GID_SQ2,
+	GID_XMASCARD,
+	GID_FANMADE,
+	GID_GETOUTTASQ, // Fanmade
+	GID_MICKEY,     // PreAGI
+	GID_WINNIE,     // PreAGI
+	GID_TROLL       // PreAGI
+};
+
+//
+// GF_OLDAMIGAV20 means that the interpreter is an old Amiga AGI interpreter that
+// uses value 20 for the computer type (v20 i.e. vComputer) rather than the usual value 5.
+//
+enum AgiGameFeatures {
+	GF_AGIMOUSE    = (1 << 0), // this disables "Click-to-walk mouse interface"
+	GF_AGDS        = (1 << 1),
+	GF_AGI256      = (1 << 2), // marks fanmade AGI-256 games
+	GF_MACGOLDRUSH = (1 << 3), // use "grdir" instead of "dir" for volume loading
+	GF_FANMADE     = (1 << 4), // marks fanmade games
+	GF_OLDAMIGAV20 = (1 << 5),
+	GF_2GSOLDSOUND = (1 << 6)
+};
+
+enum BooterDisks {
+	BooterDisk1 = 0,
+	BooterDisk2 = 1
+};
+
+} // End of namespace Agi


Commit: fa36701425315934038535a541069a599be5596a
    https://github.com/scummvm/scummvm/commit/fa36701425315934038535a541069a599be5596a
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
AGI: Split detection features & adapt to new plugins.

Changed paths:
  A engines/agi/detection_enums.h
  A engines/agi/metaengine.cpp
    configure
    engines/agi/agi.h
    engines/agi/detection.cpp
    engines/agi/detection.h
    engines/agi/module.mk


diff --git a/configure b/configure
index f0a79cd3f5..04f65c1ae6 100755
--- a/configure
+++ b/configure
@@ -6160,7 +6160,7 @@ EOF
 	fi
 done
 
-declare -a static_detect_engines=("PLUMBERS")
+declare -a static_detect_engines=("PLUMBERS" "AGI")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/agi/agi.h b/engines/agi/agi.h
index 0e9461a41f..1235c6d92a 100644
--- a/engines/agi/agi.h
+++ b/engines/agi/agi.h
@@ -44,7 +44,7 @@
 #include "agi/picture.h"
 #include "agi/logic.h"
 #include "agi/sound.h"
-#include "agi/detection.h"
+#include "agi/detection_enums.h"
 
 namespace Common {
 class RandomSource;
diff --git a/engines/agi/detection.cpp b/engines/agi/detection.cpp
index e897e1258b..10b4772f85 100644
--- a/engines/agi/detection.cpp
+++ b/engines/agi/detection.cpp
@@ -20,91 +20,17 @@
  *
  */
 
-#include "base/plugins.h"
 
-#include "engines/advancedDetector.h"
-#include "common/config-manager.h"
-#include "common/file.h"
-#include "common/md5.h"
-#include "common/savefile.h"
-#include "common/textconsole.h"
 #include "common/translation.h"
+#include "common/system.h"
+#include "common/debug.h"
 
-#include "graphics/thumbnail.h"
-#include "graphics/surface.h"
-
-#include "agi/agi.h"
-#include "agi/preagi.h"
-#include "agi/preagi_mickey.h"
-#include "agi/preagi_troll.h"
-#include "agi/preagi_winnie.h"
-#include "agi/wagparser.h"
-
-
-namespace Agi {
-
-struct AGIGameDescription {
-	ADGameDescription desc;
-
-	int gameID;
-	int gameType;
-	uint32 features;
-	uint16 version;
-};
-
-uint32 AgiBase::getGameID() const {
-	return _gameDescription->gameID;
-}
-
-uint32 AgiBase::getFeatures() const {
-	return _gameFeatures;
-}
-
-Common::Platform AgiBase::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-Common::Language AgiBase::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-uint16 AgiBase::getVersion() const {
-	return _gameVersion;
-}
-
-uint16 AgiBase::getGameType() const {
-	return _gameDescription->gameType;
-}
-
-const char *AgiBase::getGameMD5() const {
-	return _gameDescription->desc.filesDescriptions[0].md5;
-}
-
-void AgiBase::initFeatures() {
-	_gameFeatures = _gameDescription->features;
-}
-
-void AgiBase::setFeature(uint32 feature) {
-	_gameFeatures |= feature;
-}
-
-void AgiBase::setVersion(uint16 version) {
-	_gameVersion = version;
-}
-
-void AgiBase::initVersion() {
-	_gameVersion = _gameDescription->version;
-}
-
-const char *AgiBase::getDiskName(uint16 id) {
-	for (int i = 0; _gameDescription->desc.filesDescriptions[i].fileName != NULL; i++)
-		if (_gameDescription->desc.filesDescriptions[i].fileType == id)
-			return _gameDescription->desc.filesDescriptions[i].fileName;
-
-	return "";
-}
+#include "base/plugins.h"
+#include "engines/advancedDetector.h"
 
-}
+#include "agi/detection_enums.h"
+#include "agi/detection.h"
+#include "agi/wagparser.h" // for fallback detection
 
 static const PlainGameDescriptor agiGames[] = {
 	{"agi", "Sierra AGI game"},
@@ -227,218 +153,9 @@ public:
 		return "Sierra AGI Engine (C) Sierra On-Line Software";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
 };
 
-bool AgiMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-	    (f == kSupportsLoadingDuringStartup) ||
-	    (f == kSupportsDeleteSave) ||
-	    (f == kSavesSupportMetaInfo) ||
-	    (f == kSavesSupportThumbnail) ||
-	    (f == kSavesSupportCreationDate) ||
-	    (f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-bool AgiBase::hasFeature(EngineFeature f) const {
-	return
-	    (f == kSupportsReturnToLauncher) ||
-	    (f == kSupportsLoadingDuringRuntime) ||
-	    (f == kSupportsSavingDuringRuntime);
-}
-
-
-bool AgiMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Agi::AGIGameDescription *gd = (const Agi::AGIGameDescription *)desc;
-	bool res = true;
-
-	switch (gd->gameType) {
-	case Agi::GType_PreAGI:
-		switch (gd->gameID) {
-		case GID_MICKEY:
-			*engine = new Agi::MickeyEngine(syst, gd);
-			break;
-		case GID_TROLL:
-			*engine = new Agi::TrollEngine(syst, gd);
-			break;
-		case GID_WINNIE:
-			*engine = new Agi::WinnieEngine(syst, gd);
-			break;
-		default:
-			res = false;
-			error("PreAGI engine: unknown gameID");
-			break;
-		}
-		break;
-	case Agi::GType_V1:
-	case Agi::GType_V2:
-	case Agi::GType_V3:
-		*engine = new Agi::AgiEngine(syst, gd);
-		break;
-	default:
-		res = false;
-		error("AGI engine: unknown gameType");
-	}
-
-	return res;
-}
-
-SaveStateList AgiMetaEngine::listSaves(const char *target) const {
-	const uint32 AGIflag = MKTAG('A', 'G', 'I', ':');
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNr = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNr >= 0 && slotNr <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				uint32 type = in->readUint32BE();
-				char description[31];
-
-				if (type == AGIflag) {
-					uint16 descriptionPos = 0;
-
-					in->read(description, 31);
-
-					// Security-check, if saveDescription has a terminating NUL
-					while (description[descriptionPos]) {
-						descriptionPos++;
-						if (descriptionPos >= sizeof(description))
-							break;
-					}
-					if (descriptionPos >= sizeof(description)) {
-						strcpy(description, "[broken saved game]");
-					}
-				} else {
-					strcpy(description, "[not an AGI saved game]");
-				}
-
-				delete in;
-
-				saveList.push_back(SaveStateDescriptor(slotNr, description));
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int AgiMetaEngine::getMaximumSaveSlot() const { return 999; }
-
-void AgiMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-SaveStateDescriptor AgiMetaEngine::querySaveMetaInfos(const char *target, int slotNr) const {
-	const uint32 AGIflag = MKTAG('A', 'G', 'I', ':');
-	Common::String fileName = Common::String::format("%s.%03d", target, slotNr);
-
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (in) {
-		if (in->readUint32BE() != AGIflag) {
-			delete in;
-			return SaveStateDescriptor();
-		}
-
-		char description[31];
-		uint16 descriptionPos = 0;
-
-		in->read(description, 31);
-
-		while (description[descriptionPos]) {
-			descriptionPos++;
-			if (descriptionPos >= sizeof(description))
-				break;
-		}
-		if (descriptionPos >= sizeof(description)) {
-			// broken description, ignore it
-			delete in;
-
-			SaveStateDescriptor descriptor(slotNr, "[broken saved game]");
-			return descriptor;
-		}
-
-		SaveStateDescriptor descriptor(slotNr, description);
-
-		// Do not allow save slot 0 (used for auto-saving) to be deleted or
-		// overwritten.
-		if (slotNr == 0) {
-			descriptor.setWriteProtectedFlag(true);
-			descriptor.setDeletableFlag(false);
-		} else {
-			descriptor.setWriteProtectedFlag(false);
-			descriptor.setDeletableFlag(true);
-		}
-
-		char saveVersion = in->readByte();
-		if (saveVersion >= 4) {
-			Graphics::Surface *thumbnail;
-			if (!Graphics::loadThumbnail(*in, thumbnail)) {
-				delete in;
-				return SaveStateDescriptor();
-			}
-
-			descriptor.setThumbnail(thumbnail);
-
-			uint32 saveDate = in->readUint32BE();
-			uint16 saveTime = in->readUint16BE();
-			if (saveVersion >= 9) {
-				in->readByte(); // skip over seconds of saveTime (not needed here)
-			}
-			if (saveVersion >= 6) {
-				uint32 playTime = in->readUint32BE();
-				descriptor.setPlayTime(playTime * 1000);
-			}
-
-			int day = (saveDate >> 24) & 0xFF;
-			int month = (saveDate >> 16) & 0xFF;
-			int year = saveDate & 0xFFFF;
-
-			descriptor.setSaveDate(year, month, day);
-
-			int hour = (saveTime >> 8) & 0xFF;
-			int minutes = saveTime & 0xFF;
-
-			descriptor.setSaveTime(hour, minutes);
-		}
-
-		delete in;
-
-		return descriptor;
-
-	} else {
-		SaveStateDescriptor emptySave;
-		// Do not allow save slot 0 (used for auto-saving) to be overwritten.
-		if (slotNr == 0) {
-			emptySave.setWriteProtectedFlag(true);
-		} else {
-			emptySave.setWriteProtectedFlag(false);
-		}
-		return emptySave;
-	}
-}
-
 ADDetectedGame AgiMetaEngine::fallbackDetect(const FileMap &allFilesXXX, const Common::FSList &fslist) const {
 	typedef Common::HashMap<Common::String, int32> IntMap;
 	IntMap allFiles;
@@ -607,65 +324,4 @@ ADDetectedGame AgiMetaEngine::fallbackDetect(const FileMap &allFilesXXX, const C
 	return ADDetectedGame();
 }
 
-#if PLUGIN_ENABLED_DYNAMIC(AGI)
-	REGISTER_PLUGIN_DYNAMIC(AGI, PLUGIN_TYPE_ENGINE, AgiMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(AGI, PLUGIN_TYPE_ENGINE, AgiMetaEngine);
-#endif
-
-namespace Agi {
-
-bool AgiBase::canLoadGameStateCurrently() {
-	if (!(getGameType() == GType_PreAGI)) {
-		if (getFlag(VM_FLAG_MENUS_ACCESSIBLE)) {
-			if (!_noSaveLoadAllowed) {
-				if (!cycleInnerLoopIsActive()) {
-					// We can't allow to restore a game, while inner loop is active
-					// For example Mixed Up Mother Goose has an endless loop for user name input
-					// Which means even if we abort the inner loop, the game would keep on calling
-					// GetString() until something is entered. And this would of course also happen
-					// right after restoring a saved game.
-					return true;
-				}
-			}
-		}
-	}
-	return false;
-}
-
-bool AgiBase::canSaveGameStateCurrently() {
-	if (getGameID() == GID_BC) // Technically in Black Cauldron we may save anytime
-		return true;
-
-	if (!(getGameType() == GType_PreAGI)) {
-		if (getFlag(VM_FLAG_MENUS_ACCESSIBLE)) {
-			if (!_noSaveLoadAllowed) {
-				if (!cycleInnerLoopIsActive()) {
-					if (promptIsEnabled()) {
-						return true;
-					}
-				}
-			}
-		}
-	}
-	return false;
-}
-
-int AgiEngine::agiDetectGame() {
-	int ec = errOK;
-
-	assert(_gameDescription != NULL);
-
-	if (getVersion() <= 0x2001) {
-		_loader = new AgiLoader_v1(this);
-	} else if (getVersion() <= 0x2999) {
-		_loader = new AgiLoader_v2(this);
-	} else {
-		_loader = new AgiLoader_v3(this);
-	}
-	ec = _loader->detectGame();
-
-	return ec;
-}
-
-} // End of namespace Agi
+REGISTER_PLUGIN_STATIC(AGI_DETECTION, PLUGIN_TYPE_METAENGINE, AgiMetaEngine);
diff --git a/engines/agi/detection.h b/engines/agi/detection.h
index 9f6cbb9ae7..936ed786aa 100644
--- a/engines/agi/detection.h
+++ b/engines/agi/detection.h
@@ -20,9 +20,8 @@
  *
  */
 
-#include "base/plugins.h"
-
-#include "engines/advancedDetector.h"
+#ifndef AGI_DETECTION_H
+#define AGI_DETECTION_H
 
 namespace Agi {
 
@@ -35,54 +34,6 @@ struct AGIGameDescription {
 	uint16 version;
 };
 
-enum AgiGameType {
-	GType_PreAGI = 0,
-	GType_V1 = 1,
-	GType_V2 = 2,
-	GType_V3 = 3
-};
-
-enum AgiGameID {
-	GID_AGIDEMO,
-	GID_BC,
-	GID_DDP,
-	GID_GOLDRUSH,
-	GID_KQ1,
-	GID_KQ2,
-	GID_KQ3,
-	GID_KQ4,
-	GID_LSL1,
-	GID_MH1,
-	GID_MH2,
-	GID_MIXEDUP,
-	GID_PQ1,
-	GID_SQ1,
-	GID_SQ2,
-	GID_XMASCARD,
-	GID_FANMADE,
-	GID_GETOUTTASQ, // Fanmade
-	GID_MICKEY,     // PreAGI
-	GID_WINNIE,     // PreAGI
-	GID_TROLL       // PreAGI
-};
-
-//
-// GF_OLDAMIGAV20 means that the interpreter is an old Amiga AGI interpreter that
-// uses value 20 for the computer type (v20 i.e. vComputer) rather than the usual value 5.
-//
-enum AgiGameFeatures {
-	GF_AGIMOUSE    = (1 << 0), // this disables "Click-to-walk mouse interface"
-	GF_AGDS        = (1 << 1),
-	GF_AGI256      = (1 << 2), // marks fanmade AGI-256 games
-	GF_MACGOLDRUSH = (1 << 3), // use "grdir" instead of "dir" for volume loading
-	GF_FANMADE     = (1 << 4), // marks fanmade games
-	GF_OLDAMIGAV20 = (1 << 5),
-	GF_2GSOLDSOUND = (1 << 6)
-};
-
-enum BooterDisks {
-	BooterDisk1 = 0,
-	BooterDisk2 = 1
-};
-
 } // End of namespace Agi
+
+#endif // AGI_DETECTION_H
diff --git a/engines/agi/detection_enums.h b/engines/agi/detection_enums.h
new file mode 100644
index 0000000000..66f9384c7f
--- /dev/null
+++ b/engines/agi/detection_enums.h
@@ -0,0 +1,80 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef AGI_DETECTION_ENUMS_H
+#define AGI_DETECTION_ENUMS_H
+
+namespace Agi {
+
+enum AgiGameType {
+	GType_PreAGI = 0,
+	GType_V1 = 1,
+	GType_V2 = 2,
+	GType_V3 = 3
+};
+
+enum AgiGameID {
+	GID_AGIDEMO,
+	GID_BC,
+	GID_DDP,
+	GID_GOLDRUSH,
+	GID_KQ1,
+	GID_KQ2,
+	GID_KQ3,
+	GID_KQ4,
+	GID_LSL1,
+	GID_MH1,
+	GID_MH2,
+	GID_MIXEDUP,
+	GID_PQ1,
+	GID_SQ1,
+	GID_SQ2,
+	GID_XMASCARD,
+	GID_FANMADE,
+	GID_GETOUTTASQ, // Fanmade
+	GID_MICKEY,     // PreAGI
+	GID_WINNIE,     // PreAGI
+	GID_TROLL       // PreAGI
+};
+
+//
+// GF_OLDAMIGAV20 means that the interpreter is an old Amiga AGI interpreter that
+// uses value 20 for the computer type (v20 i.e. vComputer) rather than the usual value 5.
+//
+enum AgiGameFeatures {
+	GF_AGIMOUSE    = (1 << 0), // this disables "Click-to-walk mouse interface"
+	GF_AGDS        = (1 << 1),
+	GF_AGI256      = (1 << 2), // marks fanmade AGI-256 games
+	GF_MACGOLDRUSH = (1 << 3), // use "grdir" instead of "dir" for volume loading
+	GF_FANMADE     = (1 << 4), // marks fanmade games
+	GF_OLDAMIGAV20 = (1 << 5),
+	GF_2GSOLDSOUND = (1 << 6)
+};
+
+enum BooterDisks {
+	BooterDisk1 = 0,
+	BooterDisk2 = 1
+};
+
+} // End of namespace Agi
+
+#endif // AGI_DETECTION_ENUMS_H
diff --git a/engines/agi/metaengine.cpp b/engines/agi/metaengine.cpp
new file mode 100644
index 0000000000..f2507a8f37
--- /dev/null
+++ b/engines/agi/metaengine.cpp
@@ -0,0 +1,380 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/config-manager.h"
+#include "common/file.h"
+#include "common/md5.h"
+#include "common/savefile.h"
+#include "common/textconsole.h"
+
+#include "graphics/thumbnail.h"
+#include "graphics/surface.h"
+
+#include "base/plugins.h"
+#include "engines/advancedDetector.h"
+
+#include "agi/agi.h"
+#include "agi/preagi.h"
+#include "agi/preagi_mickey.h"
+#include "agi/preagi_troll.h"
+#include "agi/preagi_winnie.h"
+
+#include "agi/detection.h"
+
+namespace Agi {
+
+uint32 AgiBase::getGameID() const {
+	return _gameDescription->gameID;
+}
+
+uint32 AgiBase::getFeatures() const {
+	return _gameFeatures;
+}
+
+Common::Platform AgiBase::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+Common::Language AgiBase::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+uint16 AgiBase::getVersion() const {
+	return _gameVersion;
+}
+
+uint16 AgiBase::getGameType() const {
+	return _gameDescription->gameType;
+}
+
+const char *AgiBase::getGameMD5() const {
+	return _gameDescription->desc.filesDescriptions[0].md5;
+}
+
+void AgiBase::initFeatures() {
+	_gameFeatures = _gameDescription->features;
+}
+
+void AgiBase::setFeature(uint32 feature) {
+	_gameFeatures |= feature;
+}
+
+void AgiBase::setVersion(uint16 version) {
+	_gameVersion = version;
+}
+
+void AgiBase::initVersion() {
+	_gameVersion = _gameDescription->version;
+}
+
+const char *AgiBase::getDiskName(uint16 id) {
+	for (int i = 0; _gameDescription->desc.filesDescriptions[i].fileName != NULL; i++)
+		if (_gameDescription->desc.filesDescriptions[i].fileType == id)
+			return _gameDescription->desc.filesDescriptions[i].fileName;
+
+	return "";
+}
+
+bool AgiBase::hasFeature(EngineFeature f) const {
+	return
+	    (f == kSupportsReturnToLauncher) ||
+	    (f == kSupportsLoadingDuringRuntime) ||
+	    (f == kSupportsSavingDuringRuntime);
+}
+
+} // End of namespace Agi
+
+
+using namespace Agi;
+
+class AgiMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "agi";
+	}
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+
+	bool hasFeature(MetaEngineFeature f) const override;
+};
+
+bool AgiMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+	    (f == kSupportsLoadingDuringStartup) ||
+	    (f == kSupportsDeleteSave) ||
+	    (f == kSavesSupportMetaInfo) ||
+	    (f == kSavesSupportThumbnail) ||
+	    (f == kSavesSupportCreationDate) ||
+	    (f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+bool AgiMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Agi::AGIGameDescription *gd = (const Agi::AGIGameDescription *)desc;
+	bool res = true;
+
+	switch (gd->gameType) {
+	case Agi::GType_PreAGI:
+		switch (gd->gameID) {
+		case GID_MICKEY:
+			*engine = new Agi::MickeyEngine(syst, gd);
+			break;
+		case GID_TROLL:
+			*engine = new Agi::TrollEngine(syst, gd);
+			break;
+		case GID_WINNIE:
+			*engine = new Agi::WinnieEngine(syst, gd);
+			break;
+		default:
+			res = false;
+			error("PreAGI engine: unknown gameID");
+			break;
+		}
+		break;
+	case Agi::GType_V1:
+	case Agi::GType_V2:
+	case Agi::GType_V3:
+		*engine = new Agi::AgiEngine(syst, gd);
+		break;
+	default:
+		res = false;
+		error("AGI engine: unknown gameType");
+	}
+
+	return res;
+}
+
+SaveStateList AgiMetaEngineConnect::listSaves(const char *target) const {
+	const uint32 AGIflag = MKTAG('A', 'G', 'I', ':');
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNr = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNr >= 0 && slotNr <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				uint32 type = in->readUint32BE();
+				char description[31];
+
+				if (type == AGIflag) {
+					uint16 descriptionPos = 0;
+
+					in->read(description, 31);
+
+					// Security-check, if saveDescription has a terminating NUL
+					while (description[descriptionPos]) {
+						descriptionPos++;
+						if (descriptionPos >= sizeof(description))
+							break;
+					}
+					if (descriptionPos >= sizeof(description)) {
+						strcpy(description, "[broken saved game]");
+					}
+				} else {
+					strcpy(description, "[not an AGI saved game]");
+				}
+
+				delete in;
+
+				saveList.push_back(SaveStateDescriptor(slotNr, description));
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void AgiMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+int AgiMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+
+SaveStateDescriptor AgiMetaEngineConnect::querySaveMetaInfos(const char *target, int slotNr) const {
+	const uint32 AGIflag = MKTAG('A', 'G', 'I', ':');
+	Common::String fileName = Common::String::format("%s.%03d", target, slotNr);
+
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (in) {
+		if (in->readUint32BE() != AGIflag) {
+			delete in;
+			return SaveStateDescriptor();
+		}
+
+		char description[31];
+		uint16 descriptionPos = 0;
+
+		in->read(description, 31);
+
+		while (description[descriptionPos]) {
+			descriptionPos++;
+			if (descriptionPos >= sizeof(description))
+				break;
+		}
+		if (descriptionPos >= sizeof(description)) {
+			// broken description, ignore it
+			delete in;
+
+			SaveStateDescriptor descriptor(slotNr, "[broken saved game]");
+			return descriptor;
+		}
+
+		SaveStateDescriptor descriptor(slotNr, description);
+
+		// Do not allow save slot 0 (used for auto-saving) to be deleted or
+		// overwritten.
+		if (slotNr == 0) {
+			descriptor.setWriteProtectedFlag(true);
+			descriptor.setDeletableFlag(false);
+		} else {
+			descriptor.setWriteProtectedFlag(false);
+			descriptor.setDeletableFlag(true);
+		}
+
+		char saveVersion = in->readByte();
+		if (saveVersion >= 4) {
+			Graphics::Surface *thumbnail;
+			if (!Graphics::loadThumbnail(*in, thumbnail)) {
+				delete in;
+				return SaveStateDescriptor();
+			}
+
+			descriptor.setThumbnail(thumbnail);
+
+			uint32 saveDate = in->readUint32BE();
+			uint16 saveTime = in->readUint16BE();
+			if (saveVersion >= 9) {
+				in->readByte(); // skip over seconds of saveTime (not needed here)
+			}
+			if (saveVersion >= 6) {
+				uint32 playTime = in->readUint32BE();
+				descriptor.setPlayTime(playTime * 1000);
+			}
+
+			int day = (saveDate >> 24) & 0xFF;
+			int month = (saveDate >> 16) & 0xFF;
+			int year = saveDate & 0xFFFF;
+
+			descriptor.setSaveDate(year, month, day);
+
+			int hour = (saveTime >> 8) & 0xFF;
+			int minutes = saveTime & 0xFF;
+
+			descriptor.setSaveTime(hour, minutes);
+		}
+
+		delete in;
+
+		return descriptor;
+
+	} else {
+		SaveStateDescriptor emptySave;
+		// Do not allow save slot 0 (used for auto-saving) to be overwritten.
+		if (slotNr == 0) {
+			emptySave.setWriteProtectedFlag(true);
+		} else {
+			emptySave.setWriteProtectedFlag(false);
+		}
+		return emptySave;
+	}
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(AGI)
+	REGISTER_PLUGIN_DYNAMIC(AGI, PLUGIN_TYPE_ENGINE, AgiMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(AGI, PLUGIN_TYPE_ENGINE, AgiMetaEngineConnect);
+#endif
+
+namespace Agi {
+
+bool AgiBase::canLoadGameStateCurrently() {
+	if (!(getGameType() == GType_PreAGI)) {
+		if (getFlag(VM_FLAG_MENUS_ACCESSIBLE)) {
+			if (!_noSaveLoadAllowed) {
+				if (!cycleInnerLoopIsActive()) {
+					// We can't allow to restore a game, while inner loop is active
+					// For example Mixed Up Mother Goose has an endless loop for user name input
+					// Which means even if we abort the inner loop, the game would keep on calling
+					// GetString() until something is entered. And this would of course also happen
+					// right after restoring a saved game.
+					return true;
+				}
+			}
+		}
+	}
+	return false;
+}
+
+bool AgiBase::canSaveGameStateCurrently() {
+	if (getGameID() == GID_BC) // Technically in Black Cauldron we may save anytime
+		return true;
+
+	if (!(getGameType() == GType_PreAGI)) {
+		if (getFlag(VM_FLAG_MENUS_ACCESSIBLE)) {
+			if (!_noSaveLoadAllowed) {
+				if (!cycleInnerLoopIsActive()) {
+					if (promptIsEnabled()) {
+						return true;
+					}
+				}
+			}
+		}
+	}
+	return false;
+}
+
+int AgiEngine::agiDetectGame() {
+	int ec = errOK;
+
+	assert(_gameDescription != NULL);
+
+	if (getVersion() <= 0x2001) {
+		_loader = new AgiLoader_v1(this);
+	} else if (getVersion() <= 0x2999) {
+		_loader = new AgiLoader_v2(this);
+	} else {
+		_loader = new AgiLoader_v3(this);
+	}
+	ec = _loader->detectGame();
+
+	return ec;
+}
+
+} // End of namespace Agi
diff --git a/engines/agi/module.mk b/engines/agi/module.mk
index 8ca261f55b..d66e4129de 100644
--- a/engines/agi/module.mk
+++ b/engines/agi/module.mk
@@ -5,7 +5,6 @@ MODULE_OBJS := \
 	checks.o \
 	console.o \
 	cycle.o \
-	detection.o \
 	font.o \
 	global.o \
 	graphics.o \
@@ -17,6 +16,7 @@ MODULE_OBJS := \
 	logic.o \
 	lzw.o \
 	menu.o \
+	metaengine.o \
 	motion.o \
 	objects.o \
 	opcodes.o \
@@ -39,7 +39,6 @@ MODULE_OBJS := \
 	systemui.o \
 	text.o \
 	view.o \
-	wagparser.o \
 	words.o
 
 
@@ -50,3 +49,11 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# External dependencies of detection.
+# This is unneeded by the engine module itself,
+# so seperate it completely.
+DETECT_OBJS += $(MODULE)/wagparser.o


Commit: d10eb35dfee30f4b803144de636a3e15726fdbcf
    https://github.com/scummvm/scummvm/commit/d10eb35dfee30f4b803144de636a3e15726fdbcf
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCUMM: Move obsoleteGameIDsTable from detection_tables to a common header

- MetaEngineConnect requires these at compile time.
- In order to avoid including everything from detect_tables, we just move the one thing we need into header, and include that in metaengine.cpp
- Also include it in detection_tables.h to restore orignal functionality.

Changed paths:
  A engines/scumm/obsolete.h
    engines/scumm/detection_tables.h


diff --git a/engines/scumm/detection_tables.h b/engines/scumm/detection_tables.h
index 3dae5e181b..50bc9755ff 100644
--- a/engines/scumm/detection_tables.h
+++ b/engines/scumm/detection_tables.h
@@ -33,15 +33,10 @@
 
 #include "scumm/scumm-md5.h"
 
+#include "scumm/obsolete.h"
 
 namespace Scumm {
 
-#pragma mark -
-#pragma mark --- Data types & constants ---
-#pragma mark -
-
-#define UNK Common::kPlatformUnknown
-
 #pragma mark -
 #pragma mark --- Tables ---
 #pragma mark -
@@ -147,44 +142,6 @@ static const PlainGameDescriptor gameDescriptions[] = {
 	{ 0, 0 }
 };
 
-/**
- * Conversion table mapping old obsolete game IDs to the
- * corresponding new game ID and platform combination.
- */
-static const Engines::ObsoleteGameID obsoleteGameIDsTable[] = {
-	{"bluesabctimedemo", "bluesabctime", UNK},
-	{"BluesBirthdayDemo", "BluesBirthday", UNK},
-	{"comidemo", "comi", UNK},
-	{"digdemo", "dig", UNK},
-	{"digdemoMac", "dig", Common::kPlatformMacintosh},
-	{"dottdemo", "tentacle", UNK},
-	{"fate", "atlantis", UNK},
-	{"ftMac", "ft",  Common::kPlatformMacintosh},
-	{"ftpcdemo", "ft", UNK},
-	{"ftdemo", "ft",  Common::kPlatformMacintosh},
-	{"game", "monkey", UNK},
-	{"indy3ega", "indy3", UNK},
-	{"indy3towns", "indy3", Common::kPlatformFMTowns},
-	{"indy4", "atlantis", Common::kPlatformFMTowns},
-	{"indydemo", "atlantis", Common::kPlatformFMTowns},
-	{"loomcd", "loom", UNK},
-	{"loomTowns", "loom", Common::kPlatformFMTowns},
-	{"mi2demo", "monkey2", UNK},
-	{"monkey1", "monkey", UNK},
-	{"monkeyEGA", "monkey", UNK},
-	{"monkeyVGA", "monkey", UNK},
-	{"playfate", "atlantis", UNK},
-	{"samnmax-alt", "samnmax", UNK},
-	{"samnmaxMac", "samnmax", Common::kPlatformMacintosh},
-	{"samdemo", "samnmax", UNK},
-	{"samdemoMac", "samnmax", Common::kPlatformMacintosh},
-	{"snmdemo", "samnmax", UNK},
-	{"snmidemo", "samnmax", UNK},
-	{"tentacleMac", "tentacle", Common::kPlatformMacintosh},
-	{"zakTowns", "zak", Common::kPlatformFMTowns},
-	{NULL, NULL, UNK}
-};
-
 // The following table contains information about variants of our various
 // games. We index into it with help of md5table (from scumm-md5.h), to find
 // the correct GameSettings for a given game variant.
diff --git a/engines/scumm/obsolete.h b/engines/scumm/obsolete.h
new file mode 100644
index 0000000000..7314fc6f12
--- /dev/null
+++ b/engines/scumm/obsolete.h
@@ -0,0 +1,66 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+namespace Scumm {
+
+#define UNK Common::kPlatformUnknown
+
+/**
+ * Conversion table mapping old obsolete game IDs to the
+ * corresponding new game ID and platform combination.
+ */
+static const Engines::ObsoleteGameID obsoleteGameIDsTable[] = {
+	{"bluesabctimedemo", "bluesabctime", UNK},
+	{"BluesBirthdayDemo", "BluesBirthday", UNK},
+	{"comidemo", "comi", UNK},
+	{"digdemo", "dig", UNK},
+	{"digdemoMac", "dig", Common::kPlatformMacintosh},
+	{"dottdemo", "tentacle", UNK},
+	{"fate", "atlantis", UNK},
+	{"ftMac", "ft",  Common::kPlatformMacintosh},
+	{"ftpcdemo", "ft", UNK},
+	{"ftdemo", "ft",  Common::kPlatformMacintosh},
+	{"game", "monkey", UNK},
+	{"indy3ega", "indy3", UNK},
+	{"indy3towns", "indy3", Common::kPlatformFMTowns},
+	{"indy4", "atlantis", Common::kPlatformFMTowns},
+	{"indydemo", "atlantis", Common::kPlatformFMTowns},
+	{"loomcd", "loom", UNK},
+	{"loomTowns", "loom", Common::kPlatformFMTowns},
+	{"mi2demo", "monkey2", UNK},
+	{"monkey1", "monkey", UNK},
+	{"monkeyEGA", "monkey", UNK},
+	{"monkeyVGA", "monkey", UNK},
+	{"playfate", "atlantis", UNK},
+	{"samnmax-alt", "samnmax", UNK},
+	{"samnmaxMac", "samnmax", Common::kPlatformMacintosh},
+	{"samdemo", "samnmax", UNK},
+	{"samdemoMac", "samnmax", Common::kPlatformMacintosh},
+	{"snmdemo", "samnmax", UNK},
+	{"snmidemo", "samnmax", UNK},
+	{"tentacleMac", "tentacle", Common::kPlatformMacintosh},
+	{"zakTowns", "zak", Common::kPlatformFMTowns},
+	{NULL, NULL, UNK}
+};
+
+} // End of namespace Scumm


Commit: dc4672e29402b14a3b07e2a6604c9a6fa1556c22
    https://github.com/scummvm/scummvm/commit/dc4672e29402b14a3b07e2a6604c9a6fa1556c22
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCUMM: Split detection features & adapt to new plugins.

- Also, we remove the static keyword so other TU's can use the functions defined.
- This change has a catch.
- Because creating an instance depends on game detection code from detection.cpp, we cannot exclude it from Scumm.
- For Statically linked Scumm, we can simply exclude these detection files, because they're already being built.
- For dynamically linked Scumm, we can add it to our executable.
- Thus, for dynamically linked Scumm, one catch is that we have duplicated code (detection.o in our executable, as well as scumm.dll), but that shouldn't be a big problem considering the advantage it gives us: Detection without a plugin loading.

Changed paths:
  A engines/scumm/metaengine.cpp
  A engines/scumm/metaengine.h
    configure
    engines/scumm/detection.cpp
    engines/scumm/module.mk


diff --git a/configure b/configure
index 04f65c1ae6..e643c223ee 100755
--- a/configure
+++ b/configure
@@ -6160,7 +6160,7 @@ EOF
 	fi
 done
 
-declare -a static_detect_engines=("PLUMBERS" "AGI")
+declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/scumm/detection.cpp b/engines/scumm/detection.cpp
index b839a1c815..0bc9cb484d 100644
--- a/engines/scumm/detection.cpp
+++ b/engines/scumm/detection.cpp
@@ -22,12 +22,12 @@
 
 #include "base/plugins.h"
 
+#include "engines/metaengine.h"
+
 #include "common/archive.h"
 #include "common/config-manager.h"
-#include "common/fs.h"
 #include "common/list.h"
 #include "common/md5.h"
-#include "common/savefile.h"
 #include "common/system.h"
 #include "common/translation.h"
 
@@ -35,14 +35,8 @@
 
 #include "scumm/detection.h"
 #include "scumm/detection_tables.h"
-#include "scumm/he/intern_he.h"
-#include "scumm/scumm_v0.h"
-#include "scumm/scumm_v8.h"
 #include "scumm/file.h"
 #include "scumm/file_nes.h"
-#include "scumm/resource.h"
-
-#include "engines/metaengine.h"
 
 
 namespace Scumm {
@@ -56,170 +50,20 @@ enum {
 #pragma mark --- Miscellaneous ---
 #pragma mark -
 
-static int compareMD5Table(const void *a, const void *b) {
+int compareMD5Table(const void *a, const void *b) {
 	const char *key = (const char *)a;
 	const MD5Table *elem = (const MD5Table *)b;
 	return strcmp(key, elem->md5);
 }
 
-static const MD5Table *findInMD5Table(const char *md5) {
+const MD5Table *findInMD5Table(const char *md5) {
 	uint32 arraySize = ARRAYSIZE(md5table) - 1;
 	return (const MD5Table *)bsearch(md5, md5table, arraySize, sizeof(MD5Table), compareMD5Table);
 }
 
-Common::String ScummEngine::generateFilename(const int room) const {
-	const int diskNumber = (room > 0) ? _res->_types[rtRoom][room]._roomno : 0;
-	Common::String result;
-
-	if (_game.version == 4) {
-		if (room == 0 || room >= 900) {
-			result = Common::String::format("%03d.lfl", room);
-		} else {
-			result = Common::String::format("disk%02d.lec", diskNumber);
-		}
-	} else {
-		switch (_filenamePattern.genMethod) {
-		case kGenDiskNum:
-		case kGenDiskNumSteam:
-			result = Common::String::format(_filenamePattern.pattern, diskNumber);
-			break;
-
-		case kGenRoomNum:
-		case kGenRoomNumSteam:
-			result = Common::String::format(_filenamePattern.pattern, room);
-			break;
-
-		case kGenUnchanged:
-			result = _filenamePattern.pattern;
-			break;
-
-		default:
-			error("generateFilename: Unsupported genMethod");
-		}
-	}
-
-	return result;
-}
-
-Common::String ScummEngine_v60he::generateFilename(const int room) const {
-	Common::String result;
-	char id = 0;
-
-	switch (_filenamePattern.genMethod) {
-	case kGenHEMac:
-	case kGenHEMacNoParens:
-	case kGenHEPC:
-		if (room < 0) {
-			id = '0' - room;
-		} else {
-			const int diskNumber = (room > 0) ? _res->_types[rtRoom][room]._roomno : 0;
-			id = diskNumber + '0';
-		}
-
-		if (_filenamePattern.genMethod == kGenHEPC) {
-			result = Common::String::format("%s.he%c", _filenamePattern.pattern, id);
-		} else {
-			if (id == '3') { // Special case for cursors.
-				// For mac they're stored in game binary.
-				result = _filenamePattern.pattern;
-			} else {
-				if (_filenamePattern.genMethod == kGenHEMac)
-					result = Common::String::format("%s (%c)", _filenamePattern.pattern, id);
-				else
-					result = Common::String::format("%s %c", _filenamePattern.pattern, id);
-			}
-		}
-
-		break;
-
-	default:
-		// Fallback to parent method.
-		return ScummEngine::generateFilename(room);
-	}
-
-	return result;
-}
-
-Common::String ScummEngine_v70he::generateFilename(const int room) const {
-	Common::String result;
-	char id = 0;
-
-	Common::String bPattern = _filenamePattern.pattern;
-
-	// Special cases for Blue's games, which share common (b) files.
-	if (_game.id == GID_BIRTHDAYYELLOW || _game.id == GID_BIRTHDAYRED)
-		bPattern = "Blue'sBirthday";
-	else if (_game.id == GID_TREASUREHUNT)
-		bPattern = "Blue'sTreasureHunt";
-
-	switch (_filenamePattern.genMethod) {
-	case kGenHEMac:
-	case kGenHEMacNoParens:
-	case kGenHEPC:
-	case kGenHEIOS:
-		if (_game.heversion >= 98 && room >= 0) {
-			int disk = 0;
-			if (_heV7DiskOffsets)
-				disk = _heV7DiskOffsets[room];
-
-			switch (disk) {
-			case 2:
-				id = 'b';
-				result = bPattern + ".(b)";
-				break;
-			case 1:
-				id = 'a';
-				// Some of the newer HE games for iOS use the ".hea" suffix instead.
-				if (_filenamePattern.genMethod == kGenHEIOS)
-					result = Common::String::format("%s.hea", _filenamePattern.pattern);
-				else
-					result = Common::String::format("%s.(a)", _filenamePattern.pattern);
-				break;
-			default:
-				id = '0';
-				result = Common::String::format("%s.he0", _filenamePattern.pattern);
-			}
-		} else if (room < 0) {
-			id = '0' - room;
-		} else {
-			id = (room == 0) ? '0' : '1';
-		}
-
-		if (_filenamePattern.genMethod == kGenHEPC || _filenamePattern.genMethod == kGenHEIOS) {
-			if (id == '3' && _game.id == GID_MOONBASE) {
-				result = Common::String::format("%s.u32", _filenamePattern.pattern);
-				break;
-			}
-
-			// For HE >= 98, we already called snprintf above.
-			if (_game.heversion < 98 || room < 0)
-				result = Common::String::format("%s.he%c", _filenamePattern.pattern, id);
-		} else {
-			if (id == '3') { // Special case for cursors.
-				// For mac they're stored in game binary.
-				result = _filenamePattern.pattern;
-			} else {
-				Common::String pattern = id == 'b' ? bPattern : _filenamePattern.pattern;
-				if (_filenamePattern.genMethod == kGenHEMac)
-					result = Common::String::format("%s (%c)", pattern.c_str(), id);
-				else
-					result = Common::String::format("%s %c", pattern.c_str(), id);
-			}
-		}
-
-		break;
-
-	default:
-		// Fallback to parent method.
-		return ScummEngine_v60he::generateFilename(room);
-	}
-
-	return result;
-}
-
 // The following table includes all the index files, which are embedded in the
 // main game executables in Steam versions.
-static const SteamIndexFile steamIndexFiles[] = {
+const SteamIndexFile steamIndexFiles[] = {
 	{ GID_INDY3, Common::kPlatformWindows,   "%02d.LFL",      "00.LFL",        "Indiana Jones and the Last Crusade.exe",     162056,  6295 },
 	{ GID_INDY3, Common::kPlatformMacintosh, "%02d.LFL",      "00.LFL",        "The Last Crusade",                           150368,  6295 },
 	{ GID_INDY4, Common::kPlatformWindows,   "atlantis.%03d", "ATLANTIS.000",  "Indiana Jones and the Fate of Atlantis.exe", 224336, 12035 },
@@ -242,7 +86,7 @@ const SteamIndexFile *lookUpSteamIndexFile(Common::String pattern, Common::Platf
 	return nullptr;
 }
 
-static Common::String generateFilenameForDetection(const char *pattern, FilenameGenMethod genMethod, Common::Platform platform) {
+Common::String generateFilenameForDetection(const char *pattern, FilenameGenMethod genMethod, Common::Platform platform) {
 	Common::String result;
 
 	switch (genMethod) {
@@ -285,10 +129,6 @@ static Common::String generateFilenameForDetection(const char *pattern, Filename
 	return result;
 }
 
-bool ScummEngine::isMacM68kIMuse() const {
-	return _game.platform == Common::kPlatformMacintosh && (_game.id == GID_MONKEY2 || _game.id == GID_INDY4) && !(_game.features & GF_MAC_CONTAINER);
-}
-
 struct DetectorDesc {
 	Common::FSNode node;
 	Common::String md5;
@@ -297,14 +137,14 @@ struct DetectorDesc {
 
 typedef Common::HashMap<Common::String, DetectorDesc, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> DescMap;
 
-static bool testGame(const GameSettings *g, const DescMap &fileMD5Map, const Common::String &file);
+bool testGame(const GameSettings *g, const DescMap &fileMD5Map, const Common::String &file);
 
 
 // Search for a node with the given "name", inside fslist. Ignores case
 // when performing the matching. The first match is returned, so if you
 // search for "resource" and two nodes "RESOURE and "resource" are present,
 // the first match is used.
-static bool searchFSNode(const Common::FSList &fslist, const Common::String &name, Common::FSNode &result) {
+bool searchFSNode(const Common::FSList &fslist, const Common::String &name, Common::FSNode &result) {
 	for (Common::FSList::const_iterator file = fslist.begin(); file != fslist.end(); ++file) {
 		if (!scumm_stricmp(file->getName().c_str(), name.c_str())) {
 			result = *file;
@@ -314,7 +154,7 @@ static bool searchFSNode(const Common::FSList &fslist, const Common::String &nam
 	return false;
 }
 
-static BaseScummFile *openDiskImage(const Common::FSNode &node, const GameFilenamePattern *gfp) {
+BaseScummFile *openDiskImage(const Common::FSNode &node, const GameFilenamePattern *gfp) {
 	Common::String disk1 = node.getName();
 	BaseScummFile *diskImg;
 
@@ -354,7 +194,7 @@ static BaseScummFile *openDiskImage(const Common::FSNode &node, const GameFilena
 	return 0;
 }
 
-static void closeDiskImage(ScummDiskImage *img) {
+void closeDiskImage(ScummDiskImage *img) {
 	if (img)
 		img->close();
 	SearchMan.remove("tmpDiskImgDir");
@@ -364,7 +204,7 @@ static void closeDiskImage(ScummDiskImage *img) {
  * This function tries to detect if a speech file exists.
  * False doesn't necessarily mean there are no speech files.
  */
-static bool detectSpeech(const Common::FSList &fslist, const GameSettings *gs) {
+bool detectSpeech(const Common::FSList &fslist, const GameSettings *gs) {
 	if (gs->id == GID_MONKEY || gs->id == GID_MONKEY2) {
 		// FM-TOWNS monkey and monkey2 games don't have speech but may have .sou files.
 		if (gs->platform == Common::kPlatformFMTowns)
@@ -401,7 +241,7 @@ static bool detectSpeech(const Common::FSList &fslist, const GameSettings *gs) {
 }
 
 // The following function tries to detect the language for COMI and DIG.
-static Common::Language detectLanguage(const Common::FSList &fslist, byte id) {
+Common::Language detectLanguage(const Common::FSList &fslist, byte id) {
 	// First try to detect Chinese translation.
 	Common::FSNode fontFile;
 
@@ -505,7 +345,7 @@ static Common::Language detectLanguage(const Common::FSList &fslist, byte id) {
 }
 
 
-static void computeGameSettingsFromMD5(const Common::FSList &fslist, const GameFilenamePattern *gfp, const MD5Table *md5Entry, DetectorResult &dr) {
+void computeGameSettingsFromMD5(const Common::FSList &fslist, const GameFilenamePattern *gfp, const MD5Table *md5Entry, DetectorResult &dr) {
 	dr.language = md5Entry->language;
 	dr.extra = md5Entry->extra;
 
@@ -550,7 +390,7 @@ static void computeGameSettingsFromMD5(const Common::FSList &fslist, const GameF
 	}
 }
 
-static void composeFileHashMap(DescMap &fileMD5Map, const Common::FSList &fslist, int depth, const char *const *globs) {
+void composeFileHashMap(DescMap &fileMD5Map, const Common::FSList &fslist, int depth, const char *const *globs) {
 	if (depth <= 0)
 		return;
 
@@ -585,7 +425,7 @@ static void composeFileHashMap(DescMap &fileMD5Map, const Common::FSList &fslist
 	}
 }
 
-static void detectGames(const Common::FSList &fslist, Common::List<DetectorResult> &results, const char *gameid) {
+void detectGames(const Common::FSList &fslist, Common::List<DetectorResult> &results, const char *gameid) {
 	DescMap fileMD5Map;
 	DetectorResult dr;
 
@@ -746,7 +586,7 @@ static void detectGames(const Common::FSList &fslist, Common::List<DetectorResul
 	}
 }
 
-static bool testGame(const GameSettings *g, const DescMap &fileMD5Map, const Common::String &file) {
+bool testGame(const GameSettings *g, const DescMap &fileMD5Map, const Common::String &file) {
 	const DetectorDesc &d = fileMD5Map[file];
 
 	// At this point, we know that the gameid matches, but no variant
@@ -983,40 +823,13 @@ public:
 	const char *getName() const override;
 	const char *getOriginalCopyright() const override;
 
-	bool hasFeature(MetaEngineFeature f) const override;
 	PlainGameList getSupportedGames() const override;
 	PlainGameDescriptor findGame(const char *gameid) const override;
 	DetectedGames detectGames(const Common::FSList &fslist) const override;
 
-	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
-
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
 };
 
-bool ScummMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-bool ScummEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime) ||
-		(f == kSupportsSubtitleOptions);
-}
-
 PlainGameList ScummMetaEngine::getSupportedGames() const {
 	return PlainGameList(gameDescriptions);
 }
@@ -1076,205 +889,6 @@ DetectedGames ScummMetaEngine::detectGames(const Common::FSList &fslist) const {
 	return detectedGames;
 }
 
-/**
- * Create a ScummEngine instance, based on the given detector data.
- *
- * This is heavily based on our MD5 detection scheme.
- */
-Common::Error ScummMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
-	assert(syst);
-	assert(engine);
-	const char *gameid = ConfMan.get("gameid").c_str();
-
-	// We start by checking whether the specified game ID is obsolete.
-	// If that is the case, we automatically upgrade the target to use
-	// the correct new game ID (and platform, if specified).
-	Engines::upgradeTargetIfNecessary(obsoleteGameIDsTable);
-
-	// Fetch the list of files in the current directory.
-	Common::FSList fslist;
-	Common::FSNode dir(ConfMan.get("path"));
-	if (!dir.isDirectory())
-		return Common::kPathNotDirectory;
-	if (!dir.getChildren(fslist, Common::FSNode::kListAll))
-		return Common::kNoGameDataFoundError;
-
-	// Invoke the detector, but fixed to the specified gameid.
-	Common::List<DetectorResult> results;
-	::detectGames(fslist, results, gameid);
-
-	// Unable to locate game data.
-	if (results.empty())
-		return Common::kNoGameDataFoundError;
-
-	// No unique match found. If a platform override is present, try to
-	// narrow down the list a bit more.
-	if (results.size() > 1 && ConfMan.hasKey("platform")) {
-		Common::Platform platform = Common::parsePlatform(ConfMan.get("platform"));
-		Common::List<DetectorResult> tmp;
-
-		// Copy only those candidates which match the platform setting.
-		for (Common::List<DetectorResult>::iterator
-		          x = results.begin(); x != results.end(); ++x) {
-			if (x->game.platform == platform) {
-				tmp.push_back(*x);
-			}
-		}
-
-		// If we narrowed it down too much, print a warning, else use the list
-		// we just computed as new candidates list.
-		if (tmp.empty()) {
-			warning("Engine_SCUMM_create: Game data inconsistent with platform override");
-		} else {
-			results = tmp;
-		}
-	}
-
-	// Still no unique match found -> print a warning.
-	if (results.size() > 1)
-		warning("Engine_SCUMM_create: No unique game candidate found, using first one");
-
-	// Simply use the first match.
-	DetectorResult res(*(results.begin()));
-	debug(1, "Using gameid %s, variant %s, extra %s", res.game.gameid, res.game.variant, res.extra);
-	debug(1, "  SCUMM version %d, HE version %d", res.game.version, res.game.heversion);
-
-	// Print the MD5 of the game; either verbose using printf, in case of an
-	// unknown MD5, or with a medium debug level in case of a known MD5 (for
-	// debugging purposes).
-	if (!findInMD5Table(res.md5.c_str())) {
-		Common::String md5Warning;
-
-		md5Warning = ("Your game version appears to be unknown. If this is *NOT* a fan-modified\n"
-		               "version (in particular, not a fan-made translation), please, report the\n"
-		               "following data to the ScummVM team along with the name of the game you tried\n"
-		               "to add and its version, language, etc.:\n");
-
-		md5Warning += Common::String::format("  SCUMM gameid '%s', file '%s', MD5 '%s'\n\n",
-				res.game.gameid,
-				generateFilenameForDetection(res.fp.pattern, res.fp.genMethod, res.game.platform).c_str(),
-				res.md5.c_str());
-
-		g_system->logMessage(LogMessageType::kWarning, md5Warning.c_str());
-	} else {
-		debug(1, "Using MD5 '%s'", res.md5.c_str());
-	}
-
-	// We don't support the "Lite" version off puttzoo iOS because it contains
-	// the full game.
-	if (!strcmp(res.game.gameid, "puttzoo") && !strcmp(res.extra, "Lite")) {
-		GUIErrorMessage(_("The Lite version of Putt-Putt Saves the Zoo iOS is not supported to avoid piracy.\n"
-		                  "The full version is available for purchase from the iTunes Store."));
-		return Common::kUnsupportedGameidError;
-	}
-
-	// We don't support yet the
-	// the full game.
-	if (!strcmp(res.game.gameid, "pajama2") && !strcmp(res.extra, "Russobit")) {
-		GUIErrorMessage(_("The Russian version of Pajama Sam 2 is not supported yet due to incomplete code."));
-		return Common::kUnsupportedGameidError;
-	}
-
-	// If the GUI options were updated, we catch this here and update them in the users config
-	// file transparently.
-	Common::updateGameGUIOptions(res.game.guioptions, getGameGUIOptionsDescriptionLanguage(res.language));
-
-	// Check for a user override of the platform. We allow the user to override
-	// the platform, to make it possible to add games which are not yet in
-	// our MD5 database but require a specific platform setting.
-	// TODO: Do we really still need/want the platform override?
-	if (ConfMan.hasKey("platform"))
-		res.game.platform = Common::parsePlatform(ConfMan.get("platform"));
-
-	// Language override.
-	if (ConfMan.hasKey("language"))
-		res.language = Common::parseLanguage(ConfMan.get("language"));
-
-	// V3 FM-TOWNS games *always* should use the corresponding music driver,
-	// anything else makes no sense for them.
-	// TODO: Maybe allow the null driver, too?
-	if (res.game.platform == Common::kPlatformFMTowns && res.game.version == 3)
-		res.game.midi = MDT_TOWNS;
-	// Finally, we have massaged the GameDescriptor to our satisfaction, and can
-	// instantiate the appropriate game engine. Hooray!
-	switch (res.game.version) {
-	case 0:
-		*engine = new ScummEngine_v0(syst, res);
-		break;
-	case 1:
-	case 2:
-		*engine = new ScummEngine_v2(syst, res);
-		break;
-	case 3:
-		if (res.game.features & GF_OLD256)
-			*engine = new ScummEngine_v3(syst, res);
-		else
-			*engine = new ScummEngine_v3old(syst, res);
-		break;
-	case 4:
-		*engine = new ScummEngine_v4(syst, res);
-		break;
-	case 5:
-		*engine = new ScummEngine_v5(syst, res);
-		break;
-	case 6:
-		switch (res.game.heversion) {
-#ifdef ENABLE_HE
-		case 200:
-			*engine = new ScummEngine_vCUPhe(syst, res);
-			break;
-		case 101:
-		case 100:
-			*engine = new ScummEngine_v100he(syst, res);
-			break;
-		case 99:
-			*engine = new ScummEngine_v99he(syst, res);
-			break;
-		case 98:
-		case 95:
-		case 90:
-			*engine = new ScummEngine_v90he(syst, res);
-			break;
-		case 85:
-		case 80:
-			*engine = new ScummEngine_v80he(syst, res);
-			break;
-		case 74:
-		case 73:
-		case 72:
-			*engine = new ScummEngine_v72he(syst, res);
-			break;
-		case 71:
-			*engine = new ScummEngine_v71he(syst, res);
-			break;
-#endif
-		case 70:
-			*engine = new ScummEngine_v70he(syst, res);
-			break;
-		case 62:
-		case 61:
-		case 60:
-			*engine = new ScummEngine_v60he(syst, res);
-			break;
-		default:
-			*engine = new ScummEngine_v6(syst, res);
-		}
-		break;
-#ifdef ENABLE_SCUMM_7_8
-	case 7:
-		*engine = new ScummEngine_v7(syst, res);
-		break;
-	case 8:
-		*engine = new ScummEngine_v8(syst, res);
-		break;
-#endif
-	default:
-		error("Engine_SCUMM_create(): Unknown version of game engine");
-	}
-
-	return Common::kNoError;
-}
-
 const char *ScummMetaEngine::getName() const {
 	return "SCUMM ["
 
@@ -1300,86 +914,6 @@ const char *ScummMetaEngine::getOriginalCopyright() const {
 	       "Humongous SCUMM Games (C) Humongous";
 }
 
-namespace Scumm {
-bool getSavegameName(Common::InSaveFile *in, Common::String &desc, int heversion);
-} // End of namespace Scumm
-
-int ScummMetaEngine::getMaximumSaveSlot() const { return 99; }
-
-SaveStateList ScummMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = target;
-	pattern += ".s##";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot.
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-
-		if (slotNum >= 0 && slotNum <= 99) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				Scumm::getSavegameName(in, saveDesc, 0);	// FIXME: heversion?!?
-				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void ScummMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = ScummEngine::makeSavegameName(target, slot, false);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor ScummMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String saveDesc;
-	Graphics::Surface *thumbnail = nullptr;
-	SaveStateMetaInfos infos;
-	memset(&infos, 0, sizeof(infos));
-	SaveStateMetaInfos *infoPtr = &infos;
-
-	// FIXME: heversion?!?
-	if (!ScummEngine::querySaveMetaInfos(target, slot, 0, saveDesc, thumbnail, infoPtr)) {
-		return SaveStateDescriptor();
-	}
-
-	SaveStateDescriptor desc(slot, saveDesc);
-
-	// Do not allow save slot 0 (used for auto-saving) to be deleted or
-	// overwritten.
-	if (slot == 0) {
-		desc.setWriteProtectedFlag(true);
-		desc.setDeletableFlag(false);
-	}
-
-	desc.setThumbnail(thumbnail);
-
-	if (infoPtr) {
-		int day = (infos.date >> 24) & 0xFF;
-		int month = (infos.date >> 16) & 0xFF;
-		int year = infos.date & 0xFFFF;
-
-		desc.setSaveDate(year, month, day);
-
-		int hour = (infos.time >> 8) & 0xFF;
-		int minutes = infos.time & 0xFF;
-
-		desc.setSaveTime(hour, minutes);
-		desc.setPlayTime(infos.playtime * 1000);
-	}
-
-	return desc;
-}
-
 static const ExtraGuiOption comiObjectLabelsOption = {
 	_s("Show Object Line"),
 	_s("Show the names of objects at the bottom of the screen"),
@@ -1405,8 +939,4 @@ const ExtraGuiOptions ScummMetaEngine::getExtraGuiOptions(const Common::String &
 	return options;
 }
 
-#if PLUGIN_ENABLED_DYNAMIC(SCUMM)
-	REGISTER_PLUGIN_DYNAMIC(SCUMM, PLUGIN_TYPE_ENGINE, ScummMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(SCUMM, PLUGIN_TYPE_ENGINE, ScummMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(SCUMM_DETECTION, PLUGIN_TYPE_METAENGINE, ScummMetaEngine);
diff --git a/engines/scumm/metaengine.cpp b/engines/scumm/metaengine.cpp
new file mode 100644
index 0000000000..7fcc636ed5
--- /dev/null
+++ b/engines/scumm/metaengine.cpp
@@ -0,0 +1,523 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/obsolete.h"
+
+#include "common/savefile.h"
+#include "common/config-manager.h"
+#include "common/translation.h"
+#include "common/gui_options.h"
+
+#include "audio/mididrv.h"
+
+#include "scumm/he/intern_he.h"
+#include "scumm/scumm_v0.h"
+#include "scumm/scumm_v8.h"
+#include "scumm/resource.h"
+
+#include "scumm/metaengine.h"
+#include "scumm/detection.h"
+
+namespace Scumm {
+
+Common::String ScummEngine::generateFilename(const int room) const {
+	const int diskNumber = (room > 0) ? _res->_types[rtRoom][room]._roomno : 0;
+	Common::String result;
+
+	if (_game.version == 4) {
+		if (room == 0 || room >= 900) {
+			result = Common::String::format("%03d.lfl", room);
+		} else {
+			result = Common::String::format("disk%02d.lec", diskNumber);
+		}
+	} else {
+		switch (_filenamePattern.genMethod) {
+		case kGenDiskNum:
+		case kGenDiskNumSteam:
+			result = Common::String::format(_filenamePattern.pattern, diskNumber);
+			break;
+
+		case kGenRoomNum:
+		case kGenRoomNumSteam:
+			result = Common::String::format(_filenamePattern.pattern, room);
+			break;
+
+		case kGenUnchanged:
+			result = _filenamePattern.pattern;
+			break;
+
+		default:
+			error("generateFilename: Unsupported genMethod");
+		}
+	}
+
+	return result;
+}
+
+Common::String ScummEngine_v60he::generateFilename(const int room) const {
+	Common::String result;
+	char id = 0;
+
+	switch (_filenamePattern.genMethod) {
+	case kGenHEMac:
+	case kGenHEMacNoParens:
+	case kGenHEPC:
+		if (room < 0) {
+			id = '0' - room;
+		} else {
+			const int diskNumber = (room > 0) ? _res->_types[rtRoom][room]._roomno : 0;
+			id = diskNumber + '0';
+		}
+
+		if (_filenamePattern.genMethod == kGenHEPC) {
+			result = Common::String::format("%s.he%c", _filenamePattern.pattern, id);
+		} else {
+			if (id == '3') { // Special case for cursors.
+				// For mac they're stored in game binary.
+				result = _filenamePattern.pattern;
+			} else {
+				if (_filenamePattern.genMethod == kGenHEMac)
+					result = Common::String::format("%s (%c)", _filenamePattern.pattern, id);
+				else
+					result = Common::String::format("%s %c", _filenamePattern.pattern, id);
+			}
+		}
+
+		break;
+
+	default:
+		// Fallback to parent method.
+		return ScummEngine::generateFilename(room);
+	}
+
+	return result;
+}
+
+Common::String ScummEngine_v70he::generateFilename(const int room) const {
+	Common::String result;
+	char id = 0;
+
+	Common::String bPattern = _filenamePattern.pattern;
+
+	// Special cases for Blue's games, which share common (b) files.
+	if (_game.id == GID_BIRTHDAYYELLOW || _game.id == GID_BIRTHDAYRED)
+		bPattern = "Blue'sBirthday";
+	else if (_game.id == GID_TREASUREHUNT)
+		bPattern = "Blue'sTreasureHunt";
+
+	switch (_filenamePattern.genMethod) {
+	case kGenHEMac:
+	case kGenHEMacNoParens:
+	case kGenHEPC:
+	case kGenHEIOS:
+		if (_game.heversion >= 98 && room >= 0) {
+			int disk = 0;
+			if (_heV7DiskOffsets)
+				disk = _heV7DiskOffsets[room];
+
+			switch (disk) {
+			case 2:
+				id = 'b';
+				result = bPattern + ".(b)";
+				break;
+			case 1:
+				id = 'a';
+				// Some of the newer HE games for iOS use the ".hea" suffix instead.
+				if (_filenamePattern.genMethod == kGenHEIOS)
+					result = Common::String::format("%s.hea", _filenamePattern.pattern);
+				else
+					result = Common::String::format("%s.(a)", _filenamePattern.pattern);
+				break;
+			default:
+				id = '0';
+				result = Common::String::format("%s.he0", _filenamePattern.pattern);
+			}
+		} else if (room < 0) {
+			id = '0' - room;
+		} else {
+			id = (room == 0) ? '0' : '1';
+		}
+
+		if (_filenamePattern.genMethod == kGenHEPC || _filenamePattern.genMethod == kGenHEIOS) {
+			if (id == '3' && _game.id == GID_MOONBASE) {
+				result = Common::String::format("%s.u32", _filenamePattern.pattern);
+				break;
+			}
+
+			// For HE >= 98, we already called snprintf above.
+			if (_game.heversion < 98 || room < 0)
+				result = Common::String::format("%s.he%c", _filenamePattern.pattern, id);
+		} else {
+			if (id == '3') { // Special case for cursors.
+				// For mac they're stored in game binary.
+				result = _filenamePattern.pattern;
+			} else {
+				Common::String pattern = id == 'b' ? bPattern : _filenamePattern.pattern;
+				if (_filenamePattern.genMethod == kGenHEMac)
+					result = Common::String::format("%s (%c)", pattern.c_str(), id);
+				else
+					result = Common::String::format("%s %c", pattern.c_str(), id);
+			}
+		}
+
+		break;
+
+	default:
+		// Fallback to parent method.
+		return ScummEngine_v60he::generateFilename(room);
+	}
+
+	return result;
+}
+
+bool ScummEngine::isMacM68kIMuse() const {
+	return _game.platform == Common::kPlatformMacintosh && (_game.id == GID_MONKEY2 || _game.id == GID_INDY4) && !(_game.features & GF_MAC_CONTAINER);
+}
+
+} // End of namespace Scumm
+
+#pragma mark -
+#pragma mark --- Plugin code ---
+#pragma mark -
+
+namespace Scumm {
+
+void detectGames(const Common::FSList &fslist, Common::List<DetectorResult> &results, const char *gameid);
+
+struct MD5Table;
+const MD5Table *findInMD5Table(const char *md5);
+
+Common::String generateFilenameForDetection(const char *pattern, FilenameGenMethod genMethod, Common::Platform platform);
+
+bool getSavegameName(Common::InSaveFile *in, Common::String &desc, int heversion);
+
+} // End of namespace Scumm
+
+using namespace Scumm;
+
+const char *ScummMetaEngineConnect::getName() const {
+    return "Scumm";
+}
+
+bool ScummMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+bool ScummEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime) ||
+		(f == kSupportsSubtitleOptions);
+}
+
+
+#include "scumm/obsolete.h"
+
+/**
+ * Create a ScummEngine instance, based on the given detector data.
+ *
+ * This is heavily based on our MD5 detection scheme.
+ */
+Common::Error ScummMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
+	assert(syst);
+	assert(engine);
+	const char *gameid = ConfMan.get("gameid").c_str();
+
+	// We start by checking whether the specified game ID is obsolete.
+	// If that is the case, we automatically upgrade the target to use
+	// the correct new game ID (and platform, if specified).
+	Engines::upgradeTargetIfNecessary(obsoleteGameIDsTable);
+
+	// Fetch the list of files in the current directory.
+	Common::FSList fslist;
+	Common::FSNode dir(ConfMan.get("path"));
+	if (!dir.isDirectory())
+		return Common::kPathNotDirectory;
+	if (!dir.getChildren(fslist, Common::FSNode::kListAll))
+		return Common::kNoGameDataFoundError;
+
+	// Invoke the detector, but fixed to the specified gameid.
+	Common::List<DetectorResult> results;
+	::detectGames(fslist, results, gameid);
+
+	// Unable to locate game data.
+	if (results.empty())
+		return Common::kNoGameDataFoundError;
+
+	// No unique match found. If a platform override is present, try to
+	// narrow down the list a bit more.
+	if (results.size() > 1 && ConfMan.hasKey("platform")) {
+		Common::Platform platform = Common::parsePlatform(ConfMan.get("platform"));
+		Common::List<DetectorResult> tmp;
+
+		// Copy only those candidates which match the platform setting.
+		for (Common::List<DetectorResult>::iterator
+		          x = results.begin(); x != results.end(); ++x) {
+			if (x->game.platform == platform) {
+				tmp.push_back(*x);
+			}
+		}
+
+		// If we narrowed it down too much, print a warning, else use the list
+		// we just computed as new candidates list.
+		if (tmp.empty()) {
+			warning("Engine_SCUMM_create: Game data inconsistent with platform override");
+		} else {
+			results = tmp;
+		}
+	}
+
+	// Still no unique match found -> print a warning.
+	if (results.size() > 1)
+		warning("Engine_SCUMM_create: No unique game candidate found, using first one");
+
+	// Simply use the first match.
+	DetectorResult res(*(results.begin()));
+	debug(1, "Using gameid %s, variant %s, extra %s", res.game.gameid, res.game.variant, res.extra);
+	debug(1, "  SCUMM version %d, HE version %d", res.game.version, res.game.heversion);
+
+	// Print the MD5 of the game; either verbose using printf, in case of an
+	// unknown MD5, or with a medium debug level in case of a known MD5 (for
+	// debugging purposes).
+	if (!findInMD5Table(res.md5.c_str())) {
+		Common::String md5Warning;
+
+		md5Warning = ("Your game version appears to be unknown. If this is *NOT* a fan-modified\n"
+		               "version (in particular, not a fan-made translation), please, report the\n"
+		               "following data to the ScummVM team along with the name of the game you tried\n"
+		               "to add and its version, language, etc.:\n");
+
+		md5Warning += Common::String::format("  SCUMM gameid '%s', file '%s', MD5 '%s'\n\n",
+				res.game.gameid,
+				generateFilenameForDetection(res.fp.pattern, res.fp.genMethod, res.game.platform).c_str(),
+				res.md5.c_str());
+
+		g_system->logMessage(LogMessageType::kWarning, md5Warning.c_str());
+	} else {
+		debug(1, "Using MD5 '%s'", res.md5.c_str());
+	}
+
+	// We don't support the "Lite" version off puttzoo iOS because it contains
+	// the full game.
+	if (!strcmp(res.game.gameid, "puttzoo") && !strcmp(res.extra, "Lite")) {
+		GUIErrorMessage(_("The Lite version of Putt-Putt Saves the Zoo iOS is not supported to avoid piracy.\n"
+		                  "The full version is available for purchase from the iTunes Store."));
+		return Common::kUnsupportedGameidError;
+	}
+
+	// We don't support yet the
+	// the full game.
+	if (!strcmp(res.game.gameid, "pajama2") && !strcmp(res.extra, "Russobit")) {
+		GUIErrorMessage(_("The Russian version of Pajama Sam 2 is not supported yet due to incomplete code."));
+		return Common::kUnsupportedGameidError;
+	}
+
+	// If the GUI options were updated, we catch this here and update them in the users config
+	// file transparently.
+	Common::updateGameGUIOptions(res.game.guioptions, getGameGUIOptionsDescriptionLanguage(res.language));
+
+	// Check for a user override of the platform. We allow the user to override
+	// the platform, to make it possible to add games which are not yet in
+	// our MD5 database but require a specific platform setting.
+	// TODO: Do we really still need/want the platform override?
+	if (ConfMan.hasKey("platform"))
+		res.game.platform = Common::parsePlatform(ConfMan.get("platform"));
+
+	// Language override.
+	if (ConfMan.hasKey("language"))
+		res.language = Common::parseLanguage(ConfMan.get("language"));
+
+	// V3 FM-TOWNS games *always* should use the corresponding music driver,
+	// anything else makes no sense for them.
+	// TODO: Maybe allow the null driver, too?
+	if (res.game.platform == Common::kPlatformFMTowns && res.game.version == 3)
+		res.game.midi = MDT_TOWNS;
+	// Finally, we have massaged the GameDescriptor to our satisfaction, and can
+	// instantiate the appropriate game engine. Hooray!
+	switch (res.game.version) {
+	case 0:
+		*engine = new ScummEngine_v0(syst, res);
+		break;
+	case 1:
+	case 2:
+		*engine = new ScummEngine_v2(syst, res);
+		break;
+	case 3:
+		if (res.game.features & GF_OLD256)
+			*engine = new ScummEngine_v3(syst, res);
+		else
+			*engine = new ScummEngine_v3old(syst, res);
+		break;
+	case 4:
+		*engine = new ScummEngine_v4(syst, res);
+		break;
+	case 5:
+		*engine = new ScummEngine_v5(syst, res);
+		break;
+	case 6:
+		switch (res.game.heversion) {
+#ifdef ENABLE_HE
+		case 200:
+			*engine = new ScummEngine_vCUPhe(syst, res);
+			break;
+		case 101:
+		case 100:
+			*engine = new ScummEngine_v100he(syst, res);
+			break;
+		case 99:
+			*engine = new ScummEngine_v99he(syst, res);
+			break;
+		case 98:
+		case 95:
+		case 90:
+			*engine = new ScummEngine_v90he(syst, res);
+			break;
+		case 85:
+		case 80:
+			*engine = new ScummEngine_v80he(syst, res);
+			break;
+		case 74:
+		case 73:
+		case 72:
+			*engine = new ScummEngine_v72he(syst, res);
+			break;
+		case 71:
+			*engine = new ScummEngine_v71he(syst, res);
+			break;
+#endif
+		case 70:
+			*engine = new ScummEngine_v70he(syst, res);
+			break;
+		case 62:
+		case 61:
+		case 60:
+			*engine = new ScummEngine_v60he(syst, res);
+			break;
+		default:
+			*engine = new ScummEngine_v6(syst, res);
+		}
+		break;
+#ifdef ENABLE_SCUMM_7_8
+	case 7:
+		*engine = new ScummEngine_v7(syst, res);
+		break;
+	case 8:
+		*engine = new ScummEngine_v8(syst, res);
+		break;
+#endif
+	default:
+		error("Engine_SCUMM_create(): Unknown version of game engine");
+	}
+
+	return Common::kNoError;
+}
+
+int ScummMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+
+SaveStateList ScummMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = target;
+	pattern += ".s##";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot.
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+
+		if (slotNum >= 0 && slotNum <= 99) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				Scumm::getSavegameName(in, saveDesc, 0);	// FIXME: heversion?!?
+				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void ScummMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = ScummEngine::makeSavegameName(target, slot, false);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor ScummMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String saveDesc;
+	Graphics::Surface *thumbnail = nullptr;
+	SaveStateMetaInfos infos;
+	memset(&infos, 0, sizeof(infos));
+	SaveStateMetaInfos *infoPtr = &infos;
+
+	// FIXME: heversion?!?
+	if (!ScummEngine::querySaveMetaInfos(target, slot, 0, saveDesc, thumbnail, infoPtr)) {
+		return SaveStateDescriptor();
+	}
+
+	SaveStateDescriptor desc(slot, saveDesc);
+
+	// Do not allow save slot 0 (used for auto-saving) to be deleted or
+	// overwritten.
+	if (slot == 0) {
+		desc.setWriteProtectedFlag(true);
+		desc.setDeletableFlag(false);
+	}
+
+	desc.setThumbnail(thumbnail);
+
+	if (infoPtr) {
+		int day = (infos.date >> 24) & 0xFF;
+		int month = (infos.date >> 16) & 0xFF;
+		int year = infos.date & 0xFFFF;
+
+		desc.setSaveDate(year, month, day);
+
+		int hour = (infos.time >> 8) & 0xFF;
+		int minutes = infos.time & 0xFF;
+
+		desc.setSaveTime(hour, minutes);
+		desc.setPlayTime(infos.playtime * 1000);
+	}
+
+	return desc;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(SCUMM)
+	REGISTER_PLUGIN_DYNAMIC(SCUMM, PLUGIN_TYPE_ENGINE, ScummMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(SCUMM, PLUGIN_TYPE_ENGINE, ScummMetaEngineConnect);
+#endif
diff --git a/engines/scumm/metaengine.h b/engines/scumm/metaengine.h
new file mode 100644
index 0000000000..a2669276a1
--- /dev/null
+++ b/engines/scumm/metaengine.h
@@ -0,0 +1,36 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/metaengine.h"
+
+class ScummMetaEngineConnect : public MetaEngineConnect {
+    virtual const char *getName() const override;
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+    Common::Error createInstance(OSystem *syst, Engine **engine) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
diff --git a/engines/scumm/module.mk b/engines/scumm/module.mk
index b6a90bd6bd..f7096acc2d 100644
--- a/engines/scumm/module.mk
+++ b/engines/scumm/module.mk
@@ -35,6 +35,7 @@ MODULE_OBJS := \
 	imuse/drivers/mac_m68k.o \
 	imuse/drivers/pcspk.o \
 	input.o \
+	metaengine.o \
 	midiparser_ro.o \
 	object.o \
 	palette.o \
@@ -168,3 +169,12 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects, if building as a Dynamic Plugin.
+# Scumm uses detection files when creating an instance,
+# so we can't remove dependency completely.
+ifeq ($(ENABLE_SCUMM), DYNAMIC_PLUGIN)
+DETECT_OBJS += $(MODULE)/detection.o
+DETECT_OBJS += $(MODULE)/file.o
+DETECT_OBJS += $(MODULE)/file_nes.o
+endif


Commit: 4c1a03845f8146b8e06a1ab106615b9f1611d4d6
    https://github.com/scummvm/scummvm/commit/4c1a03845f8146b8e06a1ab106615b9f1611d4d6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCUMM: Refactoring, remove detection.o dependency from modules.

- Move detection code used by createInstance & MetaEngine to a common header - detection_internal.h
- Move steam-related method & table to detection_steam.h
- More info in comments.

Changed paths:
  A engines/scumm/detection_internal.h
  A engines/scumm/detection_steam.h
    engines/scumm/detection.cpp
    engines/scumm/file.h
    engines/scumm/metaengine.cpp
    engines/scumm/metaengine.h
    engines/scumm/module.mk
    engines/scumm/obsolete.h
    engines/scumm/scumm.cpp


diff --git a/engines/scumm/detection.cpp b/engines/scumm/detection.cpp
index 0bc9cb484d..0b316898b7 100644
--- a/engines/scumm/detection.cpp
+++ b/engines/scumm/detection.cpp
@@ -38,774 +38,14 @@
 #include "scumm/file.h"
 #include "scumm/file_nes.h"
 
-
-namespace Scumm {
-
-enum {
-	// We only compute the MD5 of the first megabyte of our data files.
-	kMD5FileSizeLimit = 1024 * 1024
-};
-
 #pragma mark -
-#pragma mark --- Miscellaneous ---
+#pragma mark --- Detection code ---
 #pragma mark -
 
-int compareMD5Table(const void *a, const void *b) {
-	const char *key = (const char *)a;
-	const MD5Table *elem = (const MD5Table *)b;
-	return strcmp(key, elem->md5);
-}
-
-const MD5Table *findInMD5Table(const char *md5) {
-	uint32 arraySize = ARRAYSIZE(md5table) - 1;
-	return (const MD5Table *)bsearch(md5, md5table, arraySize, sizeof(MD5Table), compareMD5Table);
-}
-
-// The following table includes all the index files, which are embedded in the
-// main game executables in Steam versions.
-const SteamIndexFile steamIndexFiles[] = {
-	{ GID_INDY3, Common::kPlatformWindows,   "%02d.LFL",      "00.LFL",        "Indiana Jones and the Last Crusade.exe",     162056,  6295 },
-	{ GID_INDY3, Common::kPlatformMacintosh, "%02d.LFL",      "00.LFL",        "The Last Crusade",                           150368,  6295 },
-	{ GID_INDY4, Common::kPlatformWindows,   "atlantis.%03d", "ATLANTIS.000",  "Indiana Jones and the Fate of Atlantis.exe", 224336, 12035 },
-	{ GID_INDY4, Common::kPlatformMacintosh, "atlantis.%03d", "ATLANTIS.000",  "The Fate of Atlantis",                       260224, 12035 },
-	{ GID_LOOM,  Common::kPlatformWindows,   "%03d.LFL",      "000.LFL",       "Loom.exe",                                   187248,  8307 },
-	{ GID_LOOM,  Common::kPlatformMacintosh, "%03d.LFL",      "000.LFL",       "Loom",                                       170464,  8307 },
-#ifdef ENABLE_SCUMM_7_8
-	{ GID_DIG,   Common::kPlatformWindows,   "dig.la%d",      "DIG.LA0",       "The Dig.exe",                                340632, 16304 },
-	{ GID_DIG,   Common::kPlatformMacintosh, "dig.la%d",      "DIG.LA0",       "The Dig",                                    339744, 16304 },
-#endif
-	{ 0,         Common::kPlatformUnknown,   nullptr,         nullptr,         nullptr,                                           0,     0 }
-};
-
-const SteamIndexFile *lookUpSteamIndexFile(Common::String pattern, Common::Platform platform) {
-	for (const SteamIndexFile *indexFile = steamIndexFiles; indexFile->len; ++indexFile) {
-		if (platform == indexFile->platform && pattern.equalsIgnoreCase(indexFile->pattern))
-			return indexFile;
-	}
-
-	return nullptr;
-}
-
-Common::String generateFilenameForDetection(const char *pattern, FilenameGenMethod genMethod, Common::Platform platform) {
-	Common::String result;
-
-	switch (genMethod) {
-	case kGenDiskNum:
-	case kGenRoomNum:
-		result = Common::String::format(pattern, 0);
-		break;
-
-	case kGenDiskNumSteam:
-	case kGenRoomNumSteam: {
-		const SteamIndexFile *indexFile = lookUpSteamIndexFile(pattern, platform);
-		if (!indexFile) {
-			error("Unable to find Steam executable from detection pattern");
-		} else {
-			result = indexFile->executableName;
-		}
-		} break;
-
-	case kGenHEPC:
-	case kGenHEIOS:
-		result = Common::String::format("%s.he0", pattern);
-		break;
-
-	case kGenHEMac:
-		result = Common::String::format("%s (0)", pattern);
-		break;
-
-	case kGenHEMacNoParens:
-		result = Common::String::format("%s 0", pattern);
-		break;
-
-	case kGenUnchanged:
-		result = pattern;
-		break;
-
-	default:
-		error("generateFilenameForDetection: Unsupported genMethod");
-	}
-
-	return result;
-}
-
-struct DetectorDesc {
-	Common::FSNode node;
-	Common::String md5;
-	const MD5Table *md5Entry;	// Entry of the md5 table corresponding to this file, if any.
-};
-
-typedef Common::HashMap<Common::String, DetectorDesc, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> DescMap;
-
-bool testGame(const GameSettings *g, const DescMap &fileMD5Map, const Common::String &file);
-
-
-// Search for a node with the given "name", inside fslist. Ignores case
-// when performing the matching. The first match is returned, so if you
-// search for "resource" and two nodes "RESOURE and "resource" are present,
-// the first match is used.
-bool searchFSNode(const Common::FSList &fslist, const Common::String &name, Common::FSNode &result) {
-	for (Common::FSList::const_iterator file = fslist.begin(); file != fslist.end(); ++file) {
-		if (!scumm_stricmp(file->getName().c_str(), name.c_str())) {
-			result = *file;
-			return true;
-		}
-	}
-	return false;
-}
-
-BaseScummFile *openDiskImage(const Common::FSNode &node, const GameFilenamePattern *gfp) {
-	Common::String disk1 = node.getName();
-	BaseScummFile *diskImg;
-
-	SearchMan.addDirectory("tmpDiskImgDir", node.getParent());
-
-	if (disk1.hasSuffix(".prg")) { // NES
-		diskImg = new ScummNESFile();
-	} else { // C64 or Apple //gs
-		// setup necessary game settings for disk image reader
-		GameSettings gs;
-		memset(&gs, 0, sizeof(GameSettings));
-		gs.gameid = gfp->gameid;
-		gs.id = (Common::String(gfp->gameid) == "maniac" ? GID_MANIAC : GID_ZAK);
-		gs.platform = gfp->platform;
-		if (strcmp(gfp->pattern, "maniacdemo.d64") == 0)
-			gs.features |= GF_DEMO;
-
-		// Determine second disk file name.
-		Common::String disk2(disk1);
-		for (Common::String::iterator it = disk2.begin(); it != disk2.end(); ++it) {
-			// replace "xyz1.(d64|dsk)" by "xyz2.(d64|dsk)"
-			if (*it == '1') {
-				*it = '2';
-				break;
-			}
-		}
-
-		// Open image.
-		diskImg = new ScummDiskImage(disk1.c_str(), disk2.c_str(), gs);
-	}
-
-	if (diskImg->open(disk1.c_str()) && diskImg->openSubFile("00.LFL")) {
-		debug(0, "Success");
-		return diskImg;
-	}
-	delete diskImg;
-	return 0;
-}
-
-void closeDiskImage(ScummDiskImage *img) {
-	if (img)
-		img->close();
-	SearchMan.remove("tmpDiskImgDir");
-}
-
-/*
- * This function tries to detect if a speech file exists.
- * False doesn't necessarily mean there are no speech files.
- */
-bool detectSpeech(const Common::FSList &fslist, const GameSettings *gs) {
-	if (gs->id == GID_MONKEY || gs->id == GID_MONKEY2) {
-		// FM-TOWNS monkey and monkey2 games don't have speech but may have .sou files.
-		if (gs->platform == Common::kPlatformFMTowns)
-			return false;
-
-		const char *const basenames[] = { gs->gameid, "monster", 0 };
-		static const char *const extensions[] = { "sou",
-#ifdef USE_FLAC
-		 "sof",
-#endif
-#ifdef USE_VORBIS
-		 "sog",
-#endif
-#ifdef USE_MAD
-		 "so3",
-#endif
-		 0 };
-
-		for (Common::FSList::const_iterator file = fslist.begin(); file != fslist.end(); ++file) {
-			if (file->isDirectory())
-				continue;
-
-			for (int i = 0; basenames[i]; ++i) {
-				Common::String basename = Common::String(basenames[i]) + ".";
-
-				for (int j = 0; extensions[j]; ++j) {
-					if ((basename + extensions[j]).equalsIgnoreCase(file->getName()))
-						return true;
-				}
-			}
-		}
-	}
-	return false;
-}
-
-// The following function tries to detect the language for COMI and DIG.
-Common::Language detectLanguage(const Common::FSList &fslist, byte id) {
-	// First try to detect Chinese translation.
-	Common::FSNode fontFile;
-
-	if (searchFSNode(fslist, "chinese_gb16x12.fnt", fontFile)) {
-		debug(0, "Chinese detected");
-		return Common::ZH_CNA;
-	}
-
-	// Now try to detect COMI and Dig by language files.
-	if (id != GID_CMI && id != GID_DIG)
-		return Common::UNK_LANG;
-
-	// Check for LANGUAGE.BND (Dig) resp. LANGUAGE.TAB (CMI).
-	// These are usually inside the "RESOURCE" subdirectory.
-	// If found, we match based on the file size (should we
-	// ever determine that this is insufficient, we can still
-	// switch to MD5 based detection).
-	const char *filename = (id == GID_CMI) ? "LANGUAGE.TAB" : "LANGUAGE.BND";
-	Common::File tmp;
-	Common::FSNode langFile;
-	if (searchFSNode(fslist, filename, langFile))
-		tmp.open(langFile);
-	if (!tmp.isOpen()) {
-		// Try loading in RESOURCE sub dir.
-		Common::FSNode resDir;
-		Common::FSList tmpList;
-		if (searchFSNode(fslist, "RESOURCE", resDir)
-			&& resDir.isDirectory()
-			&& resDir.getChildren(tmpList, Common::FSNode::kListFilesOnly)
-			&& searchFSNode(tmpList, filename, langFile)) {
-			tmp.open(langFile);
-		}
-		// The Steam version of Dig has the LANGUAGE.BND in the DIG sub dir.
-		if (!tmp.isOpen()
-			&& id == GID_DIG
-			&& searchFSNode(fslist, "DIG", resDir)
-			&& resDir.isDirectory()
-			&& resDir.getChildren(tmpList, Common::FSNode::kListFilesOnly)
-			&& searchFSNode(tmpList, filename, langFile)) {
-			tmp.open(langFile);
-		}
-		// The Chinese version of Dig has the LANGUAGE.BND in the VIDEO sub dir.
-		if (!tmp.isOpen()
-			&& id == GID_DIG
-			&& searchFSNode(fslist, "VIDEO", resDir)
-			&& resDir.isDirectory()
-			&& resDir.getChildren(tmpList, Common::FSNode::kListFilesOnly)
-			&& searchFSNode(tmpList, filename, langFile)) {
-			tmp.open(langFile);
-		}
-	}
-	if (tmp.isOpen()) {
-		uint size = tmp.size();
-		if (id == GID_CMI) {
-			switch (size) {
-			case 439080:	// 2daf3db71d23d99d19fc9a544fcf6431
-				return Common::EN_ANY;
-			case 322602:	// caba99f4f5a0b69963e5a4d69e6f90af
-				return Common::ZH_TWN;
-			case 493252:	// 5d59594b24f3f1332e7d7e17455ed533
-				return Common::DE_DEU;
-			case 461746:	// 35bbe0e4d573b318b7b2092c331fd1fa
-				return Common::FR_FRA;
-			case 443439:	// 4689d013f67aabd7c35f4fd7c4b4ad69
-				return Common::IT_ITA;
-			case 398613:	// d1f5750d142d34c4c8f1f330a1278709
-				return Common::KO_KOR;
-			case 440586:	// 5a1d0f4fa00917bdbfe035a72a6bba9d
-				return Common::PT_BRA;
-			case 454457:	// 0e5f450ec474a30254c0e36291fb4ebd
-			case 394083:	// ad684ca14c2b4bf4c21a81c1dbed49bc
-				return Common::RU_RUS;
-			case 449787:	// 64f3fe479d45b52902cf88145c41d172
-				return Common::ES_ESP;
-			default:
-				break;
-			}
-		} else { // The DIG
-			switch (size) {
-			case 248627:	// 1fd585ac849d57305878c77b2f6c74ff
-				return Common::DE_DEU;
-			case 257460:	// 04cf6a6ba6f57e517bc40eb81862cfb0
-				return Common::FR_FRA;
-			case 231402:	// 93d13fcede954c78e65435592182a4db
-				return Common::IT_ITA;
-			case 228772:	// 5d9ad90d3a88ea012d25d61791895ebe
-				return Common::PT_BRA;
-			case 229884:	// d890074bc15c6135868403e73c5f4f36
-				return Common::ES_ESP;
-			case 223107:	// 64f3fe479d45b52902cf88145c41d172
-				return Common::JA_JPN;
-			case 180730:	// 424fdd60822722cdc75356d921dad9bf
-				return Common::ZH_TWN;
-			default:
-				break;
-			}
-		}
-	}
-
-	return Common::UNK_LANG;
-}
-
-
-void computeGameSettingsFromMD5(const Common::FSList &fslist, const GameFilenamePattern *gfp, const MD5Table *md5Entry, DetectorResult &dr) {
-	dr.language = md5Entry->language;
-	dr.extra = md5Entry->extra;
-
-	// Compute the precise game settings using gameVariantsTable.
-	for (const GameSettings *g = gameVariantsTable; g->gameid; ++g) {
-		if (g->gameid[0] == 0 || !scumm_stricmp(md5Entry->gameid, g->gameid)) {
-			// The gameid either matches, or is empty. The latter indicates
-			// a generic entry, currently used for some generic HE settings.
-			if (g->variant == 0 || !scumm_stricmp(md5Entry->variant, g->variant)) {
-				// Perfect match found, use it and stop the loop.
-				dr.game = *g;
-				dr.game.gameid = md5Entry->gameid;
-
-				// Set the platform value. The value from the MD5 record has
-				// highest priority; if missing (i.e. set to unknown) we try
-				// to use that from the filename pattern record instead.
-				if (md5Entry->platform != Common::kPlatformUnknown) {
-					dr.game.platform = md5Entry->platform;
-				} else if (gfp->platform != Common::kPlatformUnknown) {
-					dr.game.platform = gfp->platform;
-				}
-
-				// HACK: Special case to distinguish the V1 demo from the full version
-				// (since they have identical MD5).
-				if (dr.game.id == GID_MANIAC && !strcmp(gfp->pattern, "%02d.MAN")) {
-					dr.extra = "V1 Demo";
-					dr.game.features = GF_DEMO;
-				}
-
-				// HACK: Try to detect languages for translated games.
-				if (dr.language == UNK_LANG) {
-					dr.language = detectLanguage(fslist, dr.game.id);
-				}
-
-				// HACK: Detect between 68k and PPC versions.
-				if (dr.game.platform == Common::kPlatformMacintosh && dr.game.version >= 5 && dr.game.heversion == 0 && strstr(gfp->pattern, "Data"))
-					dr.game.features |= GF_MAC_CONTAINER;
-
-				break;
-			}
-		}
-	}
-}
-
-void composeFileHashMap(DescMap &fileMD5Map, const Common::FSList &fslist, int depth, const char *const *globs) {
-	if (depth <= 0)
-		return;
-
-	if (fslist.empty())
-		return;
-
-	for (Common::FSList::const_iterator file = fslist.begin(); file != fslist.end(); ++file) {
-		if (!file->isDirectory()) {
-			DetectorDesc d;
-			d.node = *file;
-			d.md5Entry = 0;
-			fileMD5Map[file->getName()] = d;
-		} else {
-			if (!globs)
-				continue;
-
-			bool matched = false;
-			for (const char *const *glob = globs; *glob; glob++)
-				if (file->getName().matchString(*glob, true)) {
-					matched = true;
-					break;
-				}
-
-			if (!matched)
-				continue;
-
-			Common::FSList files;
-			if (file->getChildren(files, Common::FSNode::kListAll)) {
-				composeFileHashMap(fileMD5Map, files, depth - 1, globs);
-			}
-		}
-	}
-}
-
-void detectGames(const Common::FSList &fslist, Common::List<DetectorResult> &results, const char *gameid) {
-	DescMap fileMD5Map;
-	DetectorResult dr;
-
-	// Dive one level down since mac indy3/loom have their files split into directories. See Bug #1438631.
-	// Dive two levels down for Mac Steam games.
-	composeFileHashMap(fileMD5Map, fslist, 3, directoryGlobs);
-
-	// Iterate over all filename patterns.
-	for (const GameFilenamePattern *gfp = gameFilenamesTable; gfp->gameid; ++gfp) {
-		// If a gameid was specified, we only try to detect that specific game,
-		// so we can just skip over everything with a differing gameid.
-		if (gameid && scumm_stricmp(gameid, gfp->gameid))
-			continue;
-
-		// Generate the detectname corresponding to the gfp. If the file doesn't
-		// exist in the directory we are looking at, we can skip to the next
-		// one immediately.
-		Common::String file(generateFilenameForDetection(gfp->pattern, gfp->genMethod, gfp->platform));
-		if (!fileMD5Map.contains(file))
-			continue;
-
-		// Reset the DetectorResult variable.
-		dr.fp.pattern = gfp->pattern;
-		dr.fp.genMethod = gfp->genMethod;
-		dr.game.gameid = 0;
-		dr.language = gfp->language;
-		dr.md5.clear();
-		dr.extra = 0;
-
-		//  ____            _     _
-		// |  _ \ __ _ _ __| |_  / |
-		// | |_) / _` | '__| __| | |
-		// |  __/ (_| | |  | |_  | |
-		// |_|   \__,_|_|   \__| |_|
-		//
-		// PART 1: Trying to find an exact match using MD5.
-		//
-		//
-		// Background: We found a valid detection file. Check if its MD5
-		// checksum occurs in our MD5 table. If it does, try to use that
-		// to find an exact match.
-		//
-		// We only do that if the MD5 hadn't already been computed (since
-		// we may look at some detection files multiple times).
-		DetectorDesc &d = fileMD5Map[file];
-		if (d.md5.empty()) {
-			Common::SeekableReadStream *tmp = 0;
-			bool isDiskImg = (file.hasSuffix(".d64") || file.hasSuffix(".dsk") || file.hasSuffix(".prg"));
-
-			if (isDiskImg) {
-				tmp = openDiskImage(d.node, gfp);
-
-				debug(2, "Falling back to disk-based detection");
-			} else {
-				tmp = d.node.createReadStream();
-			}
-
-			Common::String md5str;
-			if (tmp)
-				md5str = computeStreamMD5AsString(*tmp, kMD5FileSizeLimit);
-			if (!md5str.empty()) {
-
-				d.md5 = md5str;
-				d.md5Entry = findInMD5Table(md5str.c_str());
-
-				dr.md5 = d.md5;
-
-				if (d.md5Entry) {
-					// Exact match found. Compute the precise game settings.
-					computeGameSettingsFromMD5(fslist, gfp, d.md5Entry, dr);
-
-					// Print some debug info.
-					int filesize = tmp->size();
-					debug(1, "SCUMM detector found matching file '%s' with MD5 %s, size %d\n",
-						file.c_str(), md5str.c_str(), filesize);
-
-					// Sanity check: We *should* have found a matching gameid/variant at this point.
-					// If not, we may have #ifdef'ed the entry out in our detection_tables.h, because we
-					// don't have the required stuff compiled in, or there's a bug in our data tables.
-					if (dr.game.gameid != 0)
-						// Add it to the list of detected games.
-						results.push_back(dr);
-				}
-			}
-
-			if (isDiskImg)
-				closeDiskImage((ScummDiskImage *)tmp);
-			delete tmp;
-		}
-
-		// If an exact match for this file has already been found, don't bother
-		// looking at it anymore.
-		if (d.md5Entry)
-			continue;
-
-		// Prevent executables being detected as Steam variant. If we don't
-		// know the md5, then it's just the regular executable. Otherwise we
-		// will most likely fail on trying to read the index from the executable.
-		// Fixes bug #10290.
-		if (gfp->genMethod == kGenRoomNumSteam || gfp->genMethod == kGenDiskNumSteam)
-			continue;
-
-		//  ____            _     ____
-		// |  _ \ __ _ _ __| |_  |___ \ *
-		// | |_) / _` | '__| __|   __) |
-		// |  __/ (_| | |  | |_   / __/
-		// |_|   \__,_|_|   \__| |_____|
-		//
-		// PART 2: Fuzzy matching for files with unknown MD5.
-		//
-		//
-		// We loop over the game variants matching the gameid associated to
-		// the gfp record. We then try to decide for each whether it could be
-		// appropriate or not.
-		dr.md5 = d.md5;
-		for (const GameSettings *g = gameVariantsTable; g->gameid; ++g) {
-			// Skip over entries with a different gameid.
-			if (g->gameid[0] == 0 || scumm_stricmp(gfp->gameid, g->gameid))
-				continue;
-
-			dr.game = *g;
-			dr.extra = g->variant; // FIXME: We (ab)use 'variant' for the 'extra' description for now.
-
-			if (gfp->platform != Common::kPlatformUnknown)
-				dr.game.platform = gfp->platform;
-
-
-			// If a variant has been specified, use that!
-			if (gfp->variant) {
-				if (!scumm_stricmp(gfp->variant, g->variant)) {
-					// Perfect match found.
-					results.push_back(dr);
-					break;
-				}
-				continue;
-			}
-
-			// HACK: Perhaps it is some modified translation?
-			dr.language = detectLanguage(fslist, g->id);
-
-			// Detect if there are speech files in this unknown game.
-			if (detectSpeech(fslist, g)) {
-				if (strchr(dr.game.guioptions, GUIO_NOSPEECH[0]) != NULL) {
-					if (g->id == GID_MONKEY || g->id == GID_MONKEY2)
-						// TODO: This may need to be updated if something important gets added
-						// in the top detection table for these game ids.
-						dr.game.guioptions = GUIO0();
-					else
-						warning("FIXME: fix NOSPEECH fallback");
-				}
-			}
-
-			// Add the game/variant to the candidates list if it is consistent
-			// with the file(s) we are seeing.
-			if (testGame(g, fileMD5Map, file))
-				results.push_back(dr);
-		}
-	}
-}
-
-bool testGame(const GameSettings *g, const DescMap &fileMD5Map, const Common::String &file) {
-	const DetectorDesc &d = fileMD5Map[file];
-
-	// At this point, we know that the gameid matches, but no variant
-	// was specified, yet there are multiple ones. So we try our best
-	// to distinguish between the variants.
-	// To do this, we take a close look at the detection file and
-	// try to filter out some cases.
-
-	Common::File tmp;
-	if (!tmp.open(d.node)) {
-		warning("SCUMM testGame: failed to open '%s' for read access", d.node.getPath().c_str());
-		return false;
-	}
-
-	if (file == "maniac1.d64" || file == "maniac1.dsk" || file == "zak1.d64") {
-		// TODO
-	} else if (file == "00.LFL") {
-		// Used in V1, V2, V3 games.
-		if (g->version > 3)
-			return false;
-
-		// Read a few bytes to narrow down the game.
-		byte buf[6];
-		tmp.read(buf, 6);
-
-		if (buf[0] == 0xbc && buf[1] == 0xb9) {
-			// The NES version of MM.
-			if (g->id == GID_MANIAC && g->platform == Common::kPlatformNES) {
-				// Perfect match.
-				return true;
-			}
-		} else if ((buf[0] == 0xCE && buf[1] == 0xF5) || // PC
-			(buf[0] == 0xCD && buf[1] == 0xFE)) {    // Commodore 64
-			// Could be V0 or V1.
-			// Candidates: maniac classic, zak classic.
-
-			if (g->version >= 2)
-				return false;
-
-			// Zak has 58.LFL, Maniac doesn't.
-			const bool has58LFL = fileMD5Map.contains("58.LFL");
-			if (g->id == GID_MANIAC && !has58LFL) {
-			} else if (g->id == GID_ZAK && has58LFL) {
-			} else
-				return false;
-		} else if (buf[0] == 0xFF && buf[1] == 0xFE) {
-			// GF_OLD_BUNDLE: could be V2 or old V3.
-			// Note that GF_OLD_BUNDLE is true if and only if GF_OLD256 is false.
-			// Candidates: maniac enhanced, zak enhanced, indy3ega, loom.
-
-			if ((g->version != 2 && g->version != 3)  || (g->features & GF_OLD256))
-				return false;
-
-			/* We distinguish the games by the presence/absence of
-			   certain files. In the following, '+' means the file
-			   present, '-' means the file is absent.
-
-			   maniac:    -58.LFL, -84.LFL,-86.LFL, -98.LFL
-
-			   zak:       +58.LFL, -84.LFL,-86.LFL, -98.LFL
-			   zakdemo:   +58.LFL, -84.LFL,-86.LFL, -98.LFL
-
-			   loom:      +58.LFL, -84.LFL,+86.LFL, -98.LFL
-			   loomdemo:  -58.LFL, +84.LFL,-86.LFL, -98.LFL
-
-			   indy3:     +58.LFL, +84.LFL,+86.LFL, +98.LFL
-			   indy3demo: -58.LFL, +84.LFL,-86.LFL, +98.LFL
-			*/
-			const bool has58LFL = fileMD5Map.contains("58.LFL");
-			const bool has84LFL = fileMD5Map.contains("84.LFL");
-			const bool has86LFL = fileMD5Map.contains("86.LFL");
-			const bool has98LFL = fileMD5Map.contains("98.LFL");
-
-			if (g->id == GID_INDY3         && has98LFL && has84LFL) {
-			} else if (g->id == GID_ZAK    && !has98LFL && !has86LFL && !has84LFL && has58LFL) {
-			} else if (g->id == GID_MANIAC && !has98LFL && !has86LFL && !has84LFL && !has58LFL) {
-			} else if (g->id == GID_LOOM   && !has98LFL && (has86LFL != has84LFL)) {
-			} else
-				return false;
-		} else if (buf[4] == '0' && buf[5] == 'R') {
-			// Newer V3 game.
-			// Candidates: indy3, indy3Towns, zakTowns, loomTowns.
-
-			if (g->version != 3 || !(g->features & GF_OLD256))
-				return false;
-
-			/*
-			Considering that we know about *all* TOWNS versions, and
-			know their MD5s, we could simply rely on this and if we find
-			something which has an unknown MD5, assume that it is an (so
-			far unknown) version of Indy3. However, there are also fan
-			translations of the TOWNS versions, so we can't do that.
-
-			But we could at least look at the resource headers to distinguish
-			TOWNS versions from regular games:
-
-			Indy3:
-			_numGlobalObjects 1000
-			_numRooms 99
-			_numCostumes 129
-			_numScripts 139
-			_numSounds 84
-
-			Indy3Towns, ZakTowns, ZakLoom demo:
-			_numGlobalObjects 1000
-			_numRooms 99
-			_numCostumes 199
-			_numScripts 199
-			_numSounds 199
-
-			Assuming that all the town variants look like the latter, we can
-			do the check like this:
-			  if (numScripts == 139)
-				assume Indy3
-			  else if (numScripts == 199)
-				assume towns game
-			  else
-				unknown, do not accept it
-			*/
-
-			// We now try to exclude various possibilities by the presence of certain
-			// LFL files. Note that we only exclude something based on the *presence*
-			// of a LFL file here; compared to checking for the absence of files, this
-			// has the advantage that we are less likely to accidentally exclude demos
-			// (which, after all, are usually missing many LFL files present in the
-			// full version of the game).
-
-			// No version of Indy3 has 05.LFL but MM, Loom and Zak all have it.
-			if (g->id == GID_INDY3 && fileMD5Map.contains("05.LFL"))
-				return false;
-
-			// All versions of Indy3 have 93.LFL, but no other game does.
-			if (g->id != GID_INDY3 && fileMD5Map.contains("93.LFL"))
-				return false;
-
-			// No version of Loom has 48.LFL.
-			if (g->id == GID_LOOM && fileMD5Map.contains("48.LFL"))
-				return false;
-
-			// No version of Zak has 60.LFL, but most (non-demo) versions of Indy3 have it.
-			if (g->id == GID_ZAK && fileMD5Map.contains("60.LFL"))
-				return false;
-
-			// All versions of Indy3 and ZakTOWNS have 98.LFL, but no other game does.
-			if (g->id == GID_LOOM && g->platform != Common::kPlatformPCEngine && fileMD5Map.contains("98.LFL"))
-				return false;
-
-
-		} else {
-			// TODO: Unknown file header, deal with it. Maybe an unencrypted
-			// variant...
-			// Anyway, we don't know how to deal with the file, so we
-			// just skip it.
-		}
-	} else if (file == "000.LFL") {
-		// Used in V4.
-		// Candidates: monkeyEGA, pass, monkeyVGA, loomcd.
-
-		if (g->version != 4)
-			return false;
-
-		/*
-		For all of them, we have:
-		_numGlobalObjects 1000
-		_numRooms 99
-		_numCostumes 199
-		_numScripts 199
-		_numSounds 199
-
-		Any good ideas to distinguish those? Maybe by the presence/absence
-		of some files?
-		At least PASS and the monkeyEGA demo differ by 903.LFL missing.
-		And the count of DISK??.LEC files differ depending on what version
-		you have (4 or 8 floppy versions).
-		loomcd of course shipped on only one "disc".
-
-		pass: 000.LFL, 901.LFL, 902.LFL, 904.LFL, disk01.lec
-		monkeyEGA:  000.LFL, 901-904.LFL, DISK01-09.LEC
-		monkeyEGA DEMO: 000.LFL, 901.LFL, 902.LFL, 904.LFL, disk01.lec
-		monkeyVGA: 000.LFL, 901-904.LFL, DISK01-04.LEC
-		loomcd: 000.LFL, 901-904.LFL, DISK01.LEC
-		*/
-
-		const bool has903LFL = fileMD5Map.contains("903.LFL");
-		const bool hasDisk02 = fileMD5Map.contains("DISK02.LEC");
-
-		// There is not much we can do based on the presence/absence
-		// of files. Only that if 903.LFL is present, it can't be PASS;
-		// and if DISK02.LEC is present, it can't be LoomCD.
-		if (g->id == GID_PASS              && !has903LFL && !hasDisk02) {
-		} else if (g->id == GID_LOOM       &&  has903LFL && !hasDisk02) {
-		} else if (g->id == GID_MONKEY_VGA) {
-		} else if (g->id == GID_MONKEY_EGA) {
-		} else
-			return false;
-	} else {
-		// Must be a V5+ game.
-		if (g->version < 5)
-			return false;
-
-		// At this point the gameid is determined, but not necessarily
-		// the variant!
-
-		// TODO: Add code that handles this, at least for the non-HE games.
-		// Not sure how realistic it is to correctly detect HE game
-		// variants, would require me to look at a sufficiently large
-		// sample collection of HE games (assuming I had the time :).
-
-		// TODO: For Mac versions in container file, we can sometimes
-		// distinguish the demo from the regular version by looking
-		// at the content of the container file and then looking for
-		// the *.000 file in there.
-	}
-
-	return true;
-}
 
+// Various methods to help in core detection.
+#include "scumm/detection_internal.h"
 
-} // End of namespace Scumm
 
 #pragma mark -
 #pragma mark --- Plugin code ---
diff --git a/engines/scumm/detection_internal.h b/engines/scumm/detection_internal.h
new file mode 100644
index 0000000000..8e6c1116c3
--- /dev/null
+++ b/engines/scumm/detection_internal.h
@@ -0,0 +1,771 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef SCUMM_DETECTION_INTERNAL_H
+#define SCUMM_DETECTION_INTERNAL_H
+
+// Includes some shared functionalities, which is required by multiple TU's.
+// Mark it as static in the header, so visibility for function is limited by the TU, and we can use it whereever required.
+// This is being done, because it's necessary in detection, creating an instance, as well as in initiliasing the ScummEngine.
+#include "scumm/detection_steam.h"
+
+namespace Scumm {
+
+enum {
+	// We only compute the MD5 of the first megabyte of our data files.
+	kMD5FileSizeLimit = 1024 * 1024
+};
+
+static int compareMD5Table(const void *a, const void *b) {
+	const char *key = (const char *)a;
+	const MD5Table *elem = (const MD5Table *)b;
+	return strcmp(key, elem->md5);
+}
+
+static const MD5Table *findInMD5Table(const char *md5) {
+	uint32 arraySize = ARRAYSIZE(md5table) - 1;
+	return (const MD5Table *)bsearch(md5, md5table, arraySize, sizeof(MD5Table), compareMD5Table);
+}
+
+
+static Common::String generateFilenameForDetection(const char *pattern, FilenameGenMethod genMethod, Common::Platform platform) {
+	Common::String result;
+
+	switch (genMethod) {
+	case kGenDiskNum:
+	case kGenRoomNum:
+		result = Common::String::format(pattern, 0);
+		break;
+
+	case kGenDiskNumSteam:
+	case kGenRoomNumSteam: {
+		const SteamIndexFile *indexFile = lookUpSteamIndexFile(pattern, platform);
+		if (!indexFile) {
+			error("Unable to find Steam executable from detection pattern");
+		} else {
+			result = indexFile->executableName;
+		}
+		} break;
+
+	case kGenHEPC:
+	case kGenHEIOS:
+		result = Common::String::format("%s.he0", pattern);
+		break;
+
+	case kGenHEMac:
+		result = Common::String::format("%s (0)", pattern);
+		break;
+
+	case kGenHEMacNoParens:
+		result = Common::String::format("%s 0", pattern);
+		break;
+
+	case kGenUnchanged:
+		result = pattern;
+		break;
+
+	default:
+		error("generateFilenameForDetection: Unsupported genMethod");
+	}
+
+	return result;
+}
+
+struct DetectorDesc {
+	Common::FSNode node;
+	Common::String md5;
+	const MD5Table *md5Entry;	// Entry of the md5 table corresponding to this file, if any.
+};
+
+typedef Common::HashMap<Common::String, DetectorDesc, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> DescMap;
+
+static bool testGame(const GameSettings *g, const DescMap &fileMD5Map, const Common::String &file);
+
+
+// Search for a node with the given "name", inside fslist. Ignores case
+// when performing the matching. The first match is returned, so if you
+// search for "resource" and two nodes "RESOURE and "resource" are present,
+// the first match is used.
+static bool searchFSNode(const Common::FSList &fslist, const Common::String &name, Common::FSNode &result) {
+	for (Common::FSList::const_iterator file = fslist.begin(); file != fslist.end(); ++file) {
+		if (!scumm_stricmp(file->getName().c_str(), name.c_str())) {
+			result = *file;
+			return true;
+		}
+	}
+	return false;
+}
+
+static BaseScummFile *openDiskImage(const Common::FSNode &node, const GameFilenamePattern *gfp) {
+	Common::String disk1 = node.getName();
+	BaseScummFile *diskImg;
+
+	SearchMan.addDirectory("tmpDiskImgDir", node.getParent());
+
+	if (disk1.hasSuffix(".prg")) { // NES
+		diskImg = new ScummNESFile();
+	} else { // C64 or Apple //gs
+		// setup necessary game settings for disk image reader
+		GameSettings gs;
+		memset(&gs, 0, sizeof(GameSettings));
+		gs.gameid = gfp->gameid;
+		gs.id = (Common::String(gfp->gameid) == "maniac" ? GID_MANIAC : GID_ZAK);
+		gs.platform = gfp->platform;
+		if (strcmp(gfp->pattern, "maniacdemo.d64") == 0)
+			gs.features |= GF_DEMO;
+
+		// Determine second disk file name.
+		Common::String disk2(disk1);
+		for (Common::String::iterator it = disk2.begin(); it != disk2.end(); ++it) {
+			// replace "xyz1.(d64|dsk)" by "xyz2.(d64|dsk)"
+			if (*it == '1') {
+				*it = '2';
+				break;
+			}
+		}
+
+		// Open image.
+		diskImg = new ScummDiskImage(disk1.c_str(), disk2.c_str(), gs);
+	}
+
+	if (diskImg->open(disk1.c_str()) && diskImg->openSubFile("00.LFL")) {
+		debug(0, "Success");
+		return diskImg;
+	}
+	delete diskImg;
+	return 0;
+}
+
+static void closeDiskImage(ScummDiskImage *img) {
+	if (img)
+		img->close();
+	SearchMan.remove("tmpDiskImgDir");
+}
+
+/*
+ * This function tries to detect if a speech file exists.
+ * False doesn't necessarily mean there are no speech files.
+ */
+static bool detectSpeech(const Common::FSList &fslist, const GameSettings *gs) {
+	if (gs->id == GID_MONKEY || gs->id == GID_MONKEY2) {
+		// FM-TOWNS monkey and monkey2 games don't have speech but may have .sou files.
+		if (gs->platform == Common::kPlatformFMTowns)
+			return false;
+
+		const char *const basenames[] = { gs->gameid, "monster", 0 };
+		static const char *const extensions[] = { "sou",
+#ifdef USE_FLAC
+		 "sof",
+#endif
+#ifdef USE_VORBIS
+		 "sog",
+#endif
+#ifdef USE_MAD
+		 "so3",
+#endif
+		 0 };
+
+		for (Common::FSList::const_iterator file = fslist.begin(); file != fslist.end(); ++file) {
+			if (file->isDirectory())
+				continue;
+
+			for (int i = 0; basenames[i]; ++i) {
+				Common::String basename = Common::String(basenames[i]) + ".";
+
+				for (int j = 0; extensions[j]; ++j) {
+					if ((basename + extensions[j]).equalsIgnoreCase(file->getName()))
+						return true;
+				}
+			}
+		}
+	}
+	return false;
+}
+
+// The following function tries to detect the language for COMI and DIG.
+static Common::Language detectLanguage(const Common::FSList &fslist, byte id) {
+	// First try to detect Chinese translation.
+	Common::FSNode fontFile;
+
+	if (searchFSNode(fslist, "chinese_gb16x12.fnt", fontFile)) {
+		debug(0, "Chinese detected");
+		return Common::ZH_CNA;
+	}
+
+	// Now try to detect COMI and Dig by language files.
+	if (id != GID_CMI && id != GID_DIG)
+		return Common::UNK_LANG;
+
+	// Check for LANGUAGE.BND (Dig) resp. LANGUAGE.TAB (CMI).
+	// These are usually inside the "RESOURCE" subdirectory.
+	// If found, we match based on the file size (should we
+	// ever determine that this is insufficient, we can still
+	// switch to MD5 based detection).
+	const char *filename = (id == GID_CMI) ? "LANGUAGE.TAB" : "LANGUAGE.BND";
+	Common::File tmp;
+	Common::FSNode langFile;
+	if (searchFSNode(fslist, filename, langFile))
+		tmp.open(langFile);
+	if (!tmp.isOpen()) {
+		// Try loading in RESOURCE sub dir.
+		Common::FSNode resDir;
+		Common::FSList tmpList;
+		if (searchFSNode(fslist, "RESOURCE", resDir)
+			&& resDir.isDirectory()
+			&& resDir.getChildren(tmpList, Common::FSNode::kListFilesOnly)
+			&& searchFSNode(tmpList, filename, langFile)) {
+			tmp.open(langFile);
+		}
+		// The Steam version of Dig has the LANGUAGE.BND in the DIG sub dir.
+		if (!tmp.isOpen()
+			&& id == GID_DIG
+			&& searchFSNode(fslist, "DIG", resDir)
+			&& resDir.isDirectory()
+			&& resDir.getChildren(tmpList, Common::FSNode::kListFilesOnly)
+			&& searchFSNode(tmpList, filename, langFile)) {
+			tmp.open(langFile);
+		}
+		// The Chinese version of Dig has the LANGUAGE.BND in the VIDEO sub dir.
+		if (!tmp.isOpen()
+			&& id == GID_DIG
+			&& searchFSNode(fslist, "VIDEO", resDir)
+			&& resDir.isDirectory()
+			&& resDir.getChildren(tmpList, Common::FSNode::kListFilesOnly)
+			&& searchFSNode(tmpList, filename, langFile)) {
+			tmp.open(langFile);
+		}
+	}
+	if (tmp.isOpen()) {
+		uint size = tmp.size();
+		if (id == GID_CMI) {
+			switch (size) {
+			case 439080:	// 2daf3db71d23d99d19fc9a544fcf6431
+				return Common::EN_ANY;
+			case 322602:	// caba99f4f5a0b69963e5a4d69e6f90af
+				return Common::ZH_TWN;
+			case 493252:	// 5d59594b24f3f1332e7d7e17455ed533
+				return Common::DE_DEU;
+			case 461746:	// 35bbe0e4d573b318b7b2092c331fd1fa
+				return Common::FR_FRA;
+			case 443439:	// 4689d013f67aabd7c35f4fd7c4b4ad69
+				return Common::IT_ITA;
+			case 398613:	// d1f5750d142d34c4c8f1f330a1278709
+				return Common::KO_KOR;
+			case 440586:	// 5a1d0f4fa00917bdbfe035a72a6bba9d
+				return Common::PT_BRA;
+			case 454457:	// 0e5f450ec474a30254c0e36291fb4ebd
+			case 394083:	// ad684ca14c2b4bf4c21a81c1dbed49bc
+				return Common::RU_RUS;
+			case 449787:	// 64f3fe479d45b52902cf88145c41d172
+				return Common::ES_ESP;
+			default:
+				break;
+			}
+		} else { // The DIG
+			switch (size) {
+			case 248627:	// 1fd585ac849d57305878c77b2f6c74ff
+				return Common::DE_DEU;
+			case 257460:	// 04cf6a6ba6f57e517bc40eb81862cfb0
+				return Common::FR_FRA;
+			case 231402:	// 93d13fcede954c78e65435592182a4db
+				return Common::IT_ITA;
+			case 228772:	// 5d9ad90d3a88ea012d25d61791895ebe
+				return Common::PT_BRA;
+			case 229884:	// d890074bc15c6135868403e73c5f4f36
+				return Common::ES_ESP;
+			case 223107:	// 64f3fe479d45b52902cf88145c41d172
+				return Common::JA_JPN;
+			case 180730:	// 424fdd60822722cdc75356d921dad9bf
+				return Common::ZH_TWN;
+			default:
+				break;
+			}
+		}
+	}
+
+	return Common::UNK_LANG;
+}
+
+
+static void computeGameSettingsFromMD5(const Common::FSList &fslist, const GameFilenamePattern *gfp, const MD5Table *md5Entry, DetectorResult &dr) {
+	dr.language = md5Entry->language;
+	dr.extra = md5Entry->extra;
+
+	// Compute the precise game settings using gameVariantsTable.
+	for (const GameSettings *g = gameVariantsTable; g->gameid; ++g) {
+		if (g->gameid[0] == 0 || !scumm_stricmp(md5Entry->gameid, g->gameid)) {
+			// The gameid either matches, or is empty. The latter indicates
+			// a generic entry, currently used for some generic HE settings.
+			if (g->variant == 0 || !scumm_stricmp(md5Entry->variant, g->variant)) {
+				// Perfect match found, use it and stop the loop.
+				dr.game = *g;
+				dr.game.gameid = md5Entry->gameid;
+
+				// Set the platform value. The value from the MD5 record has
+				// highest priority; if missing (i.e. set to unknown) we try
+				// to use that from the filename pattern record instead.
+				if (md5Entry->platform != Common::kPlatformUnknown) {
+					dr.game.platform = md5Entry->platform;
+				} else if (gfp->platform != Common::kPlatformUnknown) {
+					dr.game.platform = gfp->platform;
+				}
+
+				// HACK: Special case to distinguish the V1 demo from the full version
+				// (since they have identical MD5).
+				if (dr.game.id == GID_MANIAC && !strcmp(gfp->pattern, "%02d.MAN")) {
+					dr.extra = "V1 Demo";
+					dr.game.features = GF_DEMO;
+				}
+
+				// HACK: Try to detect languages for translated games.
+				if (dr.language == UNK_LANG) {
+					dr.language = detectLanguage(fslist, dr.game.id);
+				}
+
+				// HACK: Detect between 68k and PPC versions.
+				if (dr.game.platform == Common::kPlatformMacintosh && dr.game.version >= 5 && dr.game.heversion == 0 && strstr(gfp->pattern, "Data"))
+					dr.game.features |= GF_MAC_CONTAINER;
+
+				break;
+			}
+		}
+	}
+}
+
+static void composeFileHashMap(DescMap &fileMD5Map, const Common::FSList &fslist, int depth, const char *const *globs) {
+	if (depth <= 0)
+		return;
+
+	if (fslist.empty())
+		return;
+
+	for (Common::FSList::const_iterator file = fslist.begin(); file != fslist.end(); ++file) {
+		if (!file->isDirectory()) {
+			DetectorDesc d;
+			d.node = *file;
+			d.md5Entry = 0;
+			fileMD5Map[file->getName()] = d;
+		} else {
+			if (!globs)
+				continue;
+
+			bool matched = false;
+			for (const char *const *glob = globs; *glob; glob++)
+				if (file->getName().matchString(*glob, true)) {
+					matched = true;
+					break;
+				}
+
+			if (!matched)
+				continue;
+
+			Common::FSList files;
+			if (file->getChildren(files, Common::FSNode::kListAll)) {
+				composeFileHashMap(fileMD5Map, files, depth - 1, globs);
+			}
+		}
+	}
+}
+
+static void detectGames(const Common::FSList &fslist, Common::List<DetectorResult> &results, const char *gameid) {
+	DescMap fileMD5Map;
+	DetectorResult dr;
+
+	// Dive one level down since mac indy3/loom have their files split into directories. See Bug #1438631.
+	// Dive two levels down for Mac Steam games.
+	composeFileHashMap(fileMD5Map, fslist, 3, directoryGlobs);
+
+	// Iterate over all filename patterns.
+	for (const GameFilenamePattern *gfp = gameFilenamesTable; gfp->gameid; ++gfp) {
+		// If a gameid was specified, we only try to detect that specific game,
+		// so we can just skip over everything with a differing gameid.
+		if (gameid && scumm_stricmp(gameid, gfp->gameid))
+			continue;
+
+		// Generate the detectname corresponding to the gfp. If the file doesn't
+		// exist in the directory we are looking at, we can skip to the next
+		// one immediately.
+		Common::String file(generateFilenameForDetection(gfp->pattern, gfp->genMethod, gfp->platform));
+		if (!fileMD5Map.contains(file))
+			continue;
+
+		// Reset the DetectorResult variable.
+		dr.fp.pattern = gfp->pattern;
+		dr.fp.genMethod = gfp->genMethod;
+		dr.game.gameid = 0;
+		dr.language = gfp->language;
+		dr.md5.clear();
+		dr.extra = 0;
+
+		//  ____            _     _
+		// |  _ \ __ _ _ __| |_  / |
+		// | |_) / _` | '__| __| | |
+		// |  __/ (_| | |  | |_  | |
+		// |_|   \__,_|_|   \__| |_|
+		//
+		// PART 1: Trying to find an exact match using MD5.
+		//
+		//
+		// Background: We found a valid detection file. Check if its MD5
+		// checksum occurs in our MD5 table. If it does, try to use that
+		// to find an exact match.
+		//
+		// We only do that if the MD5 hadn't already been computed (since
+		// we may look at some detection files multiple times).
+		DetectorDesc &d = fileMD5Map[file];
+		if (d.md5.empty()) {
+			Common::SeekableReadStream *tmp = 0;
+			bool isDiskImg = (file.hasSuffix(".d64") || file.hasSuffix(".dsk") || file.hasSuffix(".prg"));
+
+			if (isDiskImg) {
+				tmp = openDiskImage(d.node, gfp);
+
+				debug(2, "Falling back to disk-based detection");
+			} else {
+				tmp = d.node.createReadStream();
+			}
+
+			Common::String md5str;
+			if (tmp)
+				md5str = computeStreamMD5AsString(*tmp, kMD5FileSizeLimit);
+			if (!md5str.empty()) {
+
+				d.md5 = md5str;
+				d.md5Entry = findInMD5Table(md5str.c_str());
+
+				dr.md5 = d.md5;
+
+				if (d.md5Entry) {
+					// Exact match found. Compute the precise game settings.
+					computeGameSettingsFromMD5(fslist, gfp, d.md5Entry, dr);
+
+					// Print some debug info.
+					int filesize = tmp->size();
+					debug(1, "SCUMM detector found matching file '%s' with MD5 %s, size %d\n",
+						file.c_str(), md5str.c_str(), filesize);
+
+					// Sanity check: We *should* have found a matching gameid/variant at this point.
+					// If not, we may have #ifdef'ed the entry out in our detection_tables.h, because we
+					// don't have the required stuff compiled in, or there's a bug in our data tables.
+					if (dr.game.gameid != 0)
+						// Add it to the list of detected games.
+						results.push_back(dr);
+				}
+			}
+
+			if (isDiskImg)
+				closeDiskImage((ScummDiskImage *)tmp);
+			delete tmp;
+		}
+
+		// If an exact match for this file has already been found, don't bother
+		// looking at it anymore.
+		if (d.md5Entry)
+			continue;
+
+		// Prevent executables being detected as Steam variant. If we don't
+		// know the md5, then it's just the regular executable. Otherwise we
+		// will most likely fail on trying to read the index from the executable.
+		// Fixes bug #10290.
+		if (gfp->genMethod == kGenRoomNumSteam || gfp->genMethod == kGenDiskNumSteam)
+			continue;
+
+		//  ____            _     ____
+		// |  _ \ __ _ _ __| |_  |___ \ *
+		// | |_) / _` | '__| __|   __) |
+		// |  __/ (_| | |  | |_   / __/
+		// |_|   \__,_|_|   \__| |_____|
+		//
+		// PART 2: Fuzzy matching for files with unknown MD5.
+		//
+		//
+		// We loop over the game variants matching the gameid associated to
+		// the gfp record. We then try to decide for each whether it could be
+		// appropriate or not.
+		dr.md5 = d.md5;
+		for (const GameSettings *g = gameVariantsTable; g->gameid; ++g) {
+			// Skip over entries with a different gameid.
+			if (g->gameid[0] == 0 || scumm_stricmp(gfp->gameid, g->gameid))
+				continue;
+
+			dr.game = *g;
+			dr.extra = g->variant; // FIXME: We (ab)use 'variant' for the 'extra' description for now.
+
+			if (gfp->platform != Common::kPlatformUnknown)
+				dr.game.platform = gfp->platform;
+
+
+			// If a variant has been specified, use that!
+			if (gfp->variant) {
+				if (!scumm_stricmp(gfp->variant, g->variant)) {
+					// Perfect match found.
+					results.push_back(dr);
+					break;
+				}
+				continue;
+			}
+
+			// HACK: Perhaps it is some modified translation?
+			dr.language = detectLanguage(fslist, g->id);
+
+			// Detect if there are speech files in this unknown game.
+			if (detectSpeech(fslist, g)) {
+				if (strchr(dr.game.guioptions, GUIO_NOSPEECH[0]) != NULL) {
+					if (g->id == GID_MONKEY || g->id == GID_MONKEY2)
+						// TODO: This may need to be updated if something important gets added
+						// in the top detection table for these game ids.
+						dr.game.guioptions = GUIO0();
+					else
+						warning("FIXME: fix NOSPEECH fallback");
+				}
+			}
+
+			// Add the game/variant to the candidates list if it is consistent
+			// with the file(s) we are seeing.
+			if (testGame(g, fileMD5Map, file))
+				results.push_back(dr);
+		}
+	}
+}
+
+static bool testGame(const GameSettings *g, const DescMap &fileMD5Map, const Common::String &file) {
+	const DetectorDesc &d = fileMD5Map[file];
+
+	// At this point, we know that the gameid matches, but no variant
+	// was specified, yet there are multiple ones. So we try our best
+	// to distinguish between the variants.
+	// To do this, we take a close look at the detection file and
+	// try to filter out some cases.
+
+	Common::File tmp;
+	if (!tmp.open(d.node)) {
+		warning("SCUMM testGame: failed to open '%s' for read access", d.node.getPath().c_str());
+		return false;
+	}
+
+	if (file == "maniac1.d64" || file == "maniac1.dsk" || file == "zak1.d64") {
+		// TODO
+	} else if (file == "00.LFL") {
+		// Used in V1, V2, V3 games.
+		if (g->version > 3)
+			return false;
+
+		// Read a few bytes to narrow down the game.
+		byte buf[6];
+		tmp.read(buf, 6);
+
+		if (buf[0] == 0xbc && buf[1] == 0xb9) {
+			// The NES version of MM.
+			if (g->id == GID_MANIAC && g->platform == Common::kPlatformNES) {
+				// Perfect match.
+				return true;
+			}
+		} else if ((buf[0] == 0xCE && buf[1] == 0xF5) || // PC
+			(buf[0] == 0xCD && buf[1] == 0xFE)) {    // Commodore 64
+			// Could be V0 or V1.
+			// Candidates: maniac classic, zak classic.
+
+			if (g->version >= 2)
+				return false;
+
+			// Zak has 58.LFL, Maniac doesn't.
+			const bool has58LFL = fileMD5Map.contains("58.LFL");
+			if (g->id == GID_MANIAC && !has58LFL) {
+			} else if (g->id == GID_ZAK && has58LFL) {
+			} else
+				return false;
+		} else if (buf[0] == 0xFF && buf[1] == 0xFE) {
+			// GF_OLD_BUNDLE: could be V2 or old V3.
+			// Note that GF_OLD_BUNDLE is true if and only if GF_OLD256 is false.
+			// Candidates: maniac enhanced, zak enhanced, indy3ega, loom.
+
+			if ((g->version != 2 && g->version != 3)  || (g->features & GF_OLD256))
+				return false;
+
+			/* We distinguish the games by the presence/absence of
+			   certain files. In the following, '+' means the file
+			   present, '-' means the file is absent.
+
+			   maniac:    -58.LFL, -84.LFL,-86.LFL, -98.LFL
+
+			   zak:       +58.LFL, -84.LFL,-86.LFL, -98.LFL
+			   zakdemo:   +58.LFL, -84.LFL,-86.LFL, -98.LFL
+
+			   loom:      +58.LFL, -84.LFL,+86.LFL, -98.LFL
+			   loomdemo:  -58.LFL, +84.LFL,-86.LFL, -98.LFL
+
+			   indy3:     +58.LFL, +84.LFL,+86.LFL, +98.LFL
+			   indy3demo: -58.LFL, +84.LFL,-86.LFL, +98.LFL
+			*/
+			const bool has58LFL = fileMD5Map.contains("58.LFL");
+			const bool has84LFL = fileMD5Map.contains("84.LFL");
+			const bool has86LFL = fileMD5Map.contains("86.LFL");
+			const bool has98LFL = fileMD5Map.contains("98.LFL");
+
+			if (g->id == GID_INDY3         && has98LFL && has84LFL) {
+			} else if (g->id == GID_ZAK    && !has98LFL && !has86LFL && !has84LFL && has58LFL) {
+			} else if (g->id == GID_MANIAC && !has98LFL && !has86LFL && !has84LFL && !has58LFL) {
+			} else if (g->id == GID_LOOM   && !has98LFL && (has86LFL != has84LFL)) {
+			} else
+				return false;
+		} else if (buf[4] == '0' && buf[5] == 'R') {
+			// Newer V3 game.
+			// Candidates: indy3, indy3Towns, zakTowns, loomTowns.
+
+			if (g->version != 3 || !(g->features & GF_OLD256))
+				return false;
+
+			/*
+			Considering that we know about *all* TOWNS versions, and
+			know their MD5s, we could simply rely on this and if we find
+			something which has an unknown MD5, assume that it is an (so
+			far unknown) version of Indy3. However, there are also fan
+			translations of the TOWNS versions, so we can't do that.
+
+			But we could at least look at the resource headers to distinguish
+			TOWNS versions from regular games:
+
+			Indy3:
+			_numGlobalObjects 1000
+			_numRooms 99
+			_numCostumes 129
+			_numScripts 139
+			_numSounds 84
+
+			Indy3Towns, ZakTowns, ZakLoom demo:
+			_numGlobalObjects 1000
+			_numRooms 99
+			_numCostumes 199
+			_numScripts 199
+			_numSounds 199
+
+			Assuming that all the town variants look like the latter, we can
+			do the check like this:
+			  if (numScripts == 139)
+				assume Indy3
+			  else if (numScripts == 199)
+				assume towns game
+			  else
+				unknown, do not accept it
+			*/
+
+			// We now try to exclude various possibilities by the presence of certain
+			// LFL files. Note that we only exclude something based on the *presence*
+			// of a LFL file here; compared to checking for the absence of files, this
+			// has the advantage that we are less likely to accidentally exclude demos
+			// (which, after all, are usually missing many LFL files present in the
+			// full version of the game).
+
+			// No version of Indy3 has 05.LFL but MM, Loom and Zak all have it.
+			if (g->id == GID_INDY3 && fileMD5Map.contains("05.LFL"))
+				return false;
+
+			// All versions of Indy3 have 93.LFL, but no other game does.
+			if (g->id != GID_INDY3 && fileMD5Map.contains("93.LFL"))
+				return false;
+
+			// No version of Loom has 48.LFL.
+			if (g->id == GID_LOOM && fileMD5Map.contains("48.LFL"))
+				return false;
+
+			// No version of Zak has 60.LFL, but most (non-demo) versions of Indy3 have it.
+			if (g->id == GID_ZAK && fileMD5Map.contains("60.LFL"))
+				return false;
+
+			// All versions of Indy3 and ZakTOWNS have 98.LFL, but no other game does.
+			if (g->id == GID_LOOM && g->platform != Common::kPlatformPCEngine && fileMD5Map.contains("98.LFL"))
+				return false;
+
+
+		} else {
+			// TODO: Unknown file header, deal with it. Maybe an unencrypted
+			// variant...
+			// Anyway, we don't know how to deal with the file, so we
+			// just skip it.
+		}
+	} else if (file == "000.LFL") {
+		// Used in V4.
+		// Candidates: monkeyEGA, pass, monkeyVGA, loomcd.
+
+		if (g->version != 4)
+			return false;
+
+		/*
+		For all of them, we have:
+		_numGlobalObjects 1000
+		_numRooms 99
+		_numCostumes 199
+		_numScripts 199
+		_numSounds 199
+
+		Any good ideas to distinguish those? Maybe by the presence/absence
+		of some files?
+		At least PASS and the monkeyEGA demo differ by 903.LFL missing.
+		And the count of DISK??.LEC files differ depending on what version
+		you have (4 or 8 floppy versions).
+		loomcd of course shipped on only one "disc".
+
+		pass: 000.LFL, 901.LFL, 902.LFL, 904.LFL, disk01.lec
+		monkeyEGA:  000.LFL, 901-904.LFL, DISK01-09.LEC
+		monkeyEGA DEMO: 000.LFL, 901.LFL, 902.LFL, 904.LFL, disk01.lec
+		monkeyVGA: 000.LFL, 901-904.LFL, DISK01-04.LEC
+		loomcd: 000.LFL, 901-904.LFL, DISK01.LEC
+		*/
+
+		const bool has903LFL = fileMD5Map.contains("903.LFL");
+		const bool hasDisk02 = fileMD5Map.contains("DISK02.LEC");
+
+		// There is not much we can do based on the presence/absence
+		// of files. Only that if 903.LFL is present, it can't be PASS;
+		// and if DISK02.LEC is present, it can't be LoomCD.
+		if (g->id == GID_PASS              && !has903LFL && !hasDisk02) {
+		} else if (g->id == GID_LOOM       &&  has903LFL && !hasDisk02) {
+		} else if (g->id == GID_MONKEY_VGA) {
+		} else if (g->id == GID_MONKEY_EGA) {
+		} else
+			return false;
+	} else {
+		// Must be a V5+ game.
+		if (g->version < 5)
+			return false;
+
+		// At this point the gameid is determined, but not necessarily
+		// the variant!
+
+		// TODO: Add code that handles this, at least for the non-HE games.
+		// Not sure how realistic it is to correctly detect HE game
+		// variants, would require me to look at a sufficiently large
+		// sample collection of HE games (assuming I had the time :).
+
+		// TODO: For Mac versions in container file, we can sometimes
+		// distinguish the demo from the regular version by looking
+		// at the content of the container file and then looking for
+		// the *.000 file in there.
+	}
+
+	return true;
+}
+
+
+} // End of namespace Scumm
+
+#endif // SCUMM_DETECTION_INTERNAL_H
diff --git a/engines/scumm/detection_steam.h b/engines/scumm/detection_steam.h
new file mode 100644
index 0000000000..20a8696bcd
--- /dev/null
+++ b/engines/scumm/detection_steam.h
@@ -0,0 +1,55 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef SCUMM_DETECTION_STEAM_H
+#define SCUMM_DETECTION_STEAM_H
+
+namespace Scumm {
+
+// The following table includes all the index files, which are embedded in the
+// main game executables in Steam versions.
+static const SteamIndexFile steamIndexFiles[] = {
+	{ GID_INDY3, Common::kPlatformWindows,   "%02d.LFL",      "00.LFL",        "Indiana Jones and the Last Crusade.exe",     162056,  6295 },
+	{ GID_INDY3, Common::kPlatformMacintosh, "%02d.LFL",      "00.LFL",        "The Last Crusade",                           150368,  6295 },
+	{ GID_INDY4, Common::kPlatformWindows,   "atlantis.%03d", "ATLANTIS.000",  "Indiana Jones and the Fate of Atlantis.exe", 224336, 12035 },
+	{ GID_INDY4, Common::kPlatformMacintosh, "atlantis.%03d", "ATLANTIS.000",  "The Fate of Atlantis",                       260224, 12035 },
+	{ GID_LOOM,  Common::kPlatformWindows,   "%03d.LFL",      "000.LFL",       "Loom.exe",                                   187248,  8307 },
+	{ GID_LOOM,  Common::kPlatformMacintosh, "%03d.LFL",      "000.LFL",       "Loom",                                       170464,  8307 },
+#ifdef ENABLE_SCUMM_7_8
+	{ GID_DIG,   Common::kPlatformWindows,   "dig.la%d",      "DIG.LA0",       "The Dig.exe",                                340632, 16304 },
+	{ GID_DIG,   Common::kPlatformMacintosh, "dig.la%d",      "DIG.LA0",       "The Dig",                                    339744, 16304 },
+#endif
+	{ 0,         Common::kPlatformUnknown,   nullptr,         nullptr,         nullptr,                                           0,     0 }
+};
+
+static const SteamIndexFile *lookUpSteamIndexFile(Common::String pattern, Common::Platform platform) {
+	for (const SteamIndexFile *indexFile = steamIndexFiles; indexFile->len; ++indexFile) {
+		if (platform == indexFile->platform && pattern.equalsIgnoreCase(indexFile->pattern))
+			return indexFile;
+	}
+
+	return nullptr;
+}
+
+} // End of namespace Scumm
+
+#endif // SCUMM_DETECTION_STEAM_H
diff --git a/engines/scumm/file.h b/engines/scumm/file.h
index 71fa641ba7..e367190d2d 100644
--- a/engines/scumm/file.h
+++ b/engines/scumm/file.h
@@ -130,8 +130,6 @@ struct SteamIndexFile {
 	int32 len;
 };
 
-const SteamIndexFile *lookUpSteamIndexFile(Common::String pattern, Common::Platform platform);
-
 class ScummSteamFile : public ScummFile {
 private:
 	const SteamIndexFile &_indexFile;
diff --git a/engines/scumm/metaengine.cpp b/engines/scumm/metaengine.cpp
index 7fcc636ed5..18a76618d1 100644
--- a/engines/scumm/metaengine.cpp
+++ b/engines/scumm/metaengine.cpp
@@ -26,6 +26,7 @@
 #include "common/config-manager.h"
 #include "common/translation.h"
 #include "common/gui_options.h"
+#include "common/md5.h"
 
 #include "audio/mididrv.h"
 
@@ -34,8 +35,12 @@
 #include "scumm/scumm_v8.h"
 #include "scumm/resource.h"
 
+// Files related for detection.
 #include "scumm/metaengine.h"
 #include "scumm/detection.h"
+#include "scumm/detection_tables.h"
+#include "scumm/file.h"
+#include "scumm/file_nes.h"
 
 namespace Scumm {
 
@@ -196,21 +201,18 @@ bool ScummEngine::isMacM68kIMuse() const {
 } // End of namespace Scumm
 
 #pragma mark -
-#pragma mark --- Plugin code ---
+#pragma mark --- Detection code ---
 #pragma mark -
 
-namespace Scumm {
 
-void detectGames(const Common::FSList &fslist, Common::List<DetectorResult> &results, const char *gameid);
+// Various methods to help in core detection.
+#include "scumm/detection_internal.h"
 
-struct MD5Table;
-const MD5Table *findInMD5Table(const char *md5);
 
-Common::String generateFilenameForDetection(const char *pattern, FilenameGenMethod genMethod, Common::Platform platform);
+#pragma mark -
+#pragma mark --- Plugin code ---
+#pragma mark -
 
-bool getSavegameName(Common::InSaveFile *in, Common::String &desc, int heversion);
-
-} // End of namespace Scumm
 
 using namespace Scumm;
 
@@ -239,8 +241,6 @@ bool ScummEngine::hasFeature(EngineFeature f) const {
 }
 
 
-#include "scumm/obsolete.h"
-
 /**
  * Create a ScummEngine instance, based on the given detector data.
  *
@@ -442,6 +442,10 @@ Common::Error ScummMetaEngine::createInstance(OSystem *syst, Engine **engine) co
 
 int ScummMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
 
+namespace Scumm {
+bool getSavegameName(Common::InSaveFile *in, Common::String &desc, int heversion);
+} // End of namespace Scumm
+
 SaveStateList ScummMetaEngineConnect::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
diff --git a/engines/scumm/metaengine.h b/engines/scumm/metaengine.h
index a2669276a1..af18d934cc 100644
--- a/engines/scumm/metaengine.h
+++ b/engines/scumm/metaengine.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef SCUMM_METAENGINE_H
+#define SCUMM_METAENGINE_H
+
 #include "engines/metaengine.h"
 
 class ScummMetaEngineConnect : public MetaEngineConnect {
@@ -34,3 +37,5 @@ class ScummMetaEngineConnect : public MetaEngineConnect {
 	void removeSaveState(const char *target, int slot) const override;
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
+
+#endif // SCUMM_METAENGINE_H
diff --git a/engines/scumm/module.mk b/engines/scumm/module.mk
index f7096acc2d..4f8322885c 100644
--- a/engines/scumm/module.mk
+++ b/engines/scumm/module.mk
@@ -13,7 +13,6 @@ MODULE_OBJS := \
 	costume.o \
 	cursor.o \
 	debugger.o \
-	detection.o \
 	dialogs.o \
 	file.o \
 	file_nes.o \
@@ -170,11 +169,14 @@ endif
 # Include common rules
 include $(srcdir)/rules.mk
 
-# Detection objects, if building as a Dynamic Plugin.
-# Scumm uses detection files when creating an instance,
-# so we can't remove dependency completely.
-ifeq ($(ENABLE_SCUMM), DYNAMIC_PLUGIN)
+# Detection objects
 DETECT_OBJS += $(MODULE)/detection.o
+
+# If this module is being built as a dynamic plugin,
+# add the additional dependencies of detection.
+# Otherwise, these are not added because they're already
+# present in the module objects.
+ifeq ($(ENABLE_SCUMM), DYNAMIC_PLUGIN)
 DETECT_OBJS += $(MODULE)/file.o
 DETECT_OBJS += $(MODULE)/file_nes.o
 endif
diff --git a/engines/scumm/obsolete.h b/engines/scumm/obsolete.h
index 7314fc6f12..cddc952479 100644
--- a/engines/scumm/obsolete.h
+++ b/engines/scumm/obsolete.h
@@ -20,6 +20,8 @@
  *
  */
 
+#ifndef SCUMM_OBSOLETE_H
+#define SCUMM_OBSOLETE_H
 
 namespace Scumm {
 
@@ -64,3 +66,5 @@ static const Engines::ObsoleteGameID obsoleteGameIDsTable[] = {
 };
 
 } // End of namespace Scumm
+
+#endif // SCUMM_OBSOLETE_H
diff --git a/engines/scumm/scumm.cpp b/engines/scumm/scumm.cpp
index 356766ce04..6bc433fa51 100644
--- a/engines/scumm/scumm.cpp
+++ b/engines/scumm/scumm.cpp
@@ -80,6 +80,7 @@
 #include "scumm/imuse/drivers/mac_m68k.h"
 #include "scumm/imuse/drivers/amiga.h"
 #include "scumm/imuse/drivers/fmtowns.h"
+#include "scumm/detection_steam.h"
 
 #include "backends/audiocd/audiocd.h"
 


Commit: 6a3b7b67220535f47c05aa82d3e833db9362a95e
    https://github.com/scummvm/scummvm/commit/6a3b7b67220535f47c05aa82d3e833db9362a95e
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SKY: Split detection features & adapt to new plugins.

Changed paths:
  A engines/sky/metaengine.cpp
    configure
    engines/sky/detection.cpp
    engines/sky/module.mk


diff --git a/configure b/configure
index e643c223ee..1bdf0c7f75 100755
--- a/configure
+++ b/configure
@@ -6160,7 +6160,7 @@ EOF
 	fi
 done
 
-declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM")
+declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/sky/detection.cpp b/engines/sky/detection.cpp
index 58d6c099ee..8db7d3f35d 100644
--- a/engines/sky/detection.cpp
+++ b/engines/sky/detection.cpp
@@ -20,21 +20,13 @@
  *
  */
 
-#include "sky/control.h"
-#include "sky/sky.h"
-
 #include "base/plugins.h"
 
-#include "backends/keymapper/action.h"
-#include "backends/keymapper/keymap.h"
-#include "backends/keymapper/standard-actions.h"
 #include "common/config-manager.h"
 #include "engines/advancedDetector.h"
 #include "engines/metaengine.h"
 #include "common/system.h"
 #include "common/file.h"
-#include "common/fs.h"
-#include "common/savefile.h"
 #include "common/textconsole.h"
 #include "common/translation.h"
 
@@ -82,18 +74,10 @@ public:
 		return "sky";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override;
 	PlainGameList getSupportedGames() const override;
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
 	PlainGameDescriptor findGame(const char *gameid) const override;
 	DetectedGames detectGames(const Common::FSList &fslist) const override;
-	Common::KeymapArray initKeymaps(const char *target) const override;
-
-	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
-
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
 const char *SkyMetaEngine::getName() const {
@@ -104,20 +88,6 @@ const char *SkyMetaEngine::getOriginalCopyright() const {
 	return "Beneath a Steel Sky (C) Revolution";
 }
 
-bool SkyMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave);
-}
-
-bool Sky::SkyEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
 PlainGameList SkyMetaEngine::getSupportedGames() const {
 	PlainGameList games;
 	games.push_back(skySetting);
@@ -205,237 +175,4 @@ DetectedGames SkyMetaEngine::detectGames(const Common::FSList &fslist) const {
 	return detectedGames;
 }
 
-Common::KeymapArray SkyMetaEngine::initKeymaps(const char *target) const {
-	using namespace Common;
-	using namespace Sky;
-
-	Keymap *mainKeymap = new Keymap(Keymap::kKeymapTypeGame, "sky-main", "Beneath a Steel Sky");
-
-	Action *act;
-
-	act = new Action("LCLK", _("Walk / Look / Talk"));
-	act->setLeftClickEvent();
-	act->addDefaultInputMapping("MOUSE_LEFT");
-	act->addDefaultInputMapping("JOY_A");
-	mainKeymap->addAction(act);
-
-	act = new Action("RCLK", _("Use"));
-	act->setRightClickEvent();
-	act->addDefaultInputMapping("MOUSE_RIGHT");
-	act->addDefaultInputMapping("JOY_B");
-	mainKeymap->addAction(act);
-
-	act = new Action("CONFIRM", _("Confirm"));
-	act->setCustomEngineActionEvent(kSkyActionConfirm);
-	act->addDefaultInputMapping("RETURN");
-	act->addDefaultInputMapping("KP_ENTER");
-	mainKeymap->addAction(act);
-
-	act = new Action(kStandardActionSkip, _("Skip / Close"));
-	act->setCustomEngineActionEvent(kSkyActionSkip);
-	act->addDefaultInputMapping("ESCAPE");
-	act->addDefaultInputMapping("JOY_Y");
-	mainKeymap->addAction(act);
-
-	Keymap *shortcutsKeymap = new Keymap(Keymap::kKeymapTypeGame, SkyEngine::shortcutsKeymapId, "Beneath a Steel Sky - Shortcuts");
-
-	act = new Action(kStandardActionOpenMainMenu, _("Open control panel"));
-	act->setCustomEngineActionEvent(kSkyActionOpenControlPanel);
-	act->addDefaultInputMapping("F5");
-	act->addDefaultInputMapping("JOY_X");
-	shortcutsKeymap->addAction(act);
-
-	act = new Action("SKPL", _("Skip line"));
-	act->setCustomEngineActionEvent(kSkyActionSkipLine);
-	act->addDefaultInputMapping("PERIOD");
-	shortcutsKeymap->addAction(act);
-
-	act = new Action(kStandardActionPause, _("Pause"));
-	act->setCustomEngineActionEvent(kSkyActionPause);
-	act->addDefaultInputMapping("p");
-	shortcutsKeymap->addAction(act);
-
-	act = new Action("FAST", _("Toggle fast mode"));
-	act->setCustomEngineActionEvent(kSkyActionToggleFastMode);
-	act->addDefaultInputMapping("C+f");
-	shortcutsKeymap->addAction(act);
-
-	act = new Action("RFAST", _("Toggle really fast mode"));
-	act->setCustomEngineActionEvent(kSkyActionToggleReallyFastMode);
-	act->addDefaultInputMapping("C+g");
-	shortcutsKeymap->addAction(act);
-
-	KeymapArray keymaps(2);
-	keymaps[0] = mainKeymap;
-	keymaps[1] = shortcutsKeymap;
-
-	return keymaps;
-}
-
-Common::Error SkyMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
-	assert(engine);
-	*engine = new Sky::SkyEngine(syst);
-	return Common::kNoError;
-}
-
-SaveStateList SkyMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	SaveStateList saveList;
-
-	// Load the descriptions
-	Common::StringArray savenames;
-	savenames.resize(MAX_SAVE_GAMES+1);
-
-	Common::InSaveFile *inf;
-	inf = saveFileMan->openForLoading("SKY-VM.SAV");
-	if (inf != NULL) {
-		char *tmpBuf =  new char[MAX_SAVE_GAMES * MAX_TEXT_LEN];
-		char *tmpPtr = tmpBuf;
-		inf->read(tmpBuf, MAX_SAVE_GAMES * MAX_TEXT_LEN);
-		for (int i = 0; i < MAX_SAVE_GAMES; ++i) {
-			savenames[i] = tmpPtr;
-			tmpPtr += savenames[i].size() + 1;
-		}
-		delete inf;
-		delete[] tmpBuf;
-	}
-
-	// Find all saves
-	Common::StringArray filenames;
-	filenames = saveFileMan->listSavefiles("SKY-VM.###");
-
-	// Prepare the list of savestates by looping over all matching savefiles
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Extract the extension
-		Common::String ext = file->c_str() + file->size() - 3;
-		ext.toUppercase();
-		int slotNum = atoi(ext.c_str());
-		Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-		if (in) {
-			saveList.push_back(SaveStateDescriptor(slotNum,
-				(slotNum == 0) ? _("Autosave") : Common::U32String(savenames[slotNum - 1])));
-			delete in;
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int SkyMetaEngine::getMaximumSaveSlot() const { return MAX_SAVE_GAMES; }
-
-void SkyMetaEngine::removeSaveState(const char *target, int slot) const {
-	if (slot == 0)	// do not delete the auto save
-		return;
-
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	char fName[20];
-	sprintf(fName,"SKY-VM.%03d", slot);
-	saveFileMan->removeSavefile(fName);
-
-	// Load current save game descriptions
-	Common::StringArray savenames;
-	savenames.resize(MAX_SAVE_GAMES+1);
-	Common::InSaveFile *inf;
-	inf = saveFileMan->openForLoading("SKY-VM.SAV");
-	if (inf != NULL) {
-		char *tmpBuf =  new char[MAX_SAVE_GAMES * MAX_TEXT_LEN];
-		char *tmpPtr = tmpBuf;
-		inf->read(tmpBuf, MAX_SAVE_GAMES * MAX_TEXT_LEN);
-		for (int i = 0; i < MAX_SAVE_GAMES; ++i) {
-			savenames[i] = tmpPtr;
-			tmpPtr += savenames[i].size() + 1;
-		}
-		delete inf;
-		delete[] tmpBuf;
-	}
-
-	// Update the save game description at the given slot
-	savenames[slot] = "";
-
-	// Save the updated descriptions
-	Common::OutSaveFile *outf;
-
-	outf = saveFileMan->openForSaving("SKY-VM.SAV");
-	bool ioFailed = true;
-	if (outf) {
-		for (uint16 cnt = 0; cnt < MAX_SAVE_GAMES; cnt++) {
-			outf->write(savenames[cnt].c_str(), savenames[cnt].size() + 1);
-		}
-		outf->finalize();
-		if (!outf->err())
-			ioFailed = false;
-		delete outf;
-	}
-	if (ioFailed)
-		warning("Unable to store Savegame names to file SKY-VM.SAV. (%s)", saveFileMan->popErrorDesc().c_str());
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(SKY)
-	REGISTER_PLUGIN_DYNAMIC(SKY, PLUGIN_TYPE_ENGINE, SkyMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(SKY, PLUGIN_TYPE_ENGINE, SkyMetaEngine);
-#endif
-
-namespace Sky {
-Common::Error SkyEngine::loadGameState(int slot) {
-	// We don't need to offset "slot" here. Both loadGameState and quickXRestore
-	// are called with the ScummVM Save File Manager's "slot" as argument
-	uint16 result = _skyControl->quickXRestore(slot);
-	return (result == GAME_RESTORED) ? Common::kNoError : Common::kUnknownError;
-}
-
-/**
-* Manually saving a game should save it into ScummVM Save File Managers slots 1 or greater.
-* ScummVM Save file manager's slot 0 is reserved for the autosave.
-* However, natively, the index 0 (_selectedGame) is the first manually saved game.
-* @param slot is the save slot on the ScummVM file manager's list
-*
-*/
-Common::Error SkyEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
-	// prevent writing to autosave slot when user selects it manually
-	// ie. from the ScummVM in-game menu Save feature
-	// This also secures _selectedGame which is unsigned integer (uint16)
-	// from overflowing in the subtraction below
-	if (slot < 0 || (!isAutosave && slot == 0)) {
-		return Common::kWritePermissionDenied;
-	}
-	// Set the save slot and save the game
-	// _selectedGame value is one unit lower than the ScummVM's Save File Manager's slot value
-	// Note that *_selectedGame* value 0 corresponds to a manually saved game (the first in order)
-	//   whereas *slot* value 0 corresponds to the autosave
-	if (slot > 0) {
-		// We don't care for updating the _selectedGame when slot == 0
-		// (in the case of autosave) but we do include the check for slot > 0
-		// to guard from overflow, which would be bad practice to allow.
-		_skyControl->_selectedGame = slot - 1;
-	}
-	if (_skyControl->saveGameToFile(false, nullptr, isAutosave) != GAME_SAVED)
-		return Common::kWritePermissionDenied;
-
-	// Load current save game descriptions
-	Common::StringArray saveGameTexts;
-	saveGameTexts.resize(MAX_SAVE_GAMES+1);
-	_skyControl->loadDescriptions(saveGameTexts);
-
-	// Update the save game description at the given slot
-	if (!isAutosave) {
-		saveGameTexts[_skyControl->_selectedGame] = desc;
-	}
-
-	// Save the updated descriptions
-	_skyControl->saveDescriptions(saveGameTexts);
-
-	return Common::kNoError;
-}
-
-bool SkyEngine::canLoadGameStateCurrently() {
-	return _systemVars->pastIntro && _skyControl->loadSaveAllowed();
-}
-
-bool SkyEngine::canSaveGameStateCurrently() {
-	return _systemVars->pastIntro && _skyControl->loadSaveAllowed();
-}
-
-} // End of namespace Sky
+REGISTER_PLUGIN_STATIC(SKY_DETECTION, PLUGIN_TYPE_METAENGINE, SkyMetaEngine);
diff --git a/engines/sky/metaengine.cpp b/engines/sky/metaengine.cpp
new file mode 100644
index 0000000000..f4708e8f30
--- /dev/null
+++ b/engines/sky/metaengine.cpp
@@ -0,0 +1,302 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/metaengine.h"
+
+#include "backends/keymapper/action.h"
+#include "backends/keymapper/keymap.h"
+#include "backends/keymapper/standard-actions.h"
+
+#include "common/system.h"
+#include "common/savefile.h"
+#include "common/translation.h"
+#include "common/file.h"
+#include "common/fs.h"
+
+#include "sky/control.h"
+#include "sky/sky.h"
+
+class SkyMetaEngineConnect : public MetaEngineConnect {
+    const char *getName() const override {
+        return "sky";
+    }
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+    Common::Error createInstance(OSystem *syst, Engine **engine) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+
+    Common::KeymapArray initKeymaps(const char *target) const override;
+};
+
+bool SkyMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave);
+}
+
+bool Sky::SkyEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+Common::KeymapArray SkyMetaEngineConnect::initKeymaps(const char *target) const {
+	using namespace Common;
+	using namespace Sky;
+
+	Keymap *mainKeymap = new Keymap(Keymap::kKeymapTypeGame, "sky-main", "Beneath a Steel Sky");
+
+	Action *act;
+
+	act = new Action("LCLK", _("Walk / Look / Talk"));
+	act->setLeftClickEvent();
+	act->addDefaultInputMapping("MOUSE_LEFT");
+	act->addDefaultInputMapping("JOY_A");
+	mainKeymap->addAction(act);
+
+	act = new Action("RCLK", _("Use"));
+	act->setRightClickEvent();
+	act->addDefaultInputMapping("MOUSE_RIGHT");
+	act->addDefaultInputMapping("JOY_B");
+	mainKeymap->addAction(act);
+
+	act = new Action("CONFIRM", _("Confirm"));
+	act->setCustomEngineActionEvent(kSkyActionConfirm);
+	act->addDefaultInputMapping("RETURN");
+	act->addDefaultInputMapping("KP_ENTER");
+	mainKeymap->addAction(act);
+
+	act = new Action(kStandardActionSkip, _("Skip / Close"));
+	act->setCustomEngineActionEvent(kSkyActionSkip);
+	act->addDefaultInputMapping("ESCAPE");
+	act->addDefaultInputMapping("JOY_Y");
+	mainKeymap->addAction(act);
+
+	Keymap *shortcutsKeymap = new Keymap(Keymap::kKeymapTypeGame, SkyEngine::shortcutsKeymapId, "Beneath a Steel Sky - Shortcuts");
+
+	act = new Action(kStandardActionOpenMainMenu, _("Open control panel"));
+	act->setCustomEngineActionEvent(kSkyActionOpenControlPanel);
+	act->addDefaultInputMapping("F5");
+	act->addDefaultInputMapping("JOY_X");
+	shortcutsKeymap->addAction(act);
+
+	act = new Action("SKPL", _("Skip line"));
+	act->setCustomEngineActionEvent(kSkyActionSkipLine);
+	act->addDefaultInputMapping("PERIOD");
+	shortcutsKeymap->addAction(act);
+
+	act = new Action(kStandardActionPause, _("Pause"));
+	act->setCustomEngineActionEvent(kSkyActionPause);
+	act->addDefaultInputMapping("p");
+	shortcutsKeymap->addAction(act);
+
+	act = new Action("FAST", _("Toggle fast mode"));
+	act->setCustomEngineActionEvent(kSkyActionToggleFastMode);
+	act->addDefaultInputMapping("C+f");
+	shortcutsKeymap->addAction(act);
+
+	act = new Action("RFAST", _("Toggle really fast mode"));
+	act->setCustomEngineActionEvent(kSkyActionToggleReallyFastMode);
+	act->addDefaultInputMapping("C+g");
+	shortcutsKeymap->addAction(act);
+
+	KeymapArray keymaps(2);
+	keymaps[0] = mainKeymap;
+	keymaps[1] = shortcutsKeymap;
+
+	return keymaps;
+}
+
+Common::Error SkyMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+	assert(engine);
+	*engine = new Sky::SkyEngine(syst);
+	return Common::kNoError;
+}
+
+SaveStateList SkyMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	SaveStateList saveList;
+
+	// Load the descriptions
+	Common::StringArray savenames;
+	savenames.resize(MAX_SAVE_GAMES+1);
+
+	Common::InSaveFile *inf;
+	inf = saveFileMan->openForLoading("SKY-VM.SAV");
+	if (inf != NULL) {
+		char *tmpBuf =  new char[MAX_SAVE_GAMES * MAX_TEXT_LEN];
+		char *tmpPtr = tmpBuf;
+		inf->read(tmpBuf, MAX_SAVE_GAMES * MAX_TEXT_LEN);
+		for (int i = 0; i < MAX_SAVE_GAMES; ++i) {
+			savenames[i] = tmpPtr;
+			tmpPtr += savenames[i].size() + 1;
+		}
+		delete inf;
+		delete[] tmpBuf;
+	}
+
+	// Find all saves
+	Common::StringArray filenames;
+	filenames = saveFileMan->listSavefiles("SKY-VM.###");
+
+	// Prepare the list of savestates by looping over all matching savefiles
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Extract the extension
+		Common::String ext = file->c_str() + file->size() - 3;
+		ext.toUppercase();
+		int slotNum = atoi(ext.c_str());
+		Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+		if (in) {
+			saveList.push_back(SaveStateDescriptor(slotNum,
+				(slotNum == 0) ? _("Autosave") : Common::U32String(savenames[slotNum - 1])));
+			delete in;
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int SkyMetaEngineConnect::getMaximumSaveSlot() const { return MAX_SAVE_GAMES; }
+
+void SkyMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	if (slot == 0)	// do not delete the auto save
+		return;
+
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	char fName[20];
+	sprintf(fName,"SKY-VM.%03d", slot);
+	saveFileMan->removeSavefile(fName);
+
+	// Load current save game descriptions
+	Common::StringArray savenames;
+	savenames.resize(MAX_SAVE_GAMES+1);
+	Common::InSaveFile *inf;
+	inf = saveFileMan->openForLoading("SKY-VM.SAV");
+	if (inf != NULL) {
+		char *tmpBuf =  new char[MAX_SAVE_GAMES * MAX_TEXT_LEN];
+		char *tmpPtr = tmpBuf;
+		inf->read(tmpBuf, MAX_SAVE_GAMES * MAX_TEXT_LEN);
+		for (int i = 0; i < MAX_SAVE_GAMES; ++i) {
+			savenames[i] = tmpPtr;
+			tmpPtr += savenames[i].size() + 1;
+		}
+		delete inf;
+		delete[] tmpBuf;
+	}
+
+	// Update the save game description at the given slot
+	savenames[slot] = "";
+
+	// Save the updated descriptions
+	Common::OutSaveFile *outf;
+
+	outf = saveFileMan->openForSaving("SKY-VM.SAV");
+	bool ioFailed = true;
+	if (outf) {
+		for (uint16 cnt = 0; cnt < MAX_SAVE_GAMES; cnt++) {
+			outf->write(savenames[cnt].c_str(), savenames[cnt].size() + 1);
+		}
+		outf->finalize();
+		if (!outf->err())
+			ioFailed = false;
+		delete outf;
+	}
+	if (ioFailed)
+		warning("Unable to store Savegame names to file SKY-VM.SAV. (%s)", saveFileMan->popErrorDesc().c_str());
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(SKY)
+	REGISTER_PLUGIN_DYNAMIC(SKY, PLUGIN_TYPE_ENGINE, SkyMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(SKY, PLUGIN_TYPE_ENGINE, SkyMetaEngineConnect);
+#endif
+
+namespace Sky {
+
+Common::Error SkyEngine::loadGameState(int slot) {
+	// We don't need to offset "slot" here. Both loadGameState and quickXRestore
+	// are called with the ScummVM Save File Manager's "slot" as argument
+	uint16 result = _skyControl->quickXRestore(slot);
+	return (result == GAME_RESTORED) ? Common::kNoError : Common::kUnknownError;
+}
+
+/**
+* Manually saving a game should save it into ScummVM Save File Managers slots 1 or greater.
+* ScummVM Save file manager's slot 0 is reserved for the autosave.
+* However, natively, the index 0 (_selectedGame) is the first manually saved game.
+* @param slot is the save slot on the ScummVM file manager's list
+*
+*/
+Common::Error SkyEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
+	// prevent writing to autosave slot when user selects it manually
+	// ie. from the ScummVM in-game menu Save feature
+	// This also secures _selectedGame which is unsigned integer (uint16)
+	// from overflowing in the subtraction below
+	if (slot < 0 || (!isAutosave && slot == 0)) {
+		return Common::kWritePermissionDenied;
+	}
+	// Set the save slot and save the game
+	// _selectedGame value is one unit lower than the ScummVM's Save File Manager's slot value
+	// Note that *_selectedGame* value 0 corresponds to a manually saved game (the first in order)
+	//   whereas *slot* value 0 corresponds to the autosave
+	if (slot > 0) {
+		// We don't care for updating the _selectedGame when slot == 0
+		// (in the case of autosave) but we do include the check for slot > 0
+		// to guard from overflow, which would be bad practice to allow.
+		_skyControl->_selectedGame = slot - 1;
+	}
+	if (_skyControl->saveGameToFile(false, nullptr, isAutosave) != GAME_SAVED)
+		return Common::kWritePermissionDenied;
+
+	// Load current save game descriptions
+	Common::StringArray saveGameTexts;
+	saveGameTexts.resize(MAX_SAVE_GAMES+1);
+	_skyControl->loadDescriptions(saveGameTexts);
+
+	// Update the save game description at the given slot
+	if (!isAutosave) {
+		saveGameTexts[_skyControl->_selectedGame] = desc;
+	}
+
+	// Save the updated descriptions
+	_skyControl->saveDescriptions(saveGameTexts);
+
+	return Common::kNoError;
+}
+
+bool SkyEngine::canLoadGameStateCurrently() {
+	return _systemVars->pastIntro && _skyControl->loadSaveAllowed();
+}
+
+bool SkyEngine::canSaveGameStateCurrently() {
+	return _systemVars->pastIntro && _skyControl->loadSaveAllowed();
+}
+
+} // End of namespace Sky
diff --git a/engines/sky/module.mk b/engines/sky/module.mk
index e75841f1bd..4dd4d20b0b 100644
--- a/engines/sky/module.mk
+++ b/engines/sky/module.mk
@@ -5,12 +5,12 @@ MODULE_OBJS := \
 	compact.o \
 	control.o \
 	debug.o \
-	detection.o \
 	disk.o \
 	grid.o \
 	hufftext.o \
 	intro.o \
 	logic.o \
+	metaengine.o \
 	mouse.o \
 	rnc_deco.o \
 	screen.o \
@@ -31,3 +31,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: cdf42613288687997484df2e02abb09a108dccac
    https://github.com/scummvm/scummvm/commit/cdf42613288687997484df2e02abb09a108dccac
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DREAMWEB: Move common struct to detection.h

- This way we don't include entire detection_tables in metaengine.cpp, which needs it.

Changed paths:
  A engines/dreamweb/detection.h
    engines/dreamweb/detection_tables.h


diff --git a/engines/dreamweb/detection.h b/engines/dreamweb/detection.h
new file mode 100644
index 0000000000..06b440c8ce
--- /dev/null
+++ b/engines/dreamweb/detection.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace DreamWeb {
+
+struct DreamWebGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace DreamWeb
diff --git a/engines/dreamweb/detection_tables.h b/engines/dreamweb/detection_tables.h
index d7bb46d33d..73802e862e 100644
--- a/engines/dreamweb/detection_tables.h
+++ b/engines/dreamweb/detection_tables.h
@@ -23,14 +23,13 @@
 #ifndef DREAMWEB_DETECTION_TABLES_H
 #define DREAMWEB_DETECTION_TABLES_H
 
+#include "dreamweb/detection.h"
+
 namespace DreamWeb {
 
 #define GAMEOPTION_ORIGINAL_SAVELOAD GUIO_GAMEOPTIONS1
 #define GAMEOPTION_BRIGHTPALETTE     GUIO_GAMEOPTIONS2
 
-struct DreamWebGameDescription {
-	ADGameDescription desc;
-};
 
 static const DreamWebGameDescription gameDescriptions[] = {
 	// International floppy release


Commit: 5161f46f9835f915ab23afb3a810d691eb55c2f5
    https://github.com/scummvm/scummvm/commit/5161f46f9835f915ab23afb3a810d691eb55c2f5
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DREAMWEB: Split detection code & adapt to new plugins.

Changed paths:
  A engines/dreamweb/metaengine.cpp
    configure
    engines/dreamweb/detection.cpp
    engines/dreamweb/detection.h
    engines/dreamweb/module.mk


diff --git a/configure b/configure
index 1bdf0c7f75..e7ae698054 100755
--- a/configure
+++ b/configure
@@ -6160,7 +6160,7 @@ EOF
 	fi
 done
 
-declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY")
+declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/dreamweb/detection.cpp b/engines/dreamweb/detection.cpp
index 4bf011754b..19e9a502a1 100644
--- a/engines/dreamweb/detection.cpp
+++ b/engines/dreamweb/detection.cpp
@@ -23,16 +23,12 @@
 #include "base/plugins.h"
 
 #include "common/algorithm.h"
-#include "common/savefile.h"
 #include "common/system.h"
 #include "common/translation.h"
 
 #include "engines/advancedDetector.h"
 
-#include "graphics/thumbnail.h"
-
-#include "dreamweb/dreamweb.h"
-#include "dreamweb/structs.h"
+#include "dreamweb/detection.h"
 
 static const PlainGameDescriptor dreamWebGames[] = {
 	{ "dreamweb", "DreamWeb" },
@@ -85,178 +81,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "DreamWeb (C) Creative Reality";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool DreamWebMetaEngine::hasFeature(MetaEngineFeature f) const {
-	switch(f) {
-	case kSupportsListSaves:
-	case kSupportsLoadingDuringStartup:
-	case kSupportsDeleteSave:
-	case kSavesSupportMetaInfo:
-	case kSavesSupportThumbnail:
-	case kSavesSupportCreationDate:
-	case kSavesSupportPlayTime:
-		return true;
-	default:
-		return false;
-	}
-}
-
-bool DreamWeb::DreamWebEngine::hasFeature(EngineFeature f) const {
-	switch(f) {
-	case kSupportsReturnToLauncher:
-		return true;
-	case kSupportsSubtitleOptions:
-		return _gameDescription->desc.flags & ADGF_CD;
-	default:
-		return false;
-	}
-	return false;
-}
-
-bool DreamWebMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const DreamWeb::DreamWebGameDescription *gd = (const DreamWeb::DreamWebGameDescription *)desc;
-	if (gd) {
-		*engine = new DreamWeb::DreamWebEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList DreamWebMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray files = saveFileMan->listSavefiles("DREAMWEB.D##");
-
-	SaveStateList saveList;
-	for (uint i = 0; i < files.size(); ++i) {
-		const Common::String &file = files[i];
-		Common::InSaveFile *stream = saveFileMan->openForLoading(file);
-		if (!stream)
-			error("cannot open save file %s", file.c_str());
-		char name[17] = {};
-		stream->seek(0x61);
-		stream->read(name, sizeof(name) - 1);
-		delete stream;
-
-		int slotNum = atoi(file.c_str() + file.size() - 2);
-		SaveStateDescriptor sd(slotNum, name);
-		saveList.push_back(sd);
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int DreamWebMetaEngine::getMaximumSaveSlot() const { return 99; }
-
-void DreamWebMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("DREAMWEB.D%02d", slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-SaveStateDescriptor DreamWebMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("DREAMWEB.D%02d", slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
-
-	if (in) {
-		DreamWeb::FileHeader header;
-		in->read((uint8 *)&header, sizeof(DreamWeb::FileHeader));
-
-		Common::String saveName;
-		byte descSize = header.len(0);
-		byte i;
-
-		for (i = 0; i < descSize; i++)
-			saveName += (char)in->readByte();
-
-		SaveStateDescriptor desc(slot, saveName);
-
-		// Check if there is a ScummVM data block
-		if (header.len(6) == SCUMMVM_BLOCK_MAGIC_SIZE) {
-			// Skip the game data
-			for (i = 1; i <= 5; i++)
-				in->skip(header.len(i));
-
-			uint32 tag = in->readUint32BE();
-			if (tag != SCUMMVM_HEADER) {
-				warning("ScummVM data block found, but the block header is incorrect - skipping");
-				delete in;
-				return desc;
-			}
-
-			byte version = in->readByte();
-			if (version > SAVEGAME_VERSION) {
-				warning("ScummVM data block found, but it has been saved with a newer version of ScummVM - skipping");
-				delete in;
-				return desc;
-			}
-
-			uint32 saveDate = in->readUint32LE();
-			uint32 saveTime = in->readUint32LE();
-			uint32 playTime = in->readUint32LE();
-			Graphics::Surface *thumbnail;
-			if (!Graphics::loadThumbnail(*in, thumbnail)) {
-				warning("Missing or broken thumbnail - skipping");
-				delete in;
-				return desc;
-			}
-
-			int day = (saveDate >> 24) & 0xFF;
-			int month = (saveDate >> 16) & 0xFF;
-			int year = saveDate & 0xFFFF;
-			int hour = (saveTime >> 16) & 0xFF;
-			int minutes = (saveTime >> 8) & 0xFF;
-
-			desc.setSaveDate(year, month, day);
-			desc.setSaveTime(hour, minutes);
-			desc.setPlayTime(playTime * 1000);
-			desc.setThumbnail(thumbnail);
-		}
-
-		delete in;
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(DREAMWEB)
-	REGISTER_PLUGIN_DYNAMIC(DREAMWEB, PLUGIN_TYPE_ENGINE, DreamWebMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(DREAMWEB, PLUGIN_TYPE_ENGINE, DreamWebMetaEngine);
-#endif
-
-namespace DreamWeb {
-
-Common::Error DreamWebEngine::loadGameState(int slot) {
-	return Common::kNoError;
-}
-
-Common::Error DreamWebEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
-	return Common::kNoError;
-}
-
-bool DreamWebEngine::canLoadGameStateCurrently() {
-	return false;
-}
-
-bool DreamWebEngine::canSaveGameStateCurrently() {
-	return false;
-}
-
-Common::Language DreamWebEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-bool DreamWebEngine::isCD() {
-	return _gameDescription->desc.flags & ADGF_CD;
-}
-
-} // End of namespace DreamWeb
+REGISTER_PLUGIN_STATIC(DREAMWEB_DETECTION, PLUGIN_TYPE_METAENGINE, DreamWebMetaEngine);
diff --git a/engines/dreamweb/detection.h b/engines/dreamweb/detection.h
index 06b440c8ce..e2941b7e30 100644
--- a/engines/dreamweb/detection.h
+++ b/engines/dreamweb/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef DREAMWEB_DETECTION_H
+#define DREAMWEB_DETECTION_H
+
 namespace DreamWeb {
 
 struct DreamWebGameDescription {
@@ -27,3 +30,5 @@ struct DreamWebGameDescription {
 };
 
 } // End of namespace DreamWeb
+
+#endif // DREAMWEB_DETECTION_H
diff --git a/engines/dreamweb/metaengine.cpp b/engines/dreamweb/metaengine.cpp
new file mode 100644
index 0000000000..e127960ed3
--- /dev/null
+++ b/engines/dreamweb/metaengine.cpp
@@ -0,0 +1,213 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/savefile.h"
+
+#include "graphics/thumbnail.h"
+
+#include "engines/advancedDetector.h"
+
+#include "dreamweb/dreamweb.h"
+#include "dreamweb/detection.h"
+
+class DreamWebMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "dreamweb";
+	}
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool DreamWebMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	switch(f) {
+	case kSupportsListSaves:
+	case kSupportsLoadingDuringStartup:
+	case kSupportsDeleteSave:
+	case kSavesSupportMetaInfo:
+	case kSavesSupportThumbnail:
+	case kSavesSupportCreationDate:
+	case kSavesSupportPlayTime:
+		return true;
+	default:
+		return false;
+	}
+}
+
+bool DreamWeb::DreamWebEngine::hasFeature(EngineFeature f) const {
+	switch(f) {
+	case kSupportsReturnToLauncher:
+		return true;
+	case kSupportsSubtitleOptions:
+		return _gameDescription->desc.flags & ADGF_CD;
+	default:
+		return false;
+	}
+	return false;
+}
+
+bool DreamWebMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const DreamWeb::DreamWebGameDescription *gd = (const DreamWeb::DreamWebGameDescription *)desc;
+	if (gd) {
+		*engine = new DreamWeb::DreamWebEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList DreamWebMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray files = saveFileMan->listSavefiles("DREAMWEB.D##");
+
+	SaveStateList saveList;
+	for (uint i = 0; i < files.size(); ++i) {
+		const Common::String &file = files[i];
+		Common::InSaveFile *stream = saveFileMan->openForLoading(file);
+		if (!stream)
+			error("cannot open save file %s", file.c_str());
+		char name[17] = {};
+		stream->seek(0x61);
+		stream->read(name, sizeof(name) - 1);
+		delete stream;
+
+		int slotNum = atoi(file.c_str() + file.size() - 2);
+		SaveStateDescriptor sd(slotNum, name);
+		saveList.push_back(sd);
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int DreamWebMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+
+void DreamWebMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("DREAMWEB.D%02d", slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+SaveStateDescriptor DreamWebMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("DREAMWEB.D%02d", slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
+
+	if (in) {
+		DreamWeb::FileHeader header;
+		in->read((uint8 *)&header, sizeof(DreamWeb::FileHeader));
+
+		Common::String saveName;
+		byte descSize = header.len(0);
+		byte i;
+
+		for (i = 0; i < descSize; i++)
+			saveName += (char)in->readByte();
+
+		SaveStateDescriptor desc(slot, saveName);
+
+		// Check if there is a ScummVM data block
+		if (header.len(6) == SCUMMVM_BLOCK_MAGIC_SIZE) {
+			// Skip the game data
+			for (i = 1; i <= 5; i++)
+				in->skip(header.len(i));
+
+			uint32 tag = in->readUint32BE();
+			if (tag != SCUMMVM_HEADER) {
+				warning("ScummVM data block found, but the block header is incorrect - skipping");
+				delete in;
+				return desc;
+			}
+
+			byte version = in->readByte();
+			if (version > SAVEGAME_VERSION) {
+				warning("ScummVM data block found, but it has been saved with a newer version of ScummVM - skipping");
+				delete in;
+				return desc;
+			}
+
+			uint32 saveDate = in->readUint32LE();
+			uint32 saveTime = in->readUint32LE();
+			uint32 playTime = in->readUint32LE();
+			Graphics::Surface *thumbnail;
+			if (!Graphics::loadThumbnail(*in, thumbnail)) {
+				warning("Missing or broken thumbnail - skipping");
+				delete in;
+				return desc;
+			}
+
+			int day = (saveDate >> 24) & 0xFF;
+			int month = (saveDate >> 16) & 0xFF;
+			int year = saveDate & 0xFFFF;
+			int hour = (saveTime >> 16) & 0xFF;
+			int minutes = (saveTime >> 8) & 0xFF;
+
+			desc.setSaveDate(year, month, day);
+			desc.setSaveTime(hour, minutes);
+			desc.setPlayTime(playTime * 1000);
+			desc.setThumbnail(thumbnail);
+		}
+
+		delete in;
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(DREAMWEB)
+	REGISTER_PLUGIN_DYNAMIC(DREAMWEB, PLUGIN_TYPE_ENGINE, DreamWebMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(DREAMWEB, PLUGIN_TYPE_ENGINE, DreamWebMetaEngineConnect);
+#endif
+
+namespace DreamWeb {
+
+Common::Error DreamWebEngine::loadGameState(int slot) {
+	return Common::kNoError;
+}
+
+Common::Error DreamWebEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
+	return Common::kNoError;
+}
+
+bool DreamWebEngine::canLoadGameStateCurrently() {
+	return false;
+}
+
+bool DreamWebEngine::canSaveGameStateCurrently() {
+	return false;
+}
+
+Common::Language DreamWebEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+bool DreamWebEngine::isCD() {
+	return _gameDescription->desc.flags & ADGF_CD;
+}
+
+} // End of namespace DreamWeb
diff --git a/engines/dreamweb/module.mk b/engines/dreamweb/module.mk
index 3e367c6fdf..d3c0f48a2a 100644
--- a/engines/dreamweb/module.mk
+++ b/engines/dreamweb/module.mk
@@ -3,9 +3,9 @@ MODULE := engines/dreamweb
 MODULE_OBJS := \
 	backdrop.o \
 	console.o \
-	detection.o \
 	dreamweb.o \
 	keypad.o \
+	metaengine.o \
 	monitor.o \
 	mouse.o \
 	newplace.o \
@@ -31,3 +31,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 14edaf3d038bc130616b33364109040d9ae226e0
    https://github.com/scummvm/scummvm/commit/14edaf3d038bc130616b33364109040d9ae226e0
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DRASCULA: Split detection code & adapt to new plugins

- Also shift common things to detection.h, like a struct & enum.

Changed paths:
  A engines/drascula/detection.h
  A engines/drascula/detection_enums.h
  A engines/drascula/metaengine.cpp
    configure
    engines/drascula/detection.cpp
    engines/drascula/drascula.h
    engines/drascula/module.mk


diff --git a/configure b/configure
index e7ae698054..378685bca0 100755
--- a/configure
+++ b/configure
@@ -6160,7 +6160,7 @@ EOF
 	fi
 done
 
-declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB")
+declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/drascula/detection.cpp b/engines/drascula/detection.cpp
index 4f28f94ab3..d8eb9b0a5a 100644
--- a/engines/drascula/detection.cpp
+++ b/engines/drascula/detection.cpp
@@ -25,40 +25,9 @@
 #include "common/translation.h"
 
 #include "engines/advancedDetector.h"
-#include "engines/savestate.h"
 
-#include "graphics/thumbnail.h"
-
-#include "drascula/drascula.h"
-
-namespace Drascula {
-
-struct DrasculaGameDescription {
-	ADGameDescription desc;
-};
-
-uint32 DrasculaEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language DrasculaEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-void DrasculaEngine::loadArchives() {
-	const ADGameFileDescription *ag;
-
-	if (getFeatures() & GF_PACKED) {
-		for (ag = _gameDescription->desc.filesDescriptions; ag->fileName; ag++) {
-			if (!_archives.hasArchive(ag->fileName))
-				_archives.registerArchive(ag->fileName, ag->fileType);
-		}
-	}
-
-	_archives.enableFallback(true);
-}
-
-}
+#include "drascula/detection_enums.h"
+#include "drascula/detection.h"
 
 static const PlainGameDescriptor drasculaGames[] = {
 	{"drascula", "Drascula: The Vampire Strikes Back"},
@@ -334,8 +303,6 @@ static const ExtraGuiOption drasculaExtraGuiOption = {
 	false
 };
 
-SaveStateDescriptor loadMetaData(Common::ReadStream *s, int slot, bool setPlayTime);
-
 class DrasculaMetaEngine : public AdvancedMetaEngine {
 public:
 	DrasculaMetaEngine() : AdvancedMetaEngine(Drascula::gameDescriptions, sizeof(Drascula::DrasculaGameDescription), drasculaGames) {
@@ -354,117 +321,15 @@ public:
 		return "Drascula: The Vampire Strikes Back (C) 2000 Alcachofa Soft, (C) 1996 Digital Dreams Multimedia, (C) 1994 Emilio de Paz";
 	}
 
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool DrasculaMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
 const ExtraGuiOptions DrasculaMetaEngine::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	options.push_back(drasculaExtraGuiOption);
 	return options;
 }
 
-SaveStateList DrasculaMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	int slotNum = 0;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				SaveStateDescriptor desc = loadMetaData(in, slotNum, false);
-				if (desc.getSaveSlot() != slotNum) {
-					// invalid
-					delete in;
-					continue;
-				}
-				saveList.push_back(desc);
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor DrasculaMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
-
-	SaveStateDescriptor desc;
-	// Do not allow save slot 0 (used for auto-saving) to be deleted or
-	// overwritten.
-	desc.setDeletableFlag(slot != 0);
-	desc.setWriteProtectedFlag(slot == 0);
-
-	if (in) {
-		desc = Drascula::loadMetaData(in, slot, false);
-		if (desc.getSaveSlot() != slot) {
-			delete in;
-			return SaveStateDescriptor();
-		}
-
-		Graphics::Surface *thumbnail;
-		if (!Graphics::loadThumbnail(*in, thumbnail)) {
-			delete in;
-			return SaveStateDescriptor();
-		}
-		desc.setThumbnail(thumbnail);
-
-		delete in;
-	}
-
-	return desc;
-}
-
-int DrasculaMetaEngine::getMaximumSaveSlot() const { return 999; }
-
-void DrasculaMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-bool DrasculaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Drascula::DrasculaGameDescription *gd = (const Drascula::DrasculaGameDescription *)desc;
-	if (gd) {
-		*engine = new Drascula::DrasculaEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
 } // End of namespace Drascula
 
-#if PLUGIN_ENABLED_DYNAMIC(DRASCULA)
-	REGISTER_PLUGIN_DYNAMIC(DRASCULA, PLUGIN_TYPE_ENGINE, Drascula::DrasculaMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(DRASCULA, PLUGIN_TYPE_ENGINE, Drascula::DrasculaMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(DRASCULA_DETECTION, PLUGIN_TYPE_METAENGINE, Drascula::DrasculaMetaEngine);
diff --git a/engines/drascula/detection.h b/engines/drascula/detection.h
new file mode 100644
index 0000000000..9e8550bac8
--- /dev/null
+++ b/engines/drascula/detection.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Drascula {
+
+struct DrasculaGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Drascula
diff --git a/engines/drascula/detection_enums.h b/engines/drascula/detection_enums.h
new file mode 100644
index 0000000000..ba46883146
--- /dev/null
+++ b/engines/drascula/detection_enums.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Drascula {
+
+enum DrasculaGameFeatures {
+	GF_PACKED = (1 << 0)
+};
+
+} // End of namespace Drascula
diff --git a/engines/drascula/drascula.h b/engines/drascula/drascula.h
index 8dcffbd64f..749f9c3033 100644
--- a/engines/drascula/drascula.h
+++ b/engines/drascula/drascula.h
@@ -39,6 +39,7 @@
 #include "engines/savestate.h"
 
 #include "drascula/console.h"
+#include "drascula/detection_enums.h"
 
 #include "audio/mixer.h"
 
@@ -57,10 +58,6 @@ namespace Drascula {
 #define DRASCULA_DAT_VER 6
 #define DATAALIGNMENT 4
 
-enum DrasculaGameFeatures {
-	GF_PACKED = (1 << 0)
-};
-
 enum Languages {
 	kEnglish = 0,
 	kSpanish = 1,
diff --git a/engines/drascula/metaengine.cpp b/engines/drascula/metaengine.cpp
new file mode 100644
index 0000000000..ec732a512b
--- /dev/null
+++ b/engines/drascula/metaengine.cpp
@@ -0,0 +1,174 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/savestate.h"
+#include "engines/advancedDetector.h"
+
+#include "graphics/thumbnail.h"
+
+#include "drascula/drascula.h"
+#include "drascula/detection.h"
+
+namespace Drascula {
+
+uint32 DrasculaEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language DrasculaEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+void DrasculaEngine::loadArchives() {
+	const ADGameFileDescription *ag;
+
+	if (getFeatures() & GF_PACKED) {
+		for (ag = _gameDescription->desc.filesDescriptions; ag->fileName; ag++) {
+			if (!_archives.hasArchive(ag->fileName))
+				_archives.registerArchive(ag->fileName, ag->fileType);
+		}
+	}
+
+	_archives.enableFallback(true);
+}
+
+} // End of namespace Drascula
+
+
+namespace Drascula {
+
+SaveStateDescriptor loadMetaData(Common::ReadStream *s, int slot, bool setPlayTime);
+
+class DrasculaMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "drascula";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+    SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool DrasculaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+SaveStateList DrasculaMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	int slotNum = 0;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				SaveStateDescriptor desc = loadMetaData(in, slotNum, false);
+				if (desc.getSaveSlot() != slotNum) {
+					// invalid
+					delete in;
+					continue;
+				}
+				saveList.push_back(desc);
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor DrasculaMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
+
+	SaveStateDescriptor desc;
+	// Do not allow save slot 0 (used for auto-saving) to be deleted or
+	// overwritten.
+	desc.setDeletableFlag(slot != 0);
+	desc.setWriteProtectedFlag(slot == 0);
+
+	if (in) {
+		desc = Drascula::loadMetaData(in, slot, false);
+		if (desc.getSaveSlot() != slot) {
+			delete in;
+			return SaveStateDescriptor();
+		}
+
+		Graphics::Surface *thumbnail;
+		if (!Graphics::loadThumbnail(*in, thumbnail)) {
+			delete in;
+			return SaveStateDescriptor();
+		}
+		desc.setThumbnail(thumbnail);
+
+		delete in;
+	}
+
+	return desc;
+}
+
+int DrasculaMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+
+void DrasculaMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+bool DrasculaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Drascula::DrasculaGameDescription *gd = (const Drascula::DrasculaGameDescription *)desc;
+	if (gd) {
+		*engine = new Drascula::DrasculaEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+} // End of namespace Drascula
+
+#if PLUGIN_ENABLED_DYNAMIC(DRASCULA)
+	REGISTER_PLUGIN_DYNAMIC(DRASCULA, PLUGIN_TYPE_ENGINE, Drascula::DrasculaMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(DRASCULA, PLUGIN_TYPE_ENGINE, Drascula::DrasculaMetaEngineConnect);
+#endif
diff --git a/engines/drascula/module.mk b/engines/drascula/module.mk
index 20fd900124..46dae3e731 100644
--- a/engines/drascula/module.mk
+++ b/engines/drascula/module.mk
@@ -5,10 +5,10 @@ MODULE_OBJS := \
 	animation.o \
 	console.o \
 	converse.o \
-	detection.o \
 	drascula.o \
 	graphics.o \
 	interface.o \
+	metaengine.o \
 	objects.o \
 	palette.o \
 	resource.o \
@@ -25,3 +25,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 141edd7eb86727812f56a242258e2f9f8dd19507
    https://github.com/scummvm/scummvm/commit/141edd7eb86727812f56a242258e2f9f8dd19507
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
LURE: Split detection code & adapt to new plugins.

- There is also some shifting around of code done, so metaengine.cpp & detection.cpp can only share what's needed.

Changed paths:
  A engines/lure/detection.h
  A engines/lure/detection_enums.h
  A engines/lure/metaengine.cpp
    configure
    engines/lure/detection.cpp
    engines/lure/lure.h
    engines/lure/luredefs.h
    engines/lure/module.mk


diff --git a/configure b/configure
index 378685bca0..39dde89d8a 100755
--- a/configure
+++ b/configure
@@ -6160,7 +6160,7 @@ EOF
 	fi
 done
 
-declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA")
+declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/lure/detection.cpp b/engines/lure/detection.cpp
index 9f397dcc45..017b7d9b52 100644
--- a/engines/lure/detection.cpp
+++ b/engines/lure/detection.cpp
@@ -23,39 +23,11 @@
 #include "base/plugins.h"
 
 #include "engines/advancedDetector.h"
-#include "engines/engine.h"
-#include "common/savefile.h"
-#include "common/system.h"
-#include "common/translation.h"
-#include "lure/lure.h"
-
-namespace Lure {
-
-struct LureGameDescription {
-	ADGameDescription desc;
-
-	uint32 features;
-};
-
-uint32 LureEngine::getFeatures() const { return _gameDescription->features; }
-Common::Language LureEngine::getLanguage() const { return _gameDescription->desc.language; }
-Common::Platform LureEngine::getPlatform() const { return _gameDescription->desc.platform; }
 
-LureLanguage LureEngine::getLureLanguage() const {
-	switch (_gameDescription->desc.language) {
-	case Common::IT_ITA: return LANG_IT_ITA;
-	case Common::FR_FRA: return LANG_FR_FRA;
-	case Common::DE_DEU: return LANG_DE_DEU;
-	case Common::ES_ESP: return LANG_ES_ESP;
-	case Common::RU_RUS: return LANG_RU_RUS;
-	case Common::EN_ANY: return LANG_EN_ANY;
-	case Common::UNK_LANG: return LANG_UNKNOWN;
-	default:
-		error("Unknown game language");
-	}
-}
+#include "common/translation.h"
 
-} // End of namespace Lure
+#include "lure/detection_enums.h"
+#include "lure/detection.h"
 
 static const PlainGameDescriptor lureGames[] = {
 	{"lure", "Lure of the Temptress"},
@@ -257,75 +229,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Lure of the Temptress (C) Revolution";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool LureMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave);
-}
-
-bool Lure::LureEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool LureMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Lure::LureGameDescription *gd = (const Lure::LureGameDescription *)desc;
-	if (gd) {
-		*engine = new Lure::LureEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList LureMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = "lure.###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				saveDesc = Lure::getSaveName(in);
-				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int LureMetaEngine::getMaximumSaveSlot() const { return 999; }
-
-void LureMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = target;
-	filename += Common::String::format(".%03d", slot);
-
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(LURE)
-	REGISTER_PLUGIN_DYNAMIC(LURE, PLUGIN_TYPE_ENGINE, LureMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(LURE, PLUGIN_TYPE_ENGINE, LureMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(LURE_DETECTION, PLUGIN_TYPE_METAENGINE, LureMetaEngine);
diff --git a/engines/lure/detection.h b/engines/lure/detection.h
new file mode 100644
index 0000000000..75f7e4c973
--- /dev/null
+++ b/engines/lure/detection.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Lure {
+
+struct LureGameDescription {
+	ADGameDescription desc;
+
+	uint32 features;
+};
+
+} // End of namespace Lure
diff --git a/engines/lure/detection_enums.h b/engines/lure/detection_enums.h
new file mode 100644
index 0000000000..90c3eba374
--- /dev/null
+++ b/engines/lure/detection_enums.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Lure {
+
+enum {
+	GF_FLOPPY	= 1 <<  0,
+	GF_EGA		= 1 <<  1,
+	GF_LNGUNK	= 1 << 15
+};
+
+} // End of namespace Lure
diff --git a/engines/lure/lure.h b/engines/lure/lure.h
index a3ca07543f..c2ec5a5328 100644
--- a/engines/lure/lure.h
+++ b/engines/lure/lure.h
@@ -24,6 +24,8 @@
 #define LURE_LURE_H
 
 #include "engines/engine.h"
+#include "engines/advancedDetector.h"
+
 #include "common/rect.h"
 #include "common/file.h"
 #include "common/savefile.h"
@@ -38,6 +40,7 @@
 #include "lure/strings.h"
 #include "lure/room.h"
 #include "lure/fights.h"
+#include "lure/detection_enums.h"
 
 /**
  * This is the namespace of the Lure engine.
diff --git a/engines/lure/luredefs.h b/engines/lure/luredefs.h
index c6d0afa34c..635b292177 100644
--- a/engines/lure/luredefs.h
+++ b/engines/lure/luredefs.h
@@ -50,12 +50,6 @@ enum {
 #define ERROR_INTERMEDIATE 2
 #define ERROR_DETAILED 3
 
-enum {
-	GF_FLOPPY	= 1 <<  0,
-	GF_EGA		= 1 <<  1,
-	GF_LNGUNK	= 1 << 15
-};
-
 enum {
 	GI_LURE = 0
 };
diff --git a/engines/lure/metaengine.cpp b/engines/lure/metaengine.cpp
new file mode 100644
index 0000000000..c6d7171f3b
--- /dev/null
+++ b/engines/lure/metaengine.cpp
@@ -0,0 +1,130 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "engines/advancedDetector.h"
+
+#include "lure/lure.h"
+#include "lure/detection.h"
+
+namespace Lure {
+
+uint32 LureEngine::getFeatures() const { return _gameDescription->features; }
+Common::Language LureEngine::getLanguage() const { return _gameDescription->desc.language; }
+Common::Platform LureEngine::getPlatform() const { return _gameDescription->desc.platform; }
+
+LureLanguage LureEngine::getLureLanguage() const {
+	switch (_gameDescription->desc.language) {
+	case Common::IT_ITA: return LANG_IT_ITA;
+	case Common::FR_FRA: return LANG_FR_FRA;
+	case Common::DE_DEU: return LANG_DE_DEU;
+	case Common::ES_ESP: return LANG_ES_ESP;
+	case Common::RU_RUS: return LANG_RU_RUS;
+	case Common::EN_ANY: return LANG_EN_ANY;
+	case Common::UNK_LANG: return LANG_UNKNOWN;
+	default:
+		error("Unknown game language");
+	}
+}
+
+} // End of namespace Lure
+
+class LureMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "lure";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool LureMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave);
+}
+
+bool Lure::LureEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool LureMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Lure::LureGameDescription *gd = (const Lure::LureGameDescription *)desc;
+	if (gd) {
+		*engine = new Lure::LureEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList LureMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = "lure.###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				saveDesc = Lure::getSaveName(in);
+				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int LureMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+
+void LureMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = target;
+	filename += Common::String::format(".%03d", slot);
+
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(LURE)
+	REGISTER_PLUGIN_DYNAMIC(LURE, PLUGIN_TYPE_ENGINE, LureMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(LURE, PLUGIN_TYPE_ENGINE, LureMetaEngineConnect);
+#endif
diff --git a/engines/lure/module.mk b/engines/lure/module.mk
index 57126a6491..7aae9073ef 100644
--- a/engines/lure/module.mk
+++ b/engines/lure/module.mk
@@ -4,7 +4,6 @@ MODULE_OBJS := \
 	animseq.o \
 	debugger.o \
 	decode.o \
-	detection.o \
 	disk.o \
 	events.o \
 	fights.o \
@@ -14,6 +13,7 @@ MODULE_OBJS := \
 	lure.o \
 	memory.o \
 	menu.o \
+	metaengine.o \
 	palette.o \
 	res.o \
 	res_struct.o \
@@ -31,3 +31,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 467ca35a371e59823fb8bfb606a3e151ed56224a
    https://github.com/scummvm/scummvm/commit/467ca35a371e59823fb8bfb606a3e151ed56224a
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SWORD1: Split detection code & adapt to new plugins.

Changed paths:
  A engines/sword1/metaengine.cpp
    configure
    engines/sword1/detection.cpp
    engines/sword1/module.mk


diff --git a/configure b/configure
index 39dde89d8a..e72d935a8c 100755
--- a/configure
+++ b/configure
@@ -6160,7 +6160,8 @@ EOF
 	fi
 done
 
-declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE")
+declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
+								  "SWORD1")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/sword1/detection.cpp b/engines/sword1/detection.cpp
index b024e29730..abfaa57518 100644
--- a/engines/sword1/detection.cpp
+++ b/engines/sword1/detection.cpp
@@ -20,16 +20,10 @@
  *
  */
 
-#include "sword1/sword1.h"
-#include "sword1/control.h"
-
 #include "base/plugins.h"
+
 #include "common/fs.h"
 #include "common/gui_options.h"
-#include "common/savefile.h"
-#include "common/system.h"
-#include "graphics/thumbnail.h"
-#include "graphics/surface.h"
 
 #include "engines/metaengine.h"
 
@@ -90,36 +84,11 @@ public:
 		return "Broken Sword: The Shadow of the Templars (C) Revolution";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override;
 	PlainGameList getSupportedGames() const override;
 	PlainGameDescriptor findGame(const char *gameId) const override;
 	DetectedGames detectGames(const Common::FSList &fslist) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-
-	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
 };
 
-bool SwordMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-	    (f == kSupportsLoadingDuringStartup) ||
-	    (f == kSupportsDeleteSave) ||
-	    (f == kSavesSupportMetaInfo) ||
-	    (f == kSavesSupportThumbnail) ||
-	    (f == kSavesSupportCreationDate) ||
-	    (f == kSavesSupportPlayTime);
-}
-
-bool Sword1::SwordEngine::hasFeature(EngineFeature f) const {
-	return
-	    (f == kSupportsReturnToLauncher) ||
-	    (f == kSupportsSavingDuringRuntime) ||
-	    (f == kSupportsLoadingDuringRuntime);
-}
-
 PlainGameList SwordMetaEngine::getSupportedGames() const {
 	PlainGameList games;
 	games.push_back(sword1FullSettings);
@@ -248,133 +217,4 @@ DetectedGames SwordMetaEngine::detectGames(const Common::FSList &fslist) const {
 	return detectedGames;
 }
 
-Common::Error SwordMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
-	assert(engine);
-	*engine = new Sword1::SwordEngine(syst);
-	return Common::kNoError;
-}
-
-SaveStateList SwordMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	SaveStateList saveList;
-	char saveName[40];
-
-	Common::StringArray filenames = saveFileMan->listSavefiles("sword1.###");
-
-	int slotNum = 0;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				in->readUint32LE(); // header
-				in->read(saveName, 40);
-				saveList.push_back(SaveStateDescriptor(slotNum, saveName));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int SwordMetaEngine::getMaximumSaveSlot() const { return 999; }
-
-void SwordMetaEngine::removeSaveState(const char *target, int slot) const {
-	g_system->getSavefileManager()->removeSavefile(Common::String::format("sword1.%03d", slot));
-}
-
-SaveStateDescriptor SwordMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("sword1.%03d", slot);
-	char name[40];
-	uint32 playTime = 0;
-	byte versionSave;
-
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (in) {
-		in->skip(4);        // header
-		in->read(name, sizeof(name));
-		in->read(&versionSave, 1);      // version
-
-		SaveStateDescriptor desc(slot, name);
-
-		if (versionSave < 2) // These older version of the savegames used a flag to signal presence of thumbnail
-			in->skip(1);
-
-		if (Graphics::checkThumbnailHeader(*in)) {
-			Graphics::Surface *thumbnail;
-			if (!Graphics::loadThumbnail(*in, thumbnail)) {
-				delete in;
-				return SaveStateDescriptor();
-			}
-			desc.setThumbnail(thumbnail);
-		}
-
-		uint32 saveDate = in->readUint32BE();
-		uint16 saveTime = in->readUint16BE();
-		if (versionSave > 1) // Previous versions did not have playtime data
-			playTime = in->readUint32BE();
-
-		int day = (saveDate >> 24) & 0xFF;
-		int month = (saveDate >> 16) & 0xFF;
-		int year = saveDate & 0xFFFF;
-
-		desc.setSaveDate(year, month, day);
-
-		int hour = (saveTime >> 8) & 0xFF;
-		int minutes = saveTime & 0xFF;
-
-		desc.setSaveTime(hour, minutes);
-
-		if (versionSave > 1) {
-			desc.setPlayTime(playTime * 1000);
-		} else { //We have no playtime data
-			desc.setPlayTime(0);
-		}
-
-		delete in;
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(SWORD1)
-	REGISTER_PLUGIN_DYNAMIC(SWORD1, PLUGIN_TYPE_ENGINE, SwordMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(SWORD1, PLUGIN_TYPE_ENGINE, SwordMetaEngine);
-#endif
-
-namespace Sword1 {
-
-Common::Error SwordEngine::loadGameState(int slot) {
-	_systemVars.forceRestart = false;
-	_systemVars.controlPanelMode = CP_NORMAL;
-	_control->restoreGameFromFile(slot);
-	reinitialize();
-	_control->doRestore();
-	reinitRes();
-	return Common::kNoError;    // TODO: return success/failure
-}
-
-bool SwordEngine::canLoadGameStateCurrently() {
-	return (mouseIsActive() && !_control->isPanelShown()); // Disable GMM loading when game panel is shown
-}
-
-Common::Error SwordEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
-	_control->setSaveDescription(slot, desc.c_str());
-	_control->saveGameToFile(slot);
-	return Common::kNoError;    // TODO: return success/failure
-}
-
-bool SwordEngine::canSaveGameStateCurrently() {
-	return (mouseIsActive() && !_control->isPanelShown());
-}
-
-} // End of namespace Sword1
+REGISTER_PLUGIN_STATIC(SWORD1_DETECTION, PLUGIN_TYPE_METAENGINE, SwordMetaEngine);
diff --git a/engines/sword1/metaengine.cpp b/engines/sword1/metaengine.cpp
new file mode 100644
index 0000000000..437b27fa9e
--- /dev/null
+++ b/engines/sword1/metaengine.cpp
@@ -0,0 +1,197 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "sword1/sword1.h"
+#include "sword1/control.h"
+
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "graphics/thumbnail.h"
+#include "graphics/surface.h"
+
+#include "engines/metaengine.h"
+
+class SwordMetaEngineConnect : public MetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "sword1";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+    SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+
+	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
+};
+
+bool SwordMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+	    (f == kSupportsLoadingDuringStartup) ||
+	    (f == kSupportsDeleteSave) ||
+	    (f == kSavesSupportMetaInfo) ||
+	    (f == kSavesSupportThumbnail) ||
+	    (f == kSavesSupportCreationDate) ||
+	    (f == kSavesSupportPlayTime);
+}
+
+bool Sword1::SwordEngine::hasFeature(EngineFeature f) const {
+	return
+	    (f == kSupportsReturnToLauncher) ||
+	    (f == kSupportsSavingDuringRuntime) ||
+	    (f == kSupportsLoadingDuringRuntime);
+}
+
+Common::Error SwordMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+	assert(engine);
+	*engine = new Sword1::SwordEngine(syst);
+	return Common::kNoError;
+}
+
+SaveStateList SwordMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	SaveStateList saveList;
+	char saveName[40];
+
+	Common::StringArray filenames = saveFileMan->listSavefiles("sword1.###");
+
+	int slotNum = 0;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				in->readUint32LE(); // header
+				in->read(saveName, 40);
+				saveList.push_back(SaveStateDescriptor(slotNum, saveName));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int SwordMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+
+void SwordMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	g_system->getSavefileManager()->removeSavefile(Common::String::format("sword1.%03d", slot));
+}
+
+SaveStateDescriptor SwordMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("sword1.%03d", slot);
+	char name[40];
+	uint32 playTime = 0;
+	byte versionSave;
+
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (in) {
+		in->skip(4);        // header
+		in->read(name, sizeof(name));
+		in->read(&versionSave, 1);      // version
+
+		SaveStateDescriptor desc(slot, name);
+
+		if (versionSave < 2) // These older version of the savegames used a flag to signal presence of thumbnail
+			in->skip(1);
+
+		if (Graphics::checkThumbnailHeader(*in)) {
+			Graphics::Surface *thumbnail;
+			if (!Graphics::loadThumbnail(*in, thumbnail)) {
+				delete in;
+				return SaveStateDescriptor();
+			}
+			desc.setThumbnail(thumbnail);
+		}
+
+		uint32 saveDate = in->readUint32BE();
+		uint16 saveTime = in->readUint16BE();
+		if (versionSave > 1) // Previous versions did not have playtime data
+			playTime = in->readUint32BE();
+
+		int day = (saveDate >> 24) & 0xFF;
+		int month = (saveDate >> 16) & 0xFF;
+		int year = saveDate & 0xFFFF;
+
+		desc.setSaveDate(year, month, day);
+
+		int hour = (saveTime >> 8) & 0xFF;
+		int minutes = saveTime & 0xFF;
+
+		desc.setSaveTime(hour, minutes);
+
+		if (versionSave > 1) {
+			desc.setPlayTime(playTime * 1000);
+		} else { //We have no playtime data
+			desc.setPlayTime(0);
+		}
+
+		delete in;
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(SWORD1)
+	REGISTER_PLUGIN_DYNAMIC(SWORD1, PLUGIN_TYPE_ENGINE, SwordMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(SWORD1, PLUGIN_TYPE_ENGINE, SwordMetaEngineConnect);
+#endif
+
+namespace Sword1 {
+
+Common::Error SwordEngine::loadGameState(int slot) {
+	_systemVars.forceRestart = false;
+	_systemVars.controlPanelMode = CP_NORMAL;
+	_control->restoreGameFromFile(slot);
+	reinitialize();
+	_control->doRestore();
+	reinitRes();
+	return Common::kNoError;    // TODO: return success/failure
+}
+
+bool SwordEngine::canLoadGameStateCurrently() {
+	return (mouseIsActive() && !_control->isPanelShown()); // Disable GMM loading when game panel is shown
+}
+
+Common::Error SwordEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
+	_control->setSaveDescription(slot, desc.c_str());
+	_control->saveGameToFile(slot);
+	return Common::kNoError;    // TODO: return success/failure
+}
+
+bool SwordEngine::canSaveGameStateCurrently() {
+	return (mouseIsActive() && !_control->isPanelShown());
+}
+
+} // End of namespace Sword1
diff --git a/engines/sword1/module.mk b/engines/sword1/module.mk
index cd1b03ee7d..a2b38fc75a 100644
--- a/engines/sword1/module.mk
+++ b/engines/sword1/module.mk
@@ -5,11 +5,11 @@ MODULE_OBJS := \
 	console.o \
 	control.o \
 	debug.o \
-	detection.o \
 	eventman.o \
 	logic.o \
 	memman.o \
 	menu.o \
+	metaengine.o \
 	mouse.o \
 	music.o \
 	objectman.o \
@@ -28,3 +28,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: a21da27bf1e318b2e146f20dc5ef70230936e735
    https://github.com/scummvm/scummvm/commit/a21da27bf1e318b2e146f20dc5ef70230936e735
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SWORD2: Refactoring of code, split detection code, adapt to new plugins.

- Entire code was located in the main sword2.cpp file.
- Seperate detection-related code to detection.cpp
- Seperate other MetaEngineConnect related code to metaengine.cpp
- detection.h serves common code between the above files
- A enum value has been copied from sword2.h into the detection TU to avoid duplicate copy
- the detection.h has static function definitions for detecting games.
- This is because metaengine.cpp includes it & detection.cpp does as well.
- If we keep the methods as static, we can truely seperate out everything detection related.

Changed paths:
  A engines/sword2/detection.cpp
  A engines/sword2/detection_enums.h
  A engines/sword2/detection_internal.h
  A engines/sword2/metaengine.cpp
    configure
    engines/sword2/module.mk
    engines/sword2/sword2.cpp
    engines/sword2/sword2.h


diff --git a/configure b/configure
index e72d935a8c..01ac66a62d 100755
--- a/configure
+++ b/configure
@@ -6161,7 +6161,7 @@ EOF
 done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
-								  "SWORD1")
+								  "SWORD1" "SWORD2")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/sword2/detection.cpp b/engines/sword2/detection.cpp
new file mode 100644
index 0000000000..c7b7134155
--- /dev/null
+++ b/engines/sword2/detection.cpp
@@ -0,0 +1,104 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * Additional copyright for this file:
+ * Copyright (C) 1994-1998 Revolution Software Ltd.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+
+#include "common/translation.h"
+
+#include "engines/metaengine.h"
+
+#include "sword2/detection_enums.h"
+#include "sword2/detection_internal.h"
+
+static const ExtraGuiOption sword2ExtraGuiOption = {
+	_s("Show object labels"),
+	_s("Show labels for objects on mouse hover"),
+	"object_labels",
+	false
+};
+
+class Sword2MetaEngine : public MetaEngine {
+public:
+	const char *getEngineId() const override {
+		return "sword2";
+	}
+
+	const char *getName() const override {
+		return "Broken Sword II: The Smoking Mirror";
+	}
+	const char *getOriginalCopyright() const override {
+		return "Broken Sword II: The Smoking Mirror (C) Revolution";
+	}
+
+	PlainGameList getSupportedGames() const override;
+	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
+	PlainGameDescriptor findGame(const char *gameid) const override;
+	DetectedGames detectGames(const Common::FSList &fslist) const override;
+};
+
+PlainGameList Sword2MetaEngine::getSupportedGames() const {
+	const Sword2::GameSettings *g = Sword2::sword2_settings;
+	PlainGameList games;
+	while (g->gameid) {
+		games.push_back(PlainGameDescriptor::of(g->gameid, g->description));
+		g++;
+	}
+	return games;
+}
+
+const ExtraGuiOptions Sword2MetaEngine::getExtraGuiOptions(const Common::String &target) const {
+	ExtraGuiOptions options;
+	options.push_back(sword2ExtraGuiOption);
+	return options;
+}
+
+PlainGameDescriptor Sword2MetaEngine::findGame(const char *gameid) const {
+	const Sword2::GameSettings *g = Sword2::sword2_settings;
+	while (g->gameid) {
+		if (0 == scumm_stricmp(gameid, g->gameid))
+			break;
+		g++;
+	}
+	return PlainGameDescriptor::of(g->gameid, g->description);
+}
+
+DetectedGames Sword2MetaEngine::detectGames(const Common::FSList &fslist) const {
+	// The required game data files can be located in the game directory, or in
+	// a subdirectory called "clusters". In the latter case, we don't want to
+	// detect the game in that subdirectory, as this will detect the game twice
+	// when mass add is searching inside a directory. In this case, the first
+	// result (the game directory) will be correct, but the second result (the
+	// clusters subdirectory) will be wrong, as the optional speech, music and
+	// video data files will be ignored. Note that this fix will skip the game
+	// data files if the user has placed them inside a "clusters" subdirectory,
+	// or if he/she points ScummVM directly to the "clusters" directory of the
+	// game CD. Fixes bug #3049336.
+	if (!fslist.empty()) {
+		Common::String directory = fslist[0].getParent().getName();
+		if (directory.hasPrefixIgnoreCase("clusters") && directory.size() <= 9)
+			return DetectedGames();
+	}
+
+	return detectGamesImpl(fslist);
+}
+
+REGISTER_PLUGIN_STATIC(SWORD2_DETECTION, PLUGIN_TYPE_METAENGINE, Sword2MetaEngine);
diff --git a/engines/sword2/detection_enums.h b/engines/sword2/detection_enums.h
new file mode 100644
index 0000000000..b9266c3298
--- /dev/null
+++ b/engines/sword2/detection_enums.h
@@ -0,0 +1,37 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * Additional copyright for this file:
+ * Copyright (C) 1994-1998 Revolution Software Ltd.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+
+#ifndef SWORD2_DETECTION_ENUMS_H
+#define SWORD2_DETECTION_ENUMS_H
+
+namespace Sword2 {
+
+enum {
+	GF_DEMO	       = 1 << 0,
+	GF_SPANISHDEMO = 1 << 1
+};
+
+} // End of namespace Sword2
+
+#endif // SWORD2_DETECTION_ENUMS_H
diff --git a/engines/sword2/detection_internal.h b/engines/sword2/detection_internal.h
new file mode 100644
index 0000000000..02861d6fb0
--- /dev/null
+++ b/engines/sword2/detection_internal.h
@@ -0,0 +1,124 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * Additional copyright for this file:
+ * Copyright (C) 1994-1998 Revolution Software Ltd.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+
+#ifndef SWORD2_DETECTION_INTERNAL_H
+#define SWORD2_DETECTION_INTERNAL_H
+
+#include "engines/metaengine.h"
+#include "common/gui_options.h"
+#include "sword2/detection_enums.h"
+
+/**
+ * The contents of this file are helpful in detecting games, 
+ * as well as helping to create an instance of the game.
+ */
+namespace Sword2 {
+
+struct GameSettings {
+	const char *gameid;
+	const char *description;
+	uint32 features;
+	const char *detectname;
+};
+
+static const GameSettings sword2_settings[] = {
+	/* Broken Sword II */
+	{"sword2", "Broken Sword II: The Smoking Mirror", 0, "players.clu" },
+	{"sword2alt", "Broken Sword II: The Smoking Mirror (alt)", 0, "r2ctlns.ocx" },
+	{"sword2psx", "Broken Sword II: The Smoking Mirror (PlayStation)", 0, "screens.clu"},
+	{"sword2psxdemo", "Broken Sword II: The Smoking Mirror (PlayStation/Demo)", Sword2::GF_DEMO, "screens.clu"},
+	{"sword2demo", "Broken Sword II: The Smoking Mirror (Demo)", Sword2::GF_DEMO, "players.clu" },
+	{"sword2demo-es", "Broken Sword II: The Smoking Mirror (Spanish/Demo)", Sword2::GF_DEMO | Sword2::GF_SPANISHDEMO, "vielogo.tga" },
+	{NULL, NULL, 0, NULL}
+};
+
+} // End of namespace Sword2
+
+static bool isFullGame(const Common::FSList &fslist) {
+	Common::FSList::const_iterator file;
+
+	// We distinguish between the two versions by the presence of paris.clu
+	for (file = fslist.begin(); file != fslist.end(); ++file) {
+		if (!file->isDirectory()) {
+			if (file->getName().equalsIgnoreCase("paris.clu"))
+				return true;
+		}
+	}
+
+	return false;
+}
+
+static DetectedGames detectGamesImpl(const Common::FSList &fslist, bool recursion = false) {
+	DetectedGames detectedGames;
+	const Sword2::GameSettings *g;
+	Common::FSList::const_iterator file;
+	bool isFullVersion = isFullGame(fslist);
+
+	for (g = Sword2::sword2_settings; g->gameid; ++g) {
+		// Iterate over all files in the given directory
+		for (file = fslist.begin(); file != fslist.end(); ++file) {
+			if (file->isDirectory()) continue;
+
+			if (file->getName().equalsIgnoreCase(g->detectname)) {
+				// Make sure that the sword2 demo is not mixed up with the
+				// full version, since they use the same filename for detection
+				if ((g->features == Sword2::GF_DEMO && isFullVersion) ||
+					(g->features == 0 && !isFullVersion))
+					continue;
+
+				// Match found, add to list of candidates, then abort inner loop.
+				DetectedGame game = DetectedGame("sword2", g->gameid, g->description);
+				game.setGUIOptions(GUIO2(GUIO_NOMIDI, GUIO_NOASPECT));
+
+				detectedGames.push_back(game);
+				break;
+			}
+		}
+	}
+
+
+	if (detectedGames.empty() && !recursion) {
+		// Nothing found -- try to recurse into the 'clusters' subdirectory,
+		// present e.g. if the user copied the data straight from CD.
+		for (file = fslist.begin(); file != fslist.end(); ++file) {
+			if (file->isDirectory()) {
+				if (file->getName().equalsIgnoreCase("clusters")) {
+					Common::FSList recList;
+					if (file->getChildren(recList, Common::FSNode::kListAll)) {
+						DetectedGames recGames = detectGamesImpl(recList, true);
+						if (!recGames.empty()) {
+							detectedGames.push_back(recGames);
+							break;
+						}
+					}
+				}
+			}
+		}
+	}
+
+
+	return detectedGames;
+}
+
+#endif // SWORD2_DETECTION_INTERNAL_H
diff --git a/engines/sword2/metaengine.cpp b/engines/sword2/metaengine.cpp
new file mode 100644
index 0000000000..cee3d1011e
--- /dev/null
+++ b/engines/sword2/metaengine.cpp
@@ -0,0 +1,137 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * Additional copyright for this file:
+ * Copyright (C) 1994-1998 Revolution Software Ltd.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+
+#include "engines/metaengine.h"
+
+#include "common/config-manager.h"
+#include "common/events.h"
+#include "common/file.h"
+#include "common/fs.h"
+#include "common/gui_options.h"
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "sword2/sword2.h"
+#include "sword2/saveload.h"
+#include "sword2/detection_internal.h"
+
+class Sword2MetaEngineConnect : public MetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "sword2";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+    SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+
+	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
+};
+
+bool Sword2MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Sword2::Sword2Engine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsSubtitleOptions) ||
+		(f == kSupportsSavingDuringRuntime) ||
+		(f == kSupportsLoadingDuringRuntime);
+}
+
+SaveStateList Sword2MetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	char saveDesc[SAVE_DESCRIPTION_LEN];
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				in->readUint32LE();
+				in->read(saveDesc, SAVE_DESCRIPTION_LEN);
+				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int Sword2MetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+
+void Sword2MetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = target;
+	filename += Common::String::format(".%03d", slot);
+
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+Common::Error Sword2MetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+	assert(syst);
+	assert(engine);
+
+	Common::FSList fslist;
+	Common::FSNode dir(ConfMan.get("path"));
+	if (!dir.getChildren(fslist, Common::FSNode::kListAll)) {
+		return Common::kNoGameDataFoundError;
+	}
+
+	// Invoke the detector
+	Common::String gameid = ConfMan.get("gameid");
+	DetectedGames detectedGames = detectGamesImpl(fslist);
+
+	for (uint i = 0; i < detectedGames.size(); i++) {
+		if (detectedGames[i].gameId == gameid) {
+			*engine = new Sword2::Sword2Engine(syst);
+			return Common::kNoError;
+		}
+	}
+
+	return Common::kNoGameDataFoundError;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(SWORD2)
+	REGISTER_PLUGIN_DYNAMIC(SWORD2, PLUGIN_TYPE_ENGINE, Sword2MetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(SWORD2, PLUGIN_TYPE_ENGINE, Sword2MetaEngineConnect);
+#endif
diff --git a/engines/sword2/module.mk b/engines/sword2/module.mk
index bf586aefff..a7d3255788 100644
--- a/engines/sword2/module.mk
+++ b/engines/sword2/module.mk
@@ -16,6 +16,7 @@ MODULE_OBJS := \
 	maketext.o \
 	memory.o \
 	menu.o \
+	metaengine.o \
 	mouse.o \
 	music.o \
 	palette.o \
@@ -41,3 +42,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword2/sword2.cpp b/engines/sword2/sword2.cpp
index 396d094052..126c282202 100644
--- a/engines/sword2/sword2.cpp
+++ b/engines/sword2/sword2.cpp
@@ -25,16 +25,10 @@
 #include "base/plugins.h"
 
 #include "common/config-manager.h"
-#include "common/events.h"
-#include "common/file.h"
-#include "common/fs.h"
-#include "common/gui_options.h"
-#include "common/savefile.h"
-#include "common/system.h"
 #include "common/textconsole.h"
 #include "common/translation.h"
+#include "common/error.h"
 
-#include "engines/metaengine.h"
 #include "engines/util.h"
 
 #include "sword2/sword2.h"
@@ -50,263 +44,11 @@
 #include "sword2/router.h"
 #include "sword2/screen.h"
 #include "sword2/sound.h"
-#include "sword2/saveload.h"
 
 namespace Sword2 {
 
 Common::Platform Sword2Engine::_platform;
 
-struct GameSettings {
-	const char *gameid;
-	const char *description;
-	uint32 features;
-	const char *detectname;
-};
-
-static const GameSettings sword2_settings[] = {
-	/* Broken Sword II */
-	{"sword2", "Broken Sword II: The Smoking Mirror", 0, "players.clu" },
-	{"sword2alt", "Broken Sword II: The Smoking Mirror (alt)", 0, "r2ctlns.ocx" },
-	{"sword2psx", "Broken Sword II: The Smoking Mirror (PlayStation)", 0, "screens.clu"},
-	{"sword2psxdemo", "Broken Sword II: The Smoking Mirror (PlayStation/Demo)", Sword2::GF_DEMO, "screens.clu"},
-	{"sword2demo", "Broken Sword II: The Smoking Mirror (Demo)", Sword2::GF_DEMO, "players.clu" },
-	{"sword2demo-es", "Broken Sword II: The Smoking Mirror (Spanish/Demo)", Sword2::GF_DEMO | Sword2::GF_SPANISHDEMO, "vielogo.tga" },
-	{NULL, NULL, 0, NULL}
-};
-
-} // End of namespace Sword2
-
-static const ExtraGuiOption sword2ExtraGuiOption = {
-	_s("Show object labels"),
-	_s("Show labels for objects on mouse hover"),
-	"object_labels",
-	false
-};
-
-class Sword2MetaEngine : public MetaEngine {
-public:
-	const char *getEngineId() const override {
-		return "sword2";
-	}
-
-	const char *getName() const override {
-		return "Broken Sword II: The Smoking Mirror";
-	}
-	const char *getOriginalCopyright() const override {
-		return "Broken Sword II: The Smoking Mirror (C) Revolution";
-	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	PlainGameList getSupportedGames() const override;
-	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
-	PlainGameDescriptor findGame(const char *gameid) const override;
-	DetectedGames detectGames(const Common::FSList &fslist) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-
-	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
-};
-
-bool Sword2MetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Sword2::Sword2Engine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsSubtitleOptions) ||
-		(f == kSupportsSavingDuringRuntime) ||
-		(f == kSupportsLoadingDuringRuntime);
-}
-
-PlainGameList Sword2MetaEngine::getSupportedGames() const {
-	const Sword2::GameSettings *g = Sword2::sword2_settings;
-	PlainGameList games;
-	while (g->gameid) {
-		games.push_back(PlainGameDescriptor::of(g->gameid, g->description));
-		g++;
-	}
-	return games;
-}
-
-const ExtraGuiOptions Sword2MetaEngine::getExtraGuiOptions(const Common::String &target) const {
-	ExtraGuiOptions options;
-	options.push_back(sword2ExtraGuiOption);
-	return options;
-}
-
-PlainGameDescriptor Sword2MetaEngine::findGame(const char *gameid) const {
-	const Sword2::GameSettings *g = Sword2::sword2_settings;
-	while (g->gameid) {
-		if (0 == scumm_stricmp(gameid, g->gameid))
-			break;
-		g++;
-	}
-	return PlainGameDescriptor::of(g->gameid, g->description);
-}
-
-bool isFullGame(const Common::FSList &fslist) {
-	Common::FSList::const_iterator file;
-
-	// We distinguish between the two versions by the presence of paris.clu
-	for (file = fslist.begin(); file != fslist.end(); ++file) {
-		if (!file->isDirectory()) {
-			if (file->getName().equalsIgnoreCase("paris.clu"))
-				return true;
-		}
-	}
-
-	return false;
-}
-
-DetectedGames detectGamesImpl(const Common::FSList &fslist, bool recursion = false) {
-	DetectedGames detectedGames;
-	const Sword2::GameSettings *g;
-	Common::FSList::const_iterator file;
-	bool isFullVersion = isFullGame(fslist);
-
-	for (g = Sword2::sword2_settings; g->gameid; ++g) {
-		// Iterate over all files in the given directory
-		for (file = fslist.begin(); file != fslist.end(); ++file) {
-			if (file->isDirectory()) continue;
-
-			if (file->getName().equalsIgnoreCase(g->detectname)) {
-				// Make sure that the sword2 demo is not mixed up with the
-				// full version, since they use the same filename for detection
-				if ((g->features == Sword2::GF_DEMO && isFullVersion) ||
-					(g->features == 0 && !isFullVersion))
-					continue;
-
-				// Match found, add to list of candidates, then abort inner loop.
-				DetectedGame game = DetectedGame("sword2", g->gameid, g->description);
-				game.setGUIOptions(GUIO2(GUIO_NOMIDI, GUIO_NOASPECT));
-
-				detectedGames.push_back(game);
-				break;
-			}
-		}
-	}
-
-
-	if (detectedGames.empty() && !recursion) {
-		// Nothing found -- try to recurse into the 'clusters' subdirectory,
-		// present e.g. if the user copied the data straight from CD.
-		for (file = fslist.begin(); file != fslist.end(); ++file) {
-			if (file->isDirectory()) {
-				if (file->getName().equalsIgnoreCase("clusters")) {
-					Common::FSList recList;
-					if (file->getChildren(recList, Common::FSNode::kListAll)) {
-						DetectedGames recGames = detectGamesImpl(recList, true);
-						if (!recGames.empty()) {
-							detectedGames.push_back(recGames);
-							break;
-						}
-					}
-				}
-			}
-		}
-	}
-
-
-	return detectedGames;
-}
-
-DetectedGames Sword2MetaEngine::detectGames(const Common::FSList &fslist) const {
-	// The required game data files can be located in the game directory, or in
-	// a subdirectory called "clusters". In the latter case, we don't want to
-	// detect the game in that subdirectory, as this will detect the game twice
-	// when mass add is searching inside a directory. In this case, the first
-	// result (the game directory) will be correct, but the second result (the
-	// clusters subdirectory) will be wrong, as the optional speech, music and
-	// video data files will be ignored. Note that this fix will skip the game
-	// data files if the user has placed them inside a "clusters" subdirectory,
-	// or if he/she points ScummVM directly to the "clusters" directory of the
-	// game CD. Fixes bug #3049336.
-	if (!fslist.empty()) {
-		Common::String directory = fslist[0].getParent().getName();
-		if (directory.hasPrefixIgnoreCase("clusters") && directory.size() <= 9)
-			return DetectedGames();
-	}
-
-	return detectGamesImpl(fslist);
-}
-
-SaveStateList Sword2MetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	char saveDesc[SAVE_DESCRIPTION_LEN];
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				in->readUint32LE();
-				in->read(saveDesc, SAVE_DESCRIPTION_LEN);
-				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int Sword2MetaEngine::getMaximumSaveSlot() const { return 999; }
-
-void Sword2MetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = target;
-	filename += Common::String::format(".%03d", slot);
-
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-Common::Error Sword2MetaEngine::createInstance(OSystem *syst, Engine **engine) const {
-	assert(syst);
-	assert(engine);
-
-	Common::FSList fslist;
-	Common::FSNode dir(ConfMan.get("path"));
-	if (!dir.getChildren(fslist, Common::FSNode::kListAll)) {
-		return Common::kNoGameDataFoundError;
-	}
-
-	// Invoke the detector
-	Common::String gameid = ConfMan.get("gameid");
-	DetectedGames detectedGames = detectGames(fslist);
-
-	for (uint i = 0; i < detectedGames.size(); i++) {
-		if (detectedGames[i].gameId == gameid) {
-			*engine = new Sword2::Sword2Engine(syst);
-			return Common::kNoError;
-		}
-	}
-
-	return Common::kNoGameDataFoundError;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(SWORD2)
-	REGISTER_PLUGIN_DYNAMIC(SWORD2, PLUGIN_TYPE_ENGINE, Sword2MetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(SWORD2, PLUGIN_TYPE_ENGINE, Sword2MetaEngine);
-#endif
-
-namespace Sword2 {
-
 Sword2Engine::Sword2Engine(OSystem *syst) : Engine(syst), _rnd("sword2") {
 	// Add default file directories
 	const Common::FSNode gameDataDir(ConfMan.get("path"));
diff --git a/engines/sword2/sword2.h b/engines/sword2/sword2.h
index 681c8603db..044f0d4032 100644
--- a/engines/sword2/sword2.h
+++ b/engines/sword2/sword2.h
@@ -39,6 +39,7 @@
 #include "common/events.h"
 #include "common/util.h"
 #include "common/random.h"
+#include "sword2/detection_enums.h"
 
 #define	MAX_starts	100
 #define	MAX_description	100
@@ -55,11 +56,6 @@ class OSystem;
  */
 namespace Sword2 {
 
-enum {
-	GF_DEMO	       = 1 << 0,
-	GF_SPANISHDEMO = 1 << 1
-};
-
 class MemoryManager;
 class ResourceManager;
 class Sound;


Commit: 0880ab9357703c62c0a36178fe410323d24f0ffc
    https://github.com/scummvm/scummvm/commit/0880ab9357703c62c0a36178fe410323d24f0ffc
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SWORD25: Split detection code & adapt to new plugins.

Changed paths:
  A engines/sword25/detection_enums.h
  A engines/sword25/metaengine.cpp
    configure
    engines/sword25/detection.cpp
    engines/sword25/module.mk
    engines/sword25/sword25.h


diff --git a/configure b/configure
index 01ac66a62d..fcd78d328b 100755
--- a/configure
+++ b/configure
@@ -6161,7 +6161,7 @@ EOF
 done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
-								  "SWORD1" "SWORD2")
+								  "SWORD1" "SWORD2" "SWORD25")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/sword25/detection.cpp b/engines/sword25/detection.cpp
index 1bfaceac96..7825fa9977 100644
--- a/engines/sword25/detection.cpp
+++ b/engines/sword25/detection.cpp
@@ -24,13 +24,8 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "sword25/sword25.h"
+#include "sword25/detection_enums.h"
 #include "sword25/detection_tables.h"
-#include "sword25/kernel/persistenceservice.h"
-
-namespace Sword25 {
-uint32 Sword25Engine::getGameFlags() const { return _gameDescription->flags; }
-}
 
 static const PlainGameDescriptor sword25Game[] = {
 	{"sword25", "Broken Sword 2.5"},
@@ -69,53 +64,13 @@ public:
 		return "Broken Sword 2.5 (C) Malte Thiesen, Daniel Queteschiner and Michael Elsdorfer";
 	}
 
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
-	int getMaximumSaveSlot() const override { return Sword25::PersistenceService::getSlotCount(); }
-	SaveStateList listSaves(const char *target) const override;
 };
 
-bool Sword25MetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Sword25::Sword25Engine(syst, desc);
-	}
-	return desc != 0;
-}
-
-bool Sword25MetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves);
-}
-
 const ExtraGuiOptions Sword25MetaEngine::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	options.push_back(sword25ExtraGuiOption);
 	return options;
 }
 
-SaveStateList Sword25MetaEngine::listSaves(const char *target) const {
-	Common::String pattern = target;
-	pattern = pattern + ".###";
-	SaveStateList saveList;
-
-	Sword25::PersistenceService ps;
-	Sword25::setGameTarget(target);
-
-	ps.reloadSlots();
-
-	for (uint i = 0; i < ps.getSlotCount(); ++i) {
-		if (ps.isSlotOccupied(i)) {
-			Common::String desc = ps.getSavegameDescription(i);
-			saveList.push_back(SaveStateDescriptor(i, desc));
-		}
-	}
-
-	return saveList;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(SWORD25)
-	REGISTER_PLUGIN_DYNAMIC(SWORD25, PLUGIN_TYPE_ENGINE, Sword25MetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(SWORD25, PLUGIN_TYPE_ENGINE, Sword25MetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(SWORD25_DETECTION, PLUGIN_TYPE_METAENGINE, Sword25MetaEngine);
diff --git a/engines/sword25/detection_enums.h b/engines/sword25/detection_enums.h
new file mode 100644
index 0000000000..f1c51a4f6f
--- /dev/null
+++ b/engines/sword25/detection_enums.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+namespace Sword25 {
+
+enum GameFlags {
+	GF_EXTRACTED = 1 << 0
+};
+
+} // End of namespace Sword25
diff --git a/engines/sword25/metaengine.cpp b/engines/sword25/metaengine.cpp
new file mode 100644
index 0000000000..bc8affb9ac
--- /dev/null
+++ b/engines/sword25/metaengine.cpp
@@ -0,0 +1,83 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/advancedDetector.h"
+
+#include "sword25/sword25.h"
+#include "sword25/kernel/persistenceservice.h"
+
+namespace Sword25 {
+
+uint32 Sword25Engine::getGameFlags() const { return _gameDescription->flags; }
+
+} // End of namespace Sword25
+
+class Sword25MetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "sword25";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+    int getMaximumSaveSlot() const override { return Sword25::PersistenceService::getSlotCount(); }
+	SaveStateList listSaves(const char *target) const override;
+};
+
+bool Sword25MetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Sword25::Sword25Engine(syst, desc);
+	}
+	return desc != 0;
+}
+
+bool Sword25MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves);
+}
+
+SaveStateList Sword25MetaEngineConnect::listSaves(const char *target) const {
+	Common::String pattern = target;
+	pattern = pattern + ".###";
+	SaveStateList saveList;
+
+	Sword25::PersistenceService ps;
+	Sword25::setGameTarget(target);
+
+	ps.reloadSlots();
+
+	for (uint i = 0; i < ps.getSlotCount(); ++i) {
+		if (ps.isSlotOccupied(i)) {
+			Common::String desc = ps.getSavegameDescription(i);
+			saveList.push_back(SaveStateDescriptor(i, desc));
+		}
+	}
+
+	return saveList;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(SWORD25)
+	REGISTER_PLUGIN_DYNAMIC(SWORD25, PLUGIN_TYPE_ENGINE, Sword25MetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(SWORD25, PLUGIN_TYPE_ENGINE, Sword25MetaEngineConnect);
+#endif
diff --git a/engines/sword25/module.mk b/engines/sword25/module.mk
index 9577bc4537..def48b42ad 100644
--- a/engines/sword25/module.mk
+++ b/engines/sword25/module.mk
@@ -2,7 +2,7 @@ MODULE := engines/sword25
 
 MODULE_OBJS := \
 	console.o \
-	detection.o \
+	metaengine.o \
 	sword25.o \
 	fmv/movieplayer.o \
 	fmv/movieplayer_script.o \
@@ -62,3 +62,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword25/sword25.h b/engines/sword25/sword25.h
index d69d34adbd..ead4c28fcf 100644
--- a/engines/sword25/sword25.h
+++ b/engines/sword25/sword25.h
@@ -27,6 +27,7 @@
 #include "engines/engine.h"
 
 #include "sword25/console.h"
+#include "sword25/detection_enums.h"
 
 namespace Common {
 class Error;
@@ -58,10 +59,6 @@ enum {
 	kDebugResource = 1 << 2
 };
 
-enum GameFlags {
-	GF_EXTRACTED = 1 << 0
-};
-
 #define MESSAGE_BASIC 1
 #define MESSAGE_INTERMEDIATE 2
 #define MESSAGE_DETAILED 3


Commit: c2428c7a8fbde1247f78a36d69c4481395b2b7f2
    https://github.com/scummvm/scummvm/commit/c2428c7a8fbde1247f78a36d69c4481395b2b7f2
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ADL: Split detection code & adapt to new plugins.

Changed paths:
  A engines/adl/metaengine.cpp
    configure
    engines/adl/adl.h
    engines/adl/detection.cpp
    engines/adl/detection.h
    engines/adl/module.mk


diff --git a/configure b/configure
index fcd78d328b..7f1edc1c2e 100755
--- a/configure
+++ b/configure
@@ -6161,7 +6161,7 @@ EOF
 done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
-								  "SWORD1" "SWORD2" "SWORD25")
+								  "SWORD1" "SWORD2" "SWORD25" "ADL")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/adl/adl.h b/engines/adl/adl.h
index 00611cc9ad..5dd7f04737 100644
--- a/engines/adl/adl.h
+++ b/engines/adl/adl.h
@@ -34,6 +34,7 @@
 #include "common/scummsys.h"
 
 #include "engines/engine.h"
+#include "engines/advancedDetector.h"
 
 #include "audio/mixer.h"
 #include "audio/softsynth/pcspk.h"
diff --git a/engines/adl/detection.cpp b/engines/adl/detection.cpp
index 2ff63f0a38..e4f9a1a349 100644
--- a/engines/adl/detection.cpp
+++ b/engines/adl/detection.cpp
@@ -20,15 +20,11 @@
  *
  */
 
-#include "common/system.h"
-#include "common/savefile.h"
 #include "common/translation.h"
 #include "common/file.h"
 #include "common/md5.h"
 #include "common/debug.h"
 
-#include "graphics/thumbnail.h"
-
 #include "engines/advancedDetector.h"
 
 #include "adl/detection.h"
@@ -112,12 +108,6 @@ static const PlainGameDescriptor adlGames[] = {
 	{ 0, 0 }
 };
 
-struct AdlGameDescription {
-	ADGameDescription desc;
-	GameType gameType;
-	GameVersion version;
-};
-
 static const AdlGameDescription gameFileDescriptions[] = {
 	{ // Hi-Res Adventure #1: Mystery House - Apple II - Contains Simi Valley address
 		{
@@ -376,137 +366,11 @@ public:
 		return "Copyright (C) Sierra On-Line";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	int getMaximumSaveSlot() const override { return 'O' - 'A'; }
-	SaveStateList listSaves(const char *target) const override;
-	void removeSaveState(const char *target, int slot) const override;
 	ADDetectedGames detectGame(const Common::FSNode &parent, const FileMap &allFiles, Common::Language language, Common::Platform platform, const Common::String &extra) const override;
 
 	bool addFileProps(const FileMap &allFiles, Common::String fname, FilePropertiesMap &filePropsMap) const;
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
 };
 
-bool AdlMetaEngine::hasFeature(MetaEngineFeature f) const {
-	switch(f) {
-	case kSupportsListSaves:
-	case kSupportsLoadingDuringStartup:
-	case kSupportsDeleteSave:
-	case kSavesSupportMetaInfo:
-	case kSavesSupportThumbnail:
-	case kSavesSupportCreationDate:
-	case kSavesSupportPlayTime:
-	case kSimpleSavesNames:
-		return true;
-	default:
-		return false;
-	}
-}
-
-SaveStateDescriptor AdlMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.s%02d", target, slot);
-	Common::InSaveFile *inFile = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (!inFile)
-		return SaveStateDescriptor();
-
-	if (inFile->readUint32BE() != MKTAG('A', 'D', 'L', ':')) {
-		delete inFile;
-		return SaveStateDescriptor();
-	}
-
-	byte saveVersion = inFile->readByte();
-	if (saveVersion != SAVEGAME_VERSION) {
-		delete inFile;
-		return SaveStateDescriptor();
-	}
-
-	char name[SAVEGAME_NAME_LEN] = { };
-	inFile->read(name, sizeof(name) - 1);
-	inFile->readByte();
-
-	if (inFile->eos() || inFile->err()) {
-		delete inFile;
-		return SaveStateDescriptor();
-	}
-
-	SaveStateDescriptor sd(slot, name);
-
-	int year = inFile->readUint16BE();
-	int month = inFile->readByte();
-	int day = inFile->readByte();
-	sd.setSaveDate(year + 1900, month + 1, day);
-
-	int hour = inFile->readByte();
-	int minutes = inFile->readByte();
-	sd.setSaveTime(hour, minutes);
-
-	uint32 playTime = inFile->readUint32BE();
-	sd.setPlayTime(playTime);
-
-	if (inFile->eos() || inFile->err()) {
-		delete inFile;
-		return SaveStateDescriptor();
-	}
-
-	Graphics::Surface *thumbnail;
-	if (!Graphics::loadThumbnail(*inFile, thumbnail)) {
-		delete inFile;
-		return SaveStateDescriptor();
-	}
-	sd.setThumbnail(thumbnail);
-
-	delete inFile;
-	return sd;
-}
-
-SaveStateList AdlMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray files = saveFileMan->listSavefiles(Common::String(target) + ".s##");
-
-	SaveStateList saveList;
-
-	for (uint i = 0; i < files.size(); ++i) {
-		const Common::String &fileName = files[i];
-		Common::InSaveFile *inFile = saveFileMan->openForLoading(fileName);
-		if (!inFile) {
-			warning("Cannot open save file '%s'", fileName.c_str());
-			continue;
-		}
-
-		if (inFile->readUint32BE() != MKTAG('A', 'D', 'L', ':')) {
-			warning("No header found in '%s'", fileName.c_str());
-			delete inFile;
-			continue;
-		}
-
-		byte saveVersion = inFile->readByte();
-		if (saveVersion != SAVEGAME_VERSION) {
-			warning("Unsupported save game version %i found in '%s'", saveVersion, fileName.c_str());
-			delete inFile;
-			continue;
-		}
-
-		char name[SAVEGAME_NAME_LEN] = { };
-		inFile->read(name, sizeof(name) - 1);
-		delete inFile;
-
-		int slotNum = atoi(fileName.c_str() + fileName.size() - 2);
-		SaveStateDescriptor sd(slotNum, name);
-		saveList.push_back(sd);
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void AdlMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.s%02d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
 Common::String getDiskImageName(const AdlGameDescription &adlDesc, byte volume) {
 	const ADGameDescription &desc = adlDesc.desc;
 	for (uint i = 0; desc.filesDescriptions[i].fileName; ++i) {
@@ -655,53 +519,6 @@ ADDetectedGames AdlMetaEngine::detectGame(const Common::FSNode &parent, const Fi
 	return matched;
 }
 
-Engine *HiRes1Engine_create(OSystem *syst, const AdlGameDescription *gd);
-Engine *HiRes2Engine_create(OSystem *syst, const AdlGameDescription *gd);
-Engine *HiRes0Engine_create(OSystem *syst, const AdlGameDescription *gd);
-Engine *HiRes3Engine_create(OSystem *syst, const AdlGameDescription *gd);
-Engine *HiRes4Engine_create(OSystem *syst, const AdlGameDescription *gd);
-Engine *HiRes5Engine_create(OSystem *syst, const AdlGameDescription *gd);
-Engine *HiRes6Engine_create(OSystem *syst, const AdlGameDescription *gd);
-
-bool AdlMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
-	if (!gd)
-		return false;
-
-	const AdlGameDescription *adlGd = (const AdlGameDescription *)gd;
-
-	switch (adlGd->gameType) {
-	case GAME_TYPE_HIRES1:
-		*engine = HiRes1Engine_create(syst, adlGd);
-		break;
-	case GAME_TYPE_HIRES2:
-		*engine = HiRes2Engine_create(syst, adlGd);
-		break;
-	case GAME_TYPE_HIRES0:
-		*engine = HiRes0Engine_create(syst, adlGd);
-		break;
-	case GAME_TYPE_HIRES3:
-		*engine = HiRes3Engine_create(syst, adlGd);
-		break;
-	case GAME_TYPE_HIRES4:
-		*engine = HiRes4Engine_create(syst, adlGd);
-		break;
-	case GAME_TYPE_HIRES5:
-		*engine = HiRes5Engine_create(syst, adlGd);
-		break;
-	case GAME_TYPE_HIRES6:
-		*engine = HiRes6Engine_create(syst, adlGd);
-		break;
-	default:
-		error("Unknown GameType");
-	}
-
-	return true;
-}
-
 } // End of namespace Adl
 
-#if PLUGIN_ENABLED_DYNAMIC(ADL)
-	REGISTER_PLUGIN_DYNAMIC(ADL, PLUGIN_TYPE_ENGINE, Adl::AdlMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(ADL, PLUGIN_TYPE_ENGINE, Adl::AdlMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(ADL_DETECTION, PLUGIN_TYPE_METAENGINE, Adl::AdlMetaEngine);
diff --git a/engines/adl/detection.h b/engines/adl/detection.h
index bd009d2cb2..acc89bfb2c 100644
--- a/engines/adl/detection.h
+++ b/engines/adl/detection.h
@@ -62,7 +62,11 @@ enum GameVersion {
 	GAME_VER_HR1_PD
 };
 
-struct AdlGameDescription;
+struct AdlGameDescription {
+	ADGameDescription desc;
+	GameType gameType;
+	GameVersion version;
+};
 
 Common::String getDiskImageName(const AdlGameDescription &adlDesc, byte volume);
 GameType getGameType(const AdlGameDescription &desc);
diff --git a/engines/adl/metaengine.cpp b/engines/adl/metaengine.cpp
new file mode 100644
index 0000000000..08e8f18c14
--- /dev/null
+++ b/engines/adl/metaengine.cpp
@@ -0,0 +1,219 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/advancedDetector.h"
+
+#include "common/system.h"
+#include "common/savefile.h"
+
+#include "graphics/thumbnail.h"
+
+#include "adl/detection.h"
+
+
+namespace Adl {
+
+class AdlMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "adl";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	int getMaximumSaveSlot() const override { return 'O' - 'A'; }
+	SaveStateList listSaves(const char *target) const override;
+	void removeSaveState(const char *target, int slot) const override;
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
+};
+
+bool AdlMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	switch(f) {
+	case kSupportsListSaves:
+	case kSupportsLoadingDuringStartup:
+	case kSupportsDeleteSave:
+	case kSavesSupportMetaInfo:
+	case kSavesSupportThumbnail:
+	case kSavesSupportCreationDate:
+	case kSavesSupportPlayTime:
+	case kSimpleSavesNames:
+		return true;
+	default:
+		return false;
+	}
+}
+
+SaveStateDescriptor AdlMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.s%02d", target, slot);
+	Common::InSaveFile *inFile = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (!inFile)
+		return SaveStateDescriptor();
+
+	if (inFile->readUint32BE() != MKTAG('A', 'D', 'L', ':')) {
+		delete inFile;
+		return SaveStateDescriptor();
+	}
+
+	byte saveVersion = inFile->readByte();
+	if (saveVersion != SAVEGAME_VERSION) {
+		delete inFile;
+		return SaveStateDescriptor();
+	}
+
+	char name[SAVEGAME_NAME_LEN] = { };
+	inFile->read(name, sizeof(name) - 1);
+	inFile->readByte();
+
+	if (inFile->eos() || inFile->err()) {
+		delete inFile;
+		return SaveStateDescriptor();
+	}
+
+	SaveStateDescriptor sd(slot, name);
+
+	int year = inFile->readUint16BE();
+	int month = inFile->readByte();
+	int day = inFile->readByte();
+	sd.setSaveDate(year + 1900, month + 1, day);
+
+	int hour = inFile->readByte();
+	int minutes = inFile->readByte();
+	sd.setSaveTime(hour, minutes);
+
+	uint32 playTime = inFile->readUint32BE();
+	sd.setPlayTime(playTime);
+
+	if (inFile->eos() || inFile->err()) {
+		delete inFile;
+		return SaveStateDescriptor();
+	}
+
+	Graphics::Surface *thumbnail;
+	if (!Graphics::loadThumbnail(*inFile, thumbnail)) {
+		delete inFile;
+		return SaveStateDescriptor();
+	}
+	sd.setThumbnail(thumbnail);
+
+	delete inFile;
+	return sd;
+}
+
+SaveStateList AdlMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray files = saveFileMan->listSavefiles(Common::String(target) + ".s##");
+
+	SaveStateList saveList;
+
+	for (uint i = 0; i < files.size(); ++i) {
+		const Common::String &fileName = files[i];
+		Common::InSaveFile *inFile = saveFileMan->openForLoading(fileName);
+		if (!inFile) {
+			warning("Cannot open save file '%s'", fileName.c_str());
+			continue;
+		}
+
+		if (inFile->readUint32BE() != MKTAG('A', 'D', 'L', ':')) {
+			warning("No header found in '%s'", fileName.c_str());
+			delete inFile;
+			continue;
+		}
+
+		byte saveVersion = inFile->readByte();
+		if (saveVersion != SAVEGAME_VERSION) {
+			warning("Unsupported save game version %i found in '%s'", saveVersion, fileName.c_str());
+			delete inFile;
+			continue;
+		}
+
+		char name[SAVEGAME_NAME_LEN] = { };
+		inFile->read(name, sizeof(name) - 1);
+		delete inFile;
+
+		int slotNum = atoi(fileName.c_str() + fileName.size() - 2);
+		SaveStateDescriptor sd(slotNum, name);
+		saveList.push_back(sd);
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void AdlMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.s%02d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+Engine *HiRes1Engine_create(OSystem *syst, const AdlGameDescription *gd);
+Engine *HiRes2Engine_create(OSystem *syst, const AdlGameDescription *gd);
+Engine *HiRes0Engine_create(OSystem *syst, const AdlGameDescription *gd);
+Engine *HiRes3Engine_create(OSystem *syst, const AdlGameDescription *gd);
+Engine *HiRes4Engine_create(OSystem *syst, const AdlGameDescription *gd);
+Engine *HiRes5Engine_create(OSystem *syst, const AdlGameDescription *gd);
+Engine *HiRes6Engine_create(OSystem *syst, const AdlGameDescription *gd);
+
+bool AdlMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+	if (!gd)
+		return false;
+
+	const AdlGameDescription *adlGd = (const AdlGameDescription *)gd;
+
+	switch (adlGd->gameType) {
+	case GAME_TYPE_HIRES1:
+		*engine = HiRes1Engine_create(syst, adlGd);
+		break;
+	case GAME_TYPE_HIRES2:
+		*engine = HiRes2Engine_create(syst, adlGd);
+		break;
+	case GAME_TYPE_HIRES0:
+		*engine = HiRes0Engine_create(syst, adlGd);
+		break;
+	case GAME_TYPE_HIRES3:
+		*engine = HiRes3Engine_create(syst, adlGd);
+		break;
+	case GAME_TYPE_HIRES4:
+		*engine = HiRes4Engine_create(syst, adlGd);
+		break;
+	case GAME_TYPE_HIRES5:
+		*engine = HiRes5Engine_create(syst, adlGd);
+		break;
+	case GAME_TYPE_HIRES6:
+		*engine = HiRes6Engine_create(syst, adlGd);
+		break;
+	default:
+		error("Unknown GameType");
+	}
+
+	return true;
+}
+
+} // End of namespace Adl
+
+#if PLUGIN_ENABLED_DYNAMIC(ADL)
+	REGISTER_PLUGIN_DYNAMIC(ADL, PLUGIN_TYPE_ENGINE, Adl::AdlMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(ADL, PLUGIN_TYPE_ENGINE, Adl::AdlMetaEngineConnect);
+#endif
+
diff --git a/engines/adl/module.mk b/engines/adl/module.mk
index 450720654b..da28b7016b 100644
--- a/engines/adl/module.mk
+++ b/engines/adl/module.mk
@@ -7,7 +7,6 @@ MODULE_OBJS := \
 	adl_v4.o \
 	adl_v5.o \
 	console.o \
-	detection.o \
 	disk.o \
 	display.o \
 	display_a2.o \
@@ -16,6 +15,7 @@ MODULE_OBJS := \
 	hires4.o \
 	hires5.o \
 	hires6.o \
+	metaengine.o \
 	sound.o
 
 MODULE_DIRS += \
@@ -28,3 +28,13 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Only include if building as a dynamic module.
+# Static module already has the contents.
+ifeq ($(ENABLE_ADL), DYNAMIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/disk.o
+endif


Commit: d57f84205c33a4cf840d3ff1db5f83f5cfc561bd
    https://github.com/scummvm/scummvm/commit/d57f84205c33a4cf840d3ff1db5f83f5cfc561bd
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ADL: Seperate detection.h into two headers to improve dependencies

- Also makes it match other engine conventions.
- Engine files get a copy of detection_enums, while metaengine & detection.cpp get a copy of detection.h as well as detection_enums.

Changed paths:
  A engines/adl/detection_enums.h
    engines/adl/adl.cpp
    engines/adl/adl.h
    engines/adl/adl_v2.cpp
    engines/adl/detection.h
    engines/adl/hires4.cpp
    engines/adl/hires5.cpp


diff --git a/engines/adl/adl.cpp b/engines/adl/adl.cpp
index db70ac3d9a..d80ef63708 100644
--- a/engines/adl/adl.cpp
+++ b/engines/adl/adl.cpp
@@ -38,7 +38,6 @@
 
 #include "adl/adl.h"
 #include "adl/display_a2.h"
-#include "adl/detection.h"
 #include "adl/graphics.h"
 #include "adl/sound.h"
 
diff --git a/engines/adl/adl.h b/engines/adl/adl.h
index 5dd7f04737..fbc1a39fca 100644
--- a/engines/adl/adl.h
+++ b/engines/adl/adl.h
@@ -34,7 +34,6 @@
 #include "common/scummsys.h"
 
 #include "engines/engine.h"
-#include "engines/advancedDetector.h"
 
 #include "audio/mixer.h"
 #include "audio/softsynth/pcspk.h"
@@ -42,7 +41,7 @@
 #include "adl/console.h"
 #include "adl/disk.h"
 #include "adl/sound.h"
-#include "adl/detection.h"
+#include "adl/detection_enums.h"
 
 namespace Common {
 class ReadStream;
diff --git a/engines/adl/adl_v2.cpp b/engines/adl/adl_v2.cpp
index e30502eac9..d13455c353 100644
--- a/engines/adl/adl_v2.cpp
+++ b/engines/adl/adl_v2.cpp
@@ -26,7 +26,7 @@
 #include "adl/adl_v2.h"
 #include "adl/display.h"
 #include "adl/graphics.h"
-#include "adl/detection.h"
+#include "adl/detection_enums.h"
 
 namespace Adl {
 
diff --git a/engines/adl/detection.h b/engines/adl/detection.h
index acc89bfb2c..b1f84aaa89 100644
--- a/engines/adl/detection.h
+++ b/engines/adl/detection.h
@@ -25,54 +25,12 @@
 
 namespace Adl {
 
-#define SAVEGAME_VERSION 0
-#define SAVEGAME_NAME_LEN 32
-
-enum GameType {
-	GAME_TYPE_NONE,
-	GAME_TYPE_HIRES0,
-	GAME_TYPE_HIRES1,
-	GAME_TYPE_HIRES2,
-	GAME_TYPE_HIRES3,
-	GAME_TYPE_HIRES4,
-	GAME_TYPE_HIRES5,
-	GAME_TYPE_HIRES6
-};
-
-/*
- * ====== Mystery House supported versions ======
- * GAME_VER_HR1_SIMI:
- * - Instructions always shown (no prompt)
- * - Instructions contain Simi Valley address
- * - On-Line Systems title screen in main executable only and waits for key
- * GAME_VER_HR1_COARSE:
- * - Longer instructions, now containing Coarsegold address
- * - On-Line Systems title screen with instructions prompt
- * GAME_VER_HR1_PD:
- * - Public Domain disclaimer on startup
- * - Sierra On-Line title screen with instructions prompt
- *
- * Note: there are probably at least two or three more variants
- */
-
-enum GameVersion {
-	GAME_VER_NONE = 0,
-	GAME_VER_HR1_SIMI = 0,
-	GAME_VER_HR1_COARSE,
-	GAME_VER_HR1_PD
-};
-
 struct AdlGameDescription {
 	ADGameDescription desc;
 	GameType gameType;
 	GameVersion version;
 };
 
-Common::String getDiskImageName(const AdlGameDescription &adlDesc, byte volume);
-GameType getGameType(const AdlGameDescription &desc);
-GameVersion getGameVersion(const AdlGameDescription &desc);
-Common::Platform getPlatform(const AdlGameDescription &desc);
-
 } // End of namespace Adl
 
-#endif
+#endif // ADL_DETECTION_H
diff --git a/engines/adl/detection_enums.h b/engines/adl/detection_enums.h
new file mode 100644
index 0000000000..da5461c118
--- /dev/null
+++ b/engines/adl/detection_enums.h
@@ -0,0 +1,69 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef ADL_DETECTION_ENUMS_H
+#define ADL_DETECTION_ENUMS_H
+
+namespace Adl {
+
+#define SAVEGAME_VERSION 0
+#define SAVEGAME_NAME_LEN 32
+
+enum GameType {
+	GAME_TYPE_NONE,
+	GAME_TYPE_HIRES0,
+	GAME_TYPE_HIRES1,
+	GAME_TYPE_HIRES2,
+	GAME_TYPE_HIRES3,
+	GAME_TYPE_HIRES4,
+	GAME_TYPE_HIRES5,
+	GAME_TYPE_HIRES6
+};
+
+/*
+ * ====== Mystery House supported versions ======
+ * GAME_VER_HR1_SIMI:
+ * - Instructions always shown (no prompt)
+ * - Instructions contain Simi Valley address
+ * - On-Line Systems title screen in main executable only and waits for key
+ * GAME_VER_HR1_COARSE:
+ * - Longer instructions, now containing Coarsegold address
+ * - On-Line Systems title screen with instructions prompt
+ * GAME_VER_HR1_PD:
+ * - Public Domain disclaimer on startup
+ * - Sierra On-Line title screen with instructions prompt
+ *
+ * Note: there are probably at least two or three more variants
+ */
+
+enum GameVersion {
+	GAME_VER_NONE = 0,
+	GAME_VER_HR1_SIMI = 0,
+	GAME_VER_HR1_COARSE,
+	GAME_VER_HR1_PD
+};
+
+struct AdlGameDescription;
+
+} // End of namespace Adl
+
+#endif // ADL_DETECTION_ENUMS_H
diff --git a/engines/adl/hires4.cpp b/engines/adl/hires4.cpp
index 626e23b6d6..b251d44d97 100644
--- a/engines/adl/hires4.cpp
+++ b/engines/adl/hires4.cpp
@@ -29,7 +29,7 @@
 #include "common/memstream.h"
 
 #include "adl/adl_v3.h"
-#include "adl/detection.h"
+#include "adl/detection_enums.h"
 #include "adl/display_a2.h"
 #include "adl/graphics.h"
 #include "adl/disk.h"
diff --git a/engines/adl/hires5.cpp b/engines/adl/hires5.cpp
index 399671a1de..ef8749eedd 100644
--- a/engines/adl/hires5.cpp
+++ b/engines/adl/hires5.cpp
@@ -27,7 +27,7 @@
 #include "common/stream.h"
 
 #include "adl/adl_v4.h"
-#include "adl/detection.h"
+#include "adl/detection_enums.h"
 #include "adl/display_a2.h"
 #include "adl/graphics.h"
 #include "adl/disk.h"


Commit: 0a14511547963e06be17e4c4f16af9074e4bb7d7
    https://github.com/scummvm/scummvm/commit/0a14511547963e06be17e4c4f16af9074e4bb7d7
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ADL: Remove unneeded functions from detection & move to metaengine.

Changed paths:
  A engines/adl/disk_image_helpers.h
    engines/adl/adl.h
    engines/adl/detection.cpp
    engines/adl/metaengine.cpp


diff --git a/engines/adl/adl.h b/engines/adl/adl.h
index fbc1a39fca..1035b41028 100644
--- a/engines/adl/adl.h
+++ b/engines/adl/adl.h
@@ -54,6 +54,11 @@ class RandomSource;
 
 namespace Adl {
 
+Common::String getDiskImageName(const AdlGameDescription &adlDesc, byte volume);
+GameType getGameType(const AdlGameDescription &desc);
+GameVersion getGameVersion(const AdlGameDescription &desc);
+Common::Platform getPlatform(const AdlGameDescription &desc);
+
 class Console;
 class Display;
 class GraphicsMan;
diff --git a/engines/adl/detection.cpp b/engines/adl/detection.cpp
index e4f9a1a349..fcb5b2bcd4 100644
--- a/engines/adl/detection.cpp
+++ b/engines/adl/detection.cpp
@@ -27,8 +27,10 @@
 
 #include "engines/advancedDetector.h"
 
+#include "adl/detection_enums.h"
 #include "adl/detection.h"
 #include "adl/disk.h"
+#include "adl/disk_image_helpers.h"
 
 namespace Adl {
 
@@ -336,20 +338,6 @@ static const AdlGameDescription gameDiskDescriptions[] = {
 	{ AD_TABLE_END_MARKER, GAME_TYPE_NONE, GAME_VER_NONE }
 };
 
-struct DiskImageExt {
-	Common::Platform platform;
-	const char *extension;
-};
-
-const DiskImageExt diskImageExts[] = {
-	{ Common::kPlatformApple2, ".woz" },
-	{ Common::kPlatformApple2, ".nib" },
-	{ Common::kPlatformApple2, ".dsk" },
-	{ Common::kPlatformApple2, ".d13" },
-	{ Common::kPlatformAtari8Bit, ".xfd" },
-	{ Common::kPlatformDOS, ".img" }
-};
-
 class AdlMetaEngine : public AdvancedMetaEngine {
 public:
 	AdlMetaEngine() : AdvancedMetaEngine(gameFileDescriptions, sizeof(AdlGameDescription), adlGames, optionsList) { }
@@ -371,40 +359,6 @@ public:
 	bool addFileProps(const FileMap &allFiles, Common::String fname, FilePropertiesMap &filePropsMap) const;
 };
 
-Common::String getDiskImageName(const AdlGameDescription &adlDesc, byte volume) {
-	const ADGameDescription &desc = adlDesc.desc;
-	for (uint i = 0; desc.filesDescriptions[i].fileName; ++i) {
-		const ADGameFileDescription &fDesc = desc.filesDescriptions[i];
-
-		if (fDesc.fileType == volume) {
-			for (uint e = 0; e < ARRAYSIZE(diskImageExts); ++e) {
-				if (diskImageExts[e].platform == desc.platform) {
-					Common::String testFileName(fDesc.fileName);
-					testFileName += diskImageExts[e].extension;
-					if (Common::File::exists(testFileName))
-						return testFileName;
-				}
-			}
-
-			error("Failed to find disk image '%s'", fDesc.fileName);
-		}
-	}
-
-	error("Disk volume %d not found", volume);
-}
-
-GameType getGameType(const AdlGameDescription &adlDesc) {
-	return adlDesc.gameType;
-}
-
-GameVersion getGameVersion(const AdlGameDescription &adlDesc) {
-	return adlDesc.version;
-}
-
-Common::Platform getPlatform(const AdlGameDescription &adlDesc) {
-	return adlDesc.desc.platform;
-}
-
 bool AdlMetaEngine::addFileProps(const FileMap &allFiles, Common::String fname, FilePropertiesMap &filePropsMap) const {
 	if (filePropsMap.contains(fname))
 		return true;
diff --git a/engines/adl/disk_image_helpers.h b/engines/adl/disk_image_helpers.h
new file mode 100644
index 0000000000..5656b9ffec
--- /dev/null
+++ b/engines/adl/disk_image_helpers.h
@@ -0,0 +1,44 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef ADL_DISK_IMAGE_HELPERS_H
+#define ADL_DISK_IMAGE_HELPERS_H
+
+namespace Adl {
+
+struct DiskImageExt {
+	Common::Platform platform;
+	const char *extension;
+};
+
+const DiskImageExt diskImageExts[] = {
+	{ Common::kPlatformApple2, ".woz" },
+	{ Common::kPlatformApple2, ".nib" },
+	{ Common::kPlatformApple2, ".dsk" },
+	{ Common::kPlatformApple2, ".d13" },
+	{ Common::kPlatformAtari8Bit, ".xfd" },
+	{ Common::kPlatformDOS, ".img" }
+};
+
+} // End of namespace Adl
+
+#endif // ADL_DISK_IMAGE_HELPERS_H
diff --git a/engines/adl/metaengine.cpp b/engines/adl/metaengine.cpp
index 08e8f18c14..a7dd3cdf51 100644
--- a/engines/adl/metaengine.cpp
+++ b/engines/adl/metaengine.cpp
@@ -24,14 +24,50 @@
 
 #include "common/system.h"
 #include "common/savefile.h"
+#include "common/file.h"
 
 #include "graphics/thumbnail.h"
 
+#include "adl/detection_enums.h"
 #include "adl/detection.h"
-
+#include "adl/disk_image_helpers.h"
 
 namespace Adl {
 
+Common::String getDiskImageName(const AdlGameDescription &adlDesc, byte volume) {
+	const ADGameDescription &desc = adlDesc.desc;
+	for (uint i = 0; desc.filesDescriptions[i].fileName; ++i) {
+		const ADGameFileDescription &fDesc = desc.filesDescriptions[i];
+
+		if (fDesc.fileType == volume) {
+			for (uint e = 0; e < ARRAYSIZE(diskImageExts); ++e) {
+				if (diskImageExts[e].platform == desc.platform) {
+					Common::String testFileName(fDesc.fileName);
+					testFileName += diskImageExts[e].extension;
+					if (Common::File::exists(testFileName))
+						return testFileName;
+				}
+			}
+
+			error("Failed to find disk image '%s'", fDesc.fileName);
+		}
+	}
+
+	error("Disk volume %d not found", volume);
+}
+
+GameType getGameType(const AdlGameDescription &adlDesc) {
+	return adlDesc.gameType;
+}
+
+GameVersion getGameVersion(const AdlGameDescription &adlDesc) {
+	return adlDesc.version;
+}
+
+Common::Platform getPlatform(const AdlGameDescription &adlDesc) {
+	return adlDesc.desc.platform;
+}
+
 class AdlMetaEngineConnect : public AdvancedMetaEngineConnect {
 public:
     const char *getName() const override {


Commit: 4b377af8c6780a939f40ec988341d118f474798b
    https://github.com/scummvm/scummvm/commit/4b377af8c6780a939f40ec988341d118f474798b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
QUEEN: Split detection code & adapt to new plugins.

Changed paths:
  A engines/queen/detection.h
  A engines/queen/metaengine.cpp
    configure
    engines/queen/detection.cpp
    engines/queen/module.mk


diff --git a/configure b/configure
index 7f1edc1c2e..4d7ff8de06 100755
--- a/configure
+++ b/configure
@@ -6161,7 +6161,7 @@ EOF
 done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
-								  "SWORD1" "SWORD2" "SWORD25" "ADL")
+								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/queen/detection.cpp b/engines/queen/detection.cpp
index 44fee6b8ec..ccafc68a47 100644
--- a/engines/queen/detection.cpp
+++ b/engines/queen/detection.cpp
@@ -24,24 +24,13 @@
 
 #include "engines/advancedDetector.h"
 
-#include "common/config-manager.h"
-#include "common/file.h"
 #include "common/gui_options.h"
-#include "common/savefile.h"
-#include "common/system.h"
+#include "common/file.h"
 #include "common/translation.h"
 
-#include "queen/queen.h"
+#include "queen/detection.h"
 #include "queen/resource.h"
 
-namespace Queen {
-
-struct QueenGameDescription {
-	ADGameDescription desc;
-};
-
-} // End of namespace Queen
-
 static const PlainGameDescriptor queenGames[] = {
 	{"queen", "Flight of the Amazon Queen"},
 	{0, 0}
@@ -496,23 +485,9 @@ public:
 		return "Flight of the Amazon Queen (C) John Passfield and Steve Stamatiadis";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override { return 99; }
-	void removeSaveState(const char *target, int slot) const override;
-	int getAutosaveSlot() const override { return 99; }
-
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
 };
 
-bool QueenMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave);
-}
-
 ADDetectedGame QueenMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	static ADGameDescription desc;
 
@@ -557,53 +532,4 @@ ADDetectedGame QueenMetaEngine::fallbackDetect(const FileMap &allFiles, const Co
 	return ADDetectedGame();
 }
 
-SaveStateList QueenMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	char saveDesc[32];
-	Common::String pattern("queen.s##");
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-
-		if (slotNum >= 0 && slotNum <= 99) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				for (int i = 0; i < 4; i++)
-					in->readUint32BE();
-				in->read(saveDesc, 32);
-				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void QueenMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("queen.s%02d", slot);
-
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-bool QueenMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Queen::QueenGameDescription *gd = (const Queen::QueenGameDescription *)desc;
-
-	if (gd)
-		*engine = new Queen::QueenEngine(syst); //FIXME , gd);
-
-	return (gd != 0);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(QUEEN)
-	REGISTER_PLUGIN_DYNAMIC(QUEEN, PLUGIN_TYPE_ENGINE, QueenMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(QUEEN, PLUGIN_TYPE_ENGINE, QueenMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(QUEEN_DETECTION, PLUGIN_TYPE_METAENGINE, QueenMetaEngine);
diff --git a/engines/queen/detection.h b/engines/queen/detection.h
new file mode 100644
index 0000000000..40820312ee
--- /dev/null
+++ b/engines/queen/detection.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Queen {
+
+struct QueenGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Queen
diff --git a/engines/queen/metaengine.cpp b/engines/queen/metaengine.cpp
new file mode 100644
index 0000000000..8cdbbecda3
--- /dev/null
+++ b/engines/queen/metaengine.cpp
@@ -0,0 +1,103 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/advancedDetector.h"
+
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "queen/queen.h"
+#include "queen/resource.h"
+#include "queen/detection.h"
+
+class QueenMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "queen";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override { return 99; }
+	void removeSaveState(const char *target, int slot) const override;
+	int getAutosaveSlot() const override { return 99; }
+};
+
+bool QueenMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave);
+}
+
+SaveStateList QueenMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	char saveDesc[32];
+	Common::String pattern("queen.s##");
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+
+		if (slotNum >= 0 && slotNum <= 99) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				for (int i = 0; i < 4; i++)
+					in->readUint32BE();
+				in->read(saveDesc, 32);
+				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void QueenMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("queen.s%02d", slot);
+
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+bool QueenMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Queen::QueenGameDescription *gd = (const Queen::QueenGameDescription *)desc;
+
+	if (gd)
+		*engine = new Queen::QueenEngine(syst); //FIXME , gd);
+
+	return (gd != 0);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(QUEEN)
+	REGISTER_PLUGIN_DYNAMIC(QUEEN, PLUGIN_TYPE_ENGINE, QueenMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(QUEEN, PLUGIN_TYPE_ENGINE, QueenMetaEngineConnect);
+#endif
+
diff --git a/engines/queen/module.mk b/engines/queen/module.mk
index 8ba49a301d..0b5b72b7fb 100644
--- a/engines/queen/module.mk
+++ b/engines/queen/module.mk
@@ -6,13 +6,13 @@ MODULE_OBJS := \
 	credits.o \
 	cutaway.o \
 	debug.o \
-	detection.o \
 	display.o \
 	graphics.o \
 	grid.o \
 	input.o \
 	journal.o \
 	logic.o \
+	metaengine.o \
 	midiadlib.o \
 	music.o \
 	musicdata.o \
@@ -31,3 +31,14 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objecs
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Only include if building as a dynamic module.
+# Static module already has the contents.
+ifeq ($(ENABLE_QUEEN), DYNAMIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/resource.o
+DETECT_OBJS += $(MODULE)/restables.o
+endif


Commit: 0d61c5bd4ba7c423e00f5115955f8c71887ad967
    https://github.com/scummvm/scummvm/commit/0d61c5bd4ba7c423e00f5115955f8c71887ad967
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CGE: Split detection code & adapt to new plugins.

Changed paths:
  A engines/cge/metaengine.cpp
    configure
    engines/cge/detection.cpp
    engines/cge/module.mk


diff --git a/configure b/configure
index 4d7ff8de06..96b7794e03 100755
--- a/configure
+++ b/configure
@@ -6161,7 +6161,7 @@ EOF
 done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
-								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN")
+								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/cge/detection.cpp b/engines/cge/detection.cpp
index 5769c81c95..92288b2e59 100644
--- a/engines/cge/detection.cpp
+++ b/engines/cge/detection.cpp
@@ -20,14 +20,12 @@
  *
  */
 
-#include "common/config-manager.h"
+#include "base/plugins.h"
+
 #include "engines/advancedDetector.h"
-#include "common/savefile.h"
-#include "common/system.h"
+
 #include "common/translation.h"
-#include "base/plugins.h"
-#include "graphics/thumbnail.h"
-#include "cge/cge.h"
+
 #include "cge/fileio.h"
 
 namespace CGE {
@@ -140,12 +138,6 @@ public:
 	}
 
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
 static ADGameDescription s_fallbackDesc = {
@@ -183,122 +175,6 @@ ADDetectedGame CGEMetaEngine::fallbackDetect(const FileMap &allFiles, const Comm
 	return game;
 }
 
-bool CGEMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-void CGEMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-int CGEMetaEngine::getMaximumSaveSlot() const {
-	return 99;
-}
-
-SaveStateList CGEMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(filename->c_str() + filename->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 99) {
-
-			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
-			if (file) {
-				CGE::SavegameHeader header;
-
-				// Check to see if it's a ScummVM savegame or not
-				char buffer[kSavegameStrSize + 1];
-				file->read(buffer, kSavegameStrSize + 1);
-
-				if (!strncmp(buffer, CGE::savegameStr, kSavegameStrSize + 1)) {
-					// Valid savegame
-					if (CGE::CGEEngine::readSavegameHeader(file, header)) {
-						saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
-					}
-				} else {
-					// Must be an original format savegame
-					saveList.push_back(SaveStateDescriptor(slotNum, "Unknown"));
-				}
-
-				delete file;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor CGEMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (f) {
-		CGE::SavegameHeader header;
-
-		// Check to see if it's a ScummVM savegame or not
-		char buffer[kSavegameStrSize + 1];
-		f->read(buffer, kSavegameStrSize + 1);
-
-		bool hasHeader = !strncmp(buffer, CGE::savegameStr, kSavegameStrSize + 1) &&
-			CGE::CGEEngine::readSavegameHeader(f, header, false);
-		delete f;
-
-		if (!hasHeader) {
-			// Original savegame perhaps?
-			SaveStateDescriptor desc(slot, "Unknown");
-			return desc;
-		} else {
-			// Create the return descriptor
-			SaveStateDescriptor desc(slot, header.saveName);
-			desc.setThumbnail(header.thumbnail);
-			desc.setSaveDate(header.saveYear, header.saveMonth, header.saveDay);
-			desc.setSaveTime(header.saveHour, header.saveMinutes);
-
-			if (header.playTime) {
-				desc.setPlayTime(header.playTime * 1000);
-			}
-
-			// Slot 0 is used for the 'automatic save on exit' save in Soltys, thus
-			// we prevent it from being deleted or overwritten by accident.
-			desc.setDeletableFlag(slot != 0);
-			desc.setWriteProtectedFlag(slot == 0);
-
-			return desc;
-		}
-	}
-
-	return SaveStateDescriptor();
-}
-
-bool CGEMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new CGE::CGEEngine(syst, desc);
-	}
-	return desc != 0;
-}
 } // End of namespace CGE
 
-#if PLUGIN_ENABLED_DYNAMIC(CGE)
-REGISTER_PLUGIN_DYNAMIC(CGE, PLUGIN_TYPE_ENGINE, CGE::CGEMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(CGE, PLUGIN_TYPE_ENGINE, CGE::CGEMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(CGE_DETECTION, PLUGIN_TYPE_METAENGINE, CGE::CGEMetaEngine);
diff --git a/engines/cge/metaengine.cpp b/engines/cge/metaengine.cpp
new file mode 100644
index 0000000000..b080e1b1ff
--- /dev/null
+++ b/engines/cge/metaengine.cpp
@@ -0,0 +1,169 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "graphics/thumbnail.h"
+
+#include "engines/advancedDetector.h"
+
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "cge/cge.h"
+
+namespace CGE {
+
+class CGEMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "cge";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool CGEMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+void CGEMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+int CGEMetaEngineConnect::getMaximumSaveSlot() const {
+	return 99;
+}
+
+SaveStateList CGEMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(filename->c_str() + filename->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 99) {
+
+			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
+			if (file) {
+				CGE::SavegameHeader header;
+
+				// Check to see if it's a ScummVM savegame or not
+				char buffer[kSavegameStrSize + 1];
+				file->read(buffer, kSavegameStrSize + 1);
+
+				if (!strncmp(buffer, CGE::savegameStr, kSavegameStrSize + 1)) {
+					// Valid savegame
+					if (CGE::CGEEngine::readSavegameHeader(file, header)) {
+						saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
+					}
+				} else {
+					// Must be an original format savegame
+					saveList.push_back(SaveStateDescriptor(slotNum, "Unknown"));
+				}
+
+				delete file;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor CGEMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (f) {
+		CGE::SavegameHeader header;
+
+		// Check to see if it's a ScummVM savegame or not
+		char buffer[kSavegameStrSize + 1];
+		f->read(buffer, kSavegameStrSize + 1);
+
+		bool hasHeader = !strncmp(buffer, CGE::savegameStr, kSavegameStrSize + 1) &&
+			CGE::CGEEngine::readSavegameHeader(f, header, false);
+		delete f;
+
+		if (!hasHeader) {
+			// Original savegame perhaps?
+			SaveStateDescriptor desc(slot, "Unknown");
+			return desc;
+		} else {
+			// Create the return descriptor
+			SaveStateDescriptor desc(slot, header.saveName);
+			desc.setThumbnail(header.thumbnail);
+			desc.setSaveDate(header.saveYear, header.saveMonth, header.saveDay);
+			desc.setSaveTime(header.saveHour, header.saveMinutes);
+
+			if (header.playTime) {
+				desc.setPlayTime(header.playTime * 1000);
+			}
+
+			// Slot 0 is used for the 'automatic save on exit' save in Soltys, thus
+			// we prevent it from being deleted or overwritten by accident.
+			desc.setDeletableFlag(slot != 0);
+			desc.setWriteProtectedFlag(slot == 0);
+
+			return desc;
+		}
+	}
+
+	return SaveStateDescriptor();
+}
+
+bool CGEMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new CGE::CGEEngine(syst, desc);
+	}
+	return desc != 0;
+}
+
+} // End of namespace CGE
+
+#if PLUGIN_ENABLED_DYNAMIC(CGE)
+REGISTER_PLUGIN_DYNAMIC(CGE, PLUGIN_TYPE_ENGINE, CGE::CGEMetaEngineConnect);
+#else
+REGISTER_PLUGIN_STATIC(CGE, PLUGIN_TYPE_ENGINE, CGE::CGEMetaEngineConnect);
+#endif
diff --git a/engines/cge/module.mk b/engines/cge/module.mk
index 1fa406f6c8..407e0efa89 100644
--- a/engines/cge/module.mk
+++ b/engines/cge/module.mk
@@ -5,10 +5,10 @@ MODULE_OBJS := \
 	cge.o \
 	cge_main.o \
 	console.o \
-	detection.o \
 	events.o \
 	fileio.o \
 	game.o \
+	metaengine.o \
 	snail.o \
 	sound.o \
 	talk.o \
@@ -28,3 +28,12 @@ endif
 # Include common rules
 include $(srcdir)/rules.mk
 
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Only include if building as a dynamic module.
+# Static module already has the contents.
+ifeq ($(ENABLE_CGE), DYNAMIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/fileio.o
+endif


Commit: 4ef8eab54577c63f25f26bbf476a1a9e8edcf4b7
    https://github.com/scummvm/scummvm/commit/4ef8eab54577c63f25f26bbf476a1a9e8edcf4b7
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CGE2: Split detection code & adapt to new plugins.

Changed paths:
  A engines/cge2/metaengine.cpp
    configure
    engines/cge2/detection.cpp
    engines/cge2/module.mk


diff --git a/configure b/configure
index 96b7794e03..6be89d5cd8 100755
--- a/configure
+++ b/configure
@@ -6161,7 +6161,7 @@ EOF
 done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
-								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE")
+								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/cge2/detection.cpp b/engines/cge2/detection.cpp
index 58081622ac..9807efad9b 100644
--- a/engines/cge2/detection.cpp
+++ b/engines/cge2/detection.cpp
@@ -25,11 +25,9 @@
  * Copyright (c) 1994-1997 Janusz B. Wisniewski and L.K. Avalon
  */
 
-#include "cge2/cge2.h"
-#include "cge2/fileio.h"
 #include "engines/advancedDetector.h"
 #include "common/translation.h"
-#include "graphics/surface.h"
+#include "cge2/fileio.h"
 
 namespace CGE2 {
 
@@ -136,12 +134,6 @@ public:
 	}
 
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
 static ADGameDescription s_fallbackDesc = {
@@ -181,123 +173,6 @@ ADDetectedGame CGE2MetaEngine::fallbackDetect(const FileMap &allFiles, const Com
 	return game;
 }
 
-bool CGE2MetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc)
-		*engine = new CGE2::CGE2Engine(syst, desc);
-
-	return desc != 0;
-}
-
-bool CGE2MetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSimpleSavesNames);
-}
-
-int CGE2MetaEngine::getMaximumSaveSlot() const {
-	return 99;
-}
-
-SaveStateList CGE2MetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(filename->c_str() + filename->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 99) {
-
-			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
-			if (file) {
-				CGE2::SavegameHeader header;
-
-				// Check to see if it's a ScummVM savegame or not
-				char buffer[kSavegameStrSize + 1];
-				file->read(buffer, kSavegameStrSize + 1);
-
-				if (!strncmp(buffer, kSavegameStr, kSavegameStrSize + 1)) {
-					// Valid savegame
-					if (CGE2::CGE2Engine::readSavegameHeader(file, header)) {
-						saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
-					}
-				} else {
-					// Must be an original format savegame
-					saveList.push_back(SaveStateDescriptor(slotNum, "Unknown"));
-				}
-
-				delete file;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor CGE2MetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (f) {
-		CGE2::SavegameHeader header;
-
-		// Check to see if it's a ScummVM savegame or not
-		char buffer[kSavegameStrSize + 1];
-		f->read(buffer, kSavegameStrSize + 1);
-
-		bool hasHeader = !strncmp(buffer, kSavegameStr, kSavegameStrSize + 1) &&
-			CGE2::CGE2Engine::readSavegameHeader(f, header, false);
-		delete f;
-
-		if (!hasHeader) {
-			// Original savegame perhaps?
-			SaveStateDescriptor desc(slot, "Unknown");
-			return desc;
-		} else {
-			// Create the return descriptor
-			SaveStateDescriptor desc(slot, header.saveName);
-			desc.setThumbnail(header.thumbnail);
-			desc.setSaveDate(header.saveYear, header.saveMonth, header.saveDay);
-			desc.setSaveTime(header.saveHour, header.saveMinutes);
-
-			if (header.playTime) {
-				desc.setPlayTime(header.playTime * 1000);
-			}
-
-			// Slot 0 is used for the 'automatic save on exit' save in Soltys, thus
-			// we prevent it from being deleted or overwritten by accident.
-			desc.setDeletableFlag(slot != 0);
-			desc.setWriteProtectedFlag(slot == 0);
-
-			return desc;
-		}
-	}
-
-	return SaveStateDescriptor();
-}
-
-void CGE2MetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
 } // End of namespace CGE2
 
-#if PLUGIN_ENABLED_DYNAMIC(CGE2)
-	REGISTER_PLUGIN_DYNAMIC(CGE2, PLUGIN_TYPE_ENGINE, CGE2::CGE2MetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(CGE2, PLUGIN_TYPE_ENGINE, CGE2::CGE2MetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(CGE2_DETECTION, PLUGIN_TYPE_METAENGINE, CGE2::CGE2MetaEngine);
diff --git a/engines/cge2/metaengine.cpp b/engines/cge2/metaengine.cpp
new file mode 100644
index 0000000000..31b2f63444
--- /dev/null
+++ b/engines/cge2/metaengine.cpp
@@ -0,0 +1,169 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+/*
+ * This code is based on original Sfinx source code
+ * Copyright (c) 1994-1997 Janusz B. Wisniewski and L.K. Avalon
+ */
+
+#include "engines/advancedDetector.h"
+
+#include "graphics/surface.h"
+
+#include "cge2/cge2.h"
+
+namespace CGE2 {
+
+class CGE2MetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "cge2";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool CGE2MetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc)
+		*engine = new CGE2::CGE2Engine(syst, desc);
+
+	return desc != 0;
+}
+
+bool CGE2MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSimpleSavesNames);
+}
+
+int CGE2MetaEngineConnect::getMaximumSaveSlot() const {
+	return 99;
+}
+
+SaveStateList CGE2MetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(filename->c_str() + filename->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 99) {
+
+			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
+			if (file) {
+				CGE2::SavegameHeader header;
+
+				// Check to see if it's a ScummVM savegame or not
+				char buffer[kSavegameStrSize + 1];
+				file->read(buffer, kSavegameStrSize + 1);
+
+				if (!strncmp(buffer, kSavegameStr, kSavegameStrSize + 1)) {
+					// Valid savegame
+					if (CGE2::CGE2Engine::readSavegameHeader(file, header)) {
+						saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
+					}
+				} else {
+					// Must be an original format savegame
+					saveList.push_back(SaveStateDescriptor(slotNum, "Unknown"));
+				}
+
+				delete file;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor CGE2MetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (f) {
+		CGE2::SavegameHeader header;
+
+		// Check to see if it's a ScummVM savegame or not
+		char buffer[kSavegameStrSize + 1];
+		f->read(buffer, kSavegameStrSize + 1);
+
+		bool hasHeader = !strncmp(buffer, kSavegameStr, kSavegameStrSize + 1) &&
+			CGE2::CGE2Engine::readSavegameHeader(f, header, false);
+		delete f;
+
+		if (!hasHeader) {
+			// Original savegame perhaps?
+			SaveStateDescriptor desc(slot, "Unknown");
+			return desc;
+		} else {
+			// Create the return descriptor
+			SaveStateDescriptor desc(slot, header.saveName);
+			desc.setThumbnail(header.thumbnail);
+			desc.setSaveDate(header.saveYear, header.saveMonth, header.saveDay);
+			desc.setSaveTime(header.saveHour, header.saveMinutes);
+
+			if (header.playTime) {
+				desc.setPlayTime(header.playTime * 1000);
+			}
+
+			// Slot 0 is used for the 'automatic save on exit' save in Soltys, thus
+			// we prevent it from being deleted or overwritten by accident.
+			desc.setDeletableFlag(slot != 0);
+			desc.setWriteProtectedFlag(slot == 0);
+
+			return desc;
+		}
+	}
+
+	return SaveStateDescriptor();
+}
+
+void CGE2MetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+} // End of namespace CGE2
+
+#if PLUGIN_ENABLED_DYNAMIC(CGE2)
+	REGISTER_PLUGIN_DYNAMIC(CGE2, PLUGIN_TYPE_ENGINE, CGE2::CGE2MetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(CGE2, PLUGIN_TYPE_ENGINE, CGE2::CGE2MetaEngineConnect);
+#endif
diff --git a/engines/cge2/module.mk b/engines/cge2/module.mk
index 4b321d88a8..208e8ba64b 100644
--- a/engines/cge2/module.mk
+++ b/engines/cge2/module.mk
@@ -2,10 +2,9 @@ MODULE := engines/cge2
 
 MODULE_OBJS = \
 	cge2.o \
-	detection.o \
-	fileio.o \
 	vga13h.o \
 	bitmap.o \
+	fileio.o \
 	sound.o \
 	cge2_main.o \
 	text.o \
@@ -15,6 +14,7 @@ MODULE_OBJS = \
 	talk.o \
 	events.o \
 	map.o \
+	metaengine.o \
 	vmenu.o \
 	saveload.o \
 	toolbar.o \
@@ -28,3 +28,13 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Only include if building as a dynamic module.
+# Static module already has the contents.
+ifeq ($(ENABLE_CGE2), DYNAMIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/fileio.o
+endif


Commit: 48751160f96fac1edd1a043568b5a4ebeeedca6c
    https://github.com/scummvm/scummvm/commit/48751160f96fac1edd1a043568b5a4ebeeedca6c
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ACCESS: Move common enum to detection_enums.h

Changed paths:
  A engines/access/detection_enums.h
    engines/access/access.h


diff --git a/engines/access/access.h b/engines/access/access.h
index 5c0519daaf..26cf6f4f4d 100644
--- a/engines/access/access.h
+++ b/engines/access/access.h
@@ -30,8 +30,11 @@
 #include "common/savefile.h"
 #include "common/serializer.h"
 #include "common/util.h"
+
 #include "engines/engine.h"
+
 #include "graphics/surface.h"
+
 #include "access/animation.h"
 #include "access/bubble_box.h"
 #include "access/char.h"
@@ -47,6 +50,7 @@
 #include "access/scripts.h"
 #include "access/sound.h"
 #include "access/video.h"
+#include "access/detection_enums.h"
 
 /**
  * This is the namespace of the Access engine.
@@ -58,12 +62,6 @@
  */
 namespace Access {
 
-enum {
-	GType_Amazon = 1,
-	GType_MartianMemorandum = 2,
-	GType_Noctropolis = 3
-};
-
 enum AccessDebugChannels {
 	kDebugPath      = 1 << 0,
 	kDebugScripts	= 1 << 1,
diff --git a/engines/access/detection_enums.h b/engines/access/detection_enums.h
new file mode 100644
index 0000000000..06bb295b65
--- /dev/null
+++ b/engines/access/detection_enums.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Access {
+
+enum {
+	GType_Amazon = 1,
+	GType_MartianMemorandum = 2,
+	GType_Noctropolis = 3
+};
+
+} // End of namespace Access


Commit: c5325c68c9217e8265d04be4dec5d7d85d912a22
    https://github.com/scummvm/scummvm/commit/c5325c68c9217e8265d04be4dec5d7d85d912a22
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ACCESS: Split detection code & adapt to new plugins.

Changed paths:
  A engines/access/detection.h
  A engines/access/metaengine.cpp
    configure
    engines/access/detection.cpp
    engines/access/module.mk


diff --git a/configure b/configure
index 6be89d5cd8..87aa92bf04 100755
--- a/configure
+++ b/configure
@@ -6161,7 +6161,7 @@ EOF
 done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
-								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2")
+								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/access/detection.cpp b/engines/access/detection.cpp
index 9a51ed2e17..e76bc9f163 100644
--- a/engines/access/detection.cpp
+++ b/engines/access/detection.cpp
@@ -20,58 +20,10 @@
  *
  */
 
-#include "access/access.h"
-#include "access/amazon/amazon_game.h"
-#include "access/martian/martian_game.h"
-
 #include "base/plugins.h"
-#include "common/savefile.h"
-#include "common/str-array.h"
-#include "common/memstream.h"
 #include "engines/advancedDetector.h"
-#include "common/system.h"
-#include "graphics/surface.h"
-
-#define MAX_SAVES 99
-
-namespace Access {
-
-struct AccessGameDescription {
-	ADGameDescription desc;
-
-	int gameID;
-	uint32 features;
-};
-
-uint32 AccessEngine::getGameID() const {
-	return _gameDescription->gameID;
-}
-
-uint32 AccessEngine::getGameFeatures() const {
-	return _gameDescription->features;
-}
-
-uint32 AccessEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-bool AccessEngine::isCD() const {
-	return (bool)(_gameDescription->desc.flags & ADGF_CD);
-}
-
-bool AccessEngine::isDemo() const {
-	return (bool)(_gameDescription->desc.flags & ADGF_DEMO);
-}
-
-Common::Language AccessEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-Common::Platform AccessEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-} // End of namespace Access
+#include "access/detection.h"
+#include "access/detection_enums.h"
 
 static const PlainGameDescriptor AccessGames[] = {
 	{"amazon", "Amazon: Guardians of Eden"},
@@ -98,118 +50,7 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Access Engine (C) 1989-1994 Access Software";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool AccessMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Access::AccessEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool AccessMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Access::AccessGameDescription *gd = (const Access::AccessGameDescription *)desc;
-	if (gd) {
-		switch (gd->gameID) {
-		case Access::GType_Amazon:
-			*engine = new Access::Amazon::AmazonEngine(syst, gd);
-			break;
-		case Access::GType_MartianMemorandum:
-			*engine = new Access::Martian::MartianEngine(syst, gd);
-			break;
-		default:
-			error("Unknown game");
-		}
-	}
-	return gd != 0;
-}
-
-SaveStateList AccessMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.0##", target);
-	Access::AccessSavegameHeader header;
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		const char *ext = strrchr(file->c_str(), '.');
-		int slot = ext ? atoi(ext + 1) : -1;
-
-		if (slot >= 0 && slot < MAX_SAVES) {
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-			if (in) {
-				if (Access::AccessEngine::readSavegameHeader(in, header))
-					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
-
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int AccessMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVES;
-}
-
-void AccessMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor AccessMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
-
-	if (f) {
-		Access::AccessSavegameHeader header;
-		if (!Access::AccessEngine::readSavegameHeader(f, header, false)) {
-			delete f;
-			return SaveStateDescriptor();
-		}
-
-		delete f;
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header._saveName);
-		desc.setThumbnail(header._thumbnail);
-		desc.setSaveDate(header._year, header._month, header._day);
-		desc.setSaveTime(header._hour, header._minute);
-		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
 
-#if PLUGIN_ENABLED_DYNAMIC(ACCESS)
-	REGISTER_PLUGIN_DYNAMIC(ACCESS, PLUGIN_TYPE_ENGINE, AccessMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(ACCESS, PLUGIN_TYPE_ENGINE, AccessMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(ACCESS_DETECTION, PLUGIN_TYPE_METAENGINE, AccessMetaEngine);
diff --git a/engines/access/detection.h b/engines/access/detection.h
new file mode 100644
index 0000000000..bd69c92dc1
--- /dev/null
+++ b/engines/access/detection.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Access {
+
+struct AccessGameDescription {
+	ADGameDescription desc;
+
+	int gameID;
+	uint32 features;
+};
+
+} // End of namespace Access
diff --git a/engines/access/metaengine.cpp b/engines/access/metaengine.cpp
new file mode 100644
index 0000000000..3ed66d49f1
--- /dev/null
+++ b/engines/access/metaengine.cpp
@@ -0,0 +1,191 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "engines/advancedDetector.h"
+
+#include "graphics/surface.h"
+
+#include "access/access.h"
+#include "access/amazon/amazon_game.h"
+#include "access/martian/martian_game.h"
+
+#include "access/detection.h"
+
+#define MAX_SAVES 99
+
+namespace Access {
+
+uint32 AccessEngine::getGameID() const {
+	return _gameDescription->gameID;
+}
+
+uint32 AccessEngine::getGameFeatures() const {
+	return _gameDescription->features;
+}
+
+uint32 AccessEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+bool AccessEngine::isCD() const {
+	return (bool)(_gameDescription->desc.flags & ADGF_CD);
+}
+
+bool AccessEngine::isDemo() const {
+	return (bool)(_gameDescription->desc.flags & ADGF_DEMO);
+}
+
+Common::Language AccessEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+Common::Platform AccessEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+} // End of namespace Access
+
+class AccessMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "access";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool AccessMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Access::AccessEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool AccessMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Access::AccessGameDescription *gd = (const Access::AccessGameDescription *)desc;
+	if (gd) {
+		switch (gd->gameID) {
+		case Access::GType_Amazon:
+			*engine = new Access::Amazon::AmazonEngine(syst, gd);
+			break;
+		case Access::GType_MartianMemorandum:
+			*engine = new Access::Martian::MartianEngine(syst, gd);
+			break;
+		default:
+			error("Unknown game");
+		}
+	}
+	return gd != 0;
+}
+
+SaveStateList AccessMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.0##", target);
+	Access::AccessSavegameHeader header;
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		const char *ext = strrchr(file->c_str(), '.');
+		int slot = ext ? atoi(ext + 1) : -1;
+
+		if (slot >= 0 && slot < MAX_SAVES) {
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+			if (in) {
+				if (Access::AccessEngine::readSavegameHeader(in, header))
+					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
+
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int AccessMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVES;
+}
+
+void AccessMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor AccessMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
+
+	if (f) {
+		Access::AccessSavegameHeader header;
+		if (!Access::AccessEngine::readSavegameHeader(f, header, false)) {
+			delete f;
+			return SaveStateDescriptor();
+		}
+
+		delete f;
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header._saveName);
+		desc.setThumbnail(header._thumbnail);
+		desc.setSaveDate(header._year, header._month, header._day);
+		desc.setSaveTime(header._hour, header._minute);
+		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(ACCESS)
+	REGISTER_PLUGIN_DYNAMIC(ACCESS, PLUGIN_TYPE_ENGINE, AccessMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(ACCESS, PLUGIN_TYPE_ENGINE, AccessMetaEngineConnect);
+#endif
diff --git a/engines/access/module.mk b/engines/access/module.mk
index cccb603d31..03465dd715 100644
--- a/engines/access/module.mk
+++ b/engines/access/module.mk
@@ -9,11 +9,11 @@ MODULE_OBJS := \
 	data.o \
 	debugger.o \
 	decompress.o \
-	detection.o \
 	events.o \
 	files.o \
 	font.o \
 	inventory.o \
+	metaengine.o \
 	player.o \
 	resources.o \
 	room.o \
@@ -41,3 +41,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: bbed4235699dac0cd4942b7eff3dba5b7a334fc6
    https://github.com/scummvm/scummvm/commit/bbed4235699dac0cd4942b7eff3dba5b7a334fc6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ZVISION: Move common enums to detection_enums header file.

- These enums are helping in game detection, as well as needed for the engine.

Changed paths:
  A engines/zvision/detection_enums.h
    engines/zvision/zvision.h


diff --git a/engines/zvision/detection_enums.h b/engines/zvision/detection_enums.h
new file mode 100644
index 0000000000..79a0fc2986
--- /dev/null
+++ b/engines/zvision/detection_enums.h
@@ -0,0 +1,36 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ *
+ */
+
+namespace ZVision {
+
+enum ZVisionGameId {
+	GID_NONE = 0,
+	GID_NEMESIS = 1,
+	GID_GRANDINQUISITOR = 2
+};
+
+enum ZVisionFeatures {
+	GF_DVD = (1 << 0) // ZGI DVD version
+};
+
+} // End of namespace ZVision
diff --git a/engines/zvision/zvision.h b/engines/zvision/zvision.h
index 7f4cc9a61d..5cdb4ea9cb 100644
--- a/engines/zvision/zvision.h
+++ b/engines/zvision/zvision.h
@@ -26,6 +26,7 @@
 
 #include "zvision/core/clock.h"
 #include "zvision/file/search_manager.h"
+#include "zvision/detection_enums.h"
 
 #include "common/random.h"
 #include "common/events.h"
@@ -90,16 +91,6 @@ enum {
 	KEYBUF_SIZE = 20
 };
 
-enum ZVisionGameId {
-	GID_NONE = 0,
-	GID_NEMESIS = 1,
-	GID_GRANDINQUISITOR = 2
-};
-
-enum ZVisionFeatures {
-	GF_DVD = (1 << 0) // ZGI DVD version
-};
-
 enum ZVisionAction {
 	kZVisionActionNone,
 	kZVisionActionUp,


Commit: c7dc3d6118ed6791e7050926c56f017812dfc199
    https://github.com/scummvm/scummvm/commit/c7dc3d6118ed6791e7050926c56f017812dfc199
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ZVISION: Split detection code & adapt to new plugins.

Changed paths:
  A engines/zvision/detection.h
  A engines/zvision/metaengine.cpp
    configure
    engines/zvision/detection.cpp
    engines/zvision/module.mk


diff --git a/configure b/configure
index 87aa92bf04..8aaa993451 100755
--- a/configure
+++ b/configure
@@ -6161,7 +6161,8 @@ EOF
 done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
-								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS")
+								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
+								  "ZVISION")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/zvision/detection.cpp b/engines/zvision/detection.cpp
index d97cee5ef4..25a9c2ca18 100644
--- a/engines/zvision/detection.cpp
+++ b/engines/zvision/detection.cpp
@@ -26,38 +26,11 @@
 
 #include "engines/advancedDetector.h"
 
-#include "zvision/zvision.h"
-#include "zvision/file/save_manager.h"
-#include "zvision/scripting/script_manager.h"
-
-#include "backends/keymapper/action.h"
-#include "backends/keymapper/keymapper.h"
-#include "backends/keymapper/standard-actions.h"
-
 #include "common/translation.h"
-#include "common/savefile.h"
 #include "common/str-array.h"
-#include "common/system.h"
-
-namespace ZVision {
-
-struct ZVisionGameDescription {
-	ADGameDescription desc;
-	ZVisionGameId gameId;
-};
-
-ZVisionGameId ZVision::getGameId() const {
-	return _gameDescription->gameId;
-}
-Common::Language ZVision::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-uint32 ZVision::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-} // End of namespace ZVision
 
+#include "zvision/detection_enums.h"
+#include "zvision/detection.h"
 #include "zvision/detection_tables.h"
 
 class ZVisionMetaEngine : public AdvancedMetaEngine {
@@ -78,282 +51,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Z-Vision (C) 1996 Activision";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	Common::KeymapArray initKeymaps(const char *target) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool ZVisionMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-bool ZVision::ZVision::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-Common::Error ZVision::ZVision::loadGameState(int slot) {
-	return _saveManager->loadGame(slot);
-}
-
-Common::Error ZVision::ZVision::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
-	_saveManager->saveGame(slot, desc, false);
-	return Common::kNoError;
-}
-
-bool ZVision::ZVision::canLoadGameStateCurrently() {
-	return !_videoIsPlaying;
-}
-
-bool ZVision::ZVision::canSaveGameStateCurrently() {
-	Location currentLocation = _scriptManager->getCurrentLocation();
-	return !_videoIsPlaying && currentLocation.world != 'g' && !(currentLocation.room == 'j' || currentLocation.room == 'a');
-}
-
-Common::KeymapArray ZVisionMetaEngine::initKeymaps(const char *target) const {
-	using namespace Common;
-	using namespace ZVision;
-
-	Keymap *mainKeymap = new Keymap(Keymap::kKeymapTypeGame, mainKeymapId, "Z-Vision");
-
-	Action *act;
-
-	act = new Action("LCLK", _("Left Click"));
-	act->setLeftClickEvent();
-	act->addDefaultInputMapping("MOUSE_LEFT");
-	act->addDefaultInputMapping("JOY_A");
-	mainKeymap->addAction(act);
-
-	act = new Action("RCLK", _("Right Click"));
-	act->setRightClickEvent();
-	act->addDefaultInputMapping("MOUSE_RIGHT");
-	act->addDefaultInputMapping("JOY_B");
-	mainKeymap->addAction(act);
-
-	Keymap *gameKeymap = new Keymap(Keymap::kKeymapTypeGame, gameKeymapId, "Z-Vision - Game");
-
-	act = new Action(kStandardActionMoveUp, _("Look Up"));
-	act->setCustomEngineActionEvent(kZVisionActionUp);
-	act->addDefaultInputMapping("UP");
-	act->addDefaultInputMapping("JOY_UP");
-	gameKeymap->addAction(act);
-
-	act = new Action(kStandardActionMoveDown, _("Look Down"));
-	act->setCustomEngineActionEvent(kZVisionActionDown);
-	act->addDefaultInputMapping("DOWN");
-	act->addDefaultInputMapping("JOY_DOWN");
-	gameKeymap->addAction(act);
-
-	act = new Action(kStandardActionMoveLeft, _("Turn Left"));
-	act->setCustomEngineActionEvent(kZVisionActionLeft);
-	act->addDefaultInputMapping("LEFT");
-	act->addDefaultInputMapping("JOY_LEFT");
-	gameKeymap->addAction(act);
-
-	act = new Action(kStandardActionMoveRight, _("Turn Right"));
-	act->setCustomEngineActionEvent(kZVisionActionRight);
-	act->addDefaultInputMapping("RIGHT");
-	act->addDefaultInputMapping("JOY_RIGHT");
-	gameKeymap->addAction(act);
-
-	act = new Action("FPS", _("Show FPS"));
-	act->setCustomEngineActionEvent(kZVisionActionShowFPS);
-	act->addDefaultInputMapping("F10");
-	gameKeymap->addAction(act);
-
-	act = new Action("HELP", _("Help"));
-	act->setKeyEvent(KEYCODE_F1);
-	act->addDefaultInputMapping("F1");
-	act->addDefaultInputMapping("JOY_LEFT_TRIGGER");
-	gameKeymap->addAction(act);
-
-	act = new Action("INV", _("Inventory"));
-	act->setKeyEvent(KEYCODE_F5);
-	act->addDefaultInputMapping("F5");
-	act->addDefaultInputMapping("JOY_LEFT_SHOULDER");
-	gameKeymap->addAction(act);
-
-	act = new Action("SPELL", _("Spellbook"));
-	act->setKeyEvent(KEYCODE_F6);
-	act->addDefaultInputMapping("F6");
-	act->addDefaultInputMapping("JOY_RIGHT_SHOULDER");
-	gameKeymap->addAction(act);
-
-	act = new Action("SCORE", _("Score"));
-	act->setKeyEvent(KEYCODE_F7);
-	act->addDefaultInputMapping("F7");
-	act->addDefaultInputMapping("JOY_RIGHT_TRIGGER");
-	gameKeymap->addAction(act);
-
-	act = new Action("AWAY", _("Put away object"));
-	act->setKeyEvent(KEYCODE_F8);
-	act->addDefaultInputMapping("F8");
-	act->addDefaultInputMapping("JOY_X");
-	gameKeymap->addAction(act);
-
-	act = new Action("COIN", _("Extract coin"));
-	act->setKeyEvent(KEYCODE_F9);
-	act->addDefaultInputMapping("F9");
-	act->addDefaultInputMapping("JOY_Y");
-	gameKeymap->addAction(act);
-
-	act = new Action(kStandardActionSave, _("Save"));
-	act->setCustomEngineActionEvent(kZVisionActionSave);
-	act->addDefaultInputMapping("C+s");
-	gameKeymap->addAction(act);
-
-	act = new Action(kStandardActionLoad, _("Restore"));
-	act->setCustomEngineActionEvent(kZVisionActionRestore);
-	act->addDefaultInputMapping("C+r");
-	gameKeymap->addAction(act);
-
-	act = new Action("QUIT", _("Quit"));
-	act->setCustomEngineActionEvent(kZVisionActionQuit);
-	act->addDefaultInputMapping("C+q");
-	gameKeymap->addAction(act);
-
-	act = new Action(kStandardActionOpenSettings, _("Preferences"));
-	act->setCustomEngineActionEvent(kZVisionActionPreferences);
-	act->addDefaultInputMapping("C+p");
-	gameKeymap->addAction(act);
-
-	Keymap *cutscenesKeymap = new Keymap(Keymap::kKeymapTypeGame, cutscenesKeymapId, "Z-Vision - Cutscenes");
-
-	act = new Action(kStandardActionSkip, _("Skip cutscene"));
-	act->setCustomEngineActionEvent(kZVisionActionSkipCutscene);
-	act->addDefaultInputMapping("SPACE");
-	act->addDefaultInputMapping("JOY_Y");
-	cutscenesKeymap->addAction(act);
-
-	act = new Action("QUIT", _("Quit"));
-	act->setCustomEngineActionEvent(kZVisionActionQuit);
-	act->addDefaultInputMapping("C+q");
-	cutscenesKeymap->addAction(act);
-
-	KeymapArray keymaps(3);
-	keymaps[0] = mainKeymap;
-	keymaps[1] = gameKeymap;
-	keymaps[2] = cutscenesKeymap;
-
-	return keymaps;
-}
-
-bool ZVisionMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const ZVision::ZVisionGameDescription *gd = (const ZVision::ZVisionGameDescription *)desc;
-	if (gd) {
-		*engine = new ZVision::ZVision(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList ZVisionMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	ZVision::SaveGameHeader header;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	Common::StringArray filenames;
-	filenames = saveFileMan->listSavefiles(pattern.c_str());
-
-	SaveStateList saveList;
-	// We only use readSaveGameHeader() here, which doesn't need an engine callback
-	ZVision::SaveManager *zvisionSaveMan = new ZVision::SaveManager(NULL);
-
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); file++) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
-			if (in) {
-				if (zvisionSaveMan->readSaveGameHeader(in, header)) {
-					saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
-				}
-				delete in;
-			}
-		}
-	}
-
-	delete zvisionSaveMan;
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int ZVisionMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-void ZVisionMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	saveFileMan->removeSavefile(Common::String::format("%s.%03u", target, slot));
-}
-
-SaveStateDescriptor ZVisionMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03u", target, slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
-
-	if (in) {
-		ZVision::SaveGameHeader header;
-
-		// We only use readSaveGameHeader() here, which doesn't need an engine callback
-		ZVision::SaveManager *zvisionSaveMan = new ZVision::SaveManager(NULL);
-		bool successfulRead = zvisionSaveMan->readSaveGameHeader(in, header, false);
-		delete zvisionSaveMan;
-		delete in;
-
-		if (successfulRead) {
-			SaveStateDescriptor desc(slot, header.saveName);
-
-			// Do not allow save slot 0 (used for auto-saving) to be deleted or
-			// overwritten.
-			desc.setDeletableFlag(slot != 0);
-			desc.setWriteProtectedFlag(slot == 0);
-
-			desc.setThumbnail(header.thumbnail);
-
-			if (header.version >= 1) {
-				int day = header.saveDay;
-				int month = header.saveMonth;
-				int year = header.saveYear;
-
-				desc.setSaveDate(year, month, day);
-
-				int hour = header.saveHour;
-				int minutes = header.saveMinutes;
-
-				desc.setSaveTime(hour, minutes);
-			}
-
-			if (header.version >= 2) {
-				desc.setPlayTime(header.playTime * 1000);
-			}
-
-			return desc;
-		}
-	}
-
-	return SaveStateDescriptor();
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(ZVISION)
-	REGISTER_PLUGIN_DYNAMIC(ZVISION, PLUGIN_TYPE_ENGINE, ZVisionMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(ZVISION, PLUGIN_TYPE_ENGINE, ZVisionMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(ZVISION_DETECTION, PLUGIN_TYPE_METAENGINE, ZVisionMetaEngine);
diff --git a/engines/zvision/detection.h b/engines/zvision/detection.h
new file mode 100644
index 0000000000..1b32a5c024
--- /dev/null
+++ b/engines/zvision/detection.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace ZVision {
+
+struct ZVisionGameDescription {
+	ADGameDescription desc;
+	ZVisionGameId gameId;
+};
+
+} // End of namespace ZVision
diff --git a/engines/zvision/metaengine.cpp b/engines/zvision/metaengine.cpp
new file mode 100644
index 0000000000..1732a0e5ed
--- /dev/null
+++ b/engines/zvision/metaengine.cpp
@@ -0,0 +1,338 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/scummsys.h"
+
+#include "engines/advancedDetector.h"
+
+#include "zvision/zvision.h"
+#include "zvision/file/save_manager.h"
+#include "zvision/scripting/script_manager.h"
+#include "zvision/detection.h"
+
+#include "backends/keymapper/action.h"
+#include "backends/keymapper/keymapper.h"
+#include "backends/keymapper/standard-actions.h"
+
+#include "common/savefile.h"
+#include "common/system.h"
+#include "common/translation.h"
+
+namespace ZVision {
+
+ZVisionGameId ZVision::getGameId() const {
+	return _gameDescription->gameId;
+}
+Common::Language ZVision::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+uint32 ZVision::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+} // End of namespace ZVision
+
+class ZVisionMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "zvision";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	Common::KeymapArray initKeymaps(const char *target) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool ZVisionMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+bool ZVision::ZVision::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+Common::Error ZVision::ZVision::loadGameState(int slot) {
+	return _saveManager->loadGame(slot);
+}
+
+Common::Error ZVision::ZVision::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
+	_saveManager->saveGame(slot, desc, false);
+	return Common::kNoError;
+}
+
+bool ZVision::ZVision::canLoadGameStateCurrently() {
+	return !_videoIsPlaying;
+}
+
+bool ZVision::ZVision::canSaveGameStateCurrently() {
+	Location currentLocation = _scriptManager->getCurrentLocation();
+	return !_videoIsPlaying && currentLocation.world != 'g' && !(currentLocation.room == 'j' || currentLocation.room == 'a');
+}
+
+Common::KeymapArray ZVisionMetaEngineConnect::initKeymaps(const char *target) const {
+	using namespace Common;
+	using namespace ZVision;
+
+	Keymap *mainKeymap = new Keymap(Keymap::kKeymapTypeGame, mainKeymapId, "Z-Vision");
+
+	Action *act;
+
+	act = new Action("LCLK", _("Left Click"));
+	act->setLeftClickEvent();
+	act->addDefaultInputMapping("MOUSE_LEFT");
+	act->addDefaultInputMapping("JOY_A");
+	mainKeymap->addAction(act);
+
+	act = new Action("RCLK", _("Right Click"));
+	act->setRightClickEvent();
+	act->addDefaultInputMapping("MOUSE_RIGHT");
+	act->addDefaultInputMapping("JOY_B");
+	mainKeymap->addAction(act);
+
+	Keymap *gameKeymap = new Keymap(Keymap::kKeymapTypeGame, gameKeymapId, "Z-Vision - Game");
+
+	act = new Action(kStandardActionMoveUp, _("Look Up"));
+	act->setCustomEngineActionEvent(kZVisionActionUp);
+	act->addDefaultInputMapping("UP");
+	act->addDefaultInputMapping("JOY_UP");
+	gameKeymap->addAction(act);
+
+	act = new Action(kStandardActionMoveDown, _("Look Down"));
+	act->setCustomEngineActionEvent(kZVisionActionDown);
+	act->addDefaultInputMapping("DOWN");
+	act->addDefaultInputMapping("JOY_DOWN");
+	gameKeymap->addAction(act);
+
+	act = new Action(kStandardActionMoveLeft, _("Turn Left"));
+	act->setCustomEngineActionEvent(kZVisionActionLeft);
+	act->addDefaultInputMapping("LEFT");
+	act->addDefaultInputMapping("JOY_LEFT");
+	gameKeymap->addAction(act);
+
+	act = new Action(kStandardActionMoveRight, _("Turn Right"));
+	act->setCustomEngineActionEvent(kZVisionActionRight);
+	act->addDefaultInputMapping("RIGHT");
+	act->addDefaultInputMapping("JOY_RIGHT");
+	gameKeymap->addAction(act);
+
+	act = new Action("FPS", _("Show FPS"));
+	act->setCustomEngineActionEvent(kZVisionActionShowFPS);
+	act->addDefaultInputMapping("F10");
+	gameKeymap->addAction(act);
+
+	act = new Action("HELP", _("Help"));
+	act->setKeyEvent(KEYCODE_F1);
+	act->addDefaultInputMapping("F1");
+	act->addDefaultInputMapping("JOY_LEFT_TRIGGER");
+	gameKeymap->addAction(act);
+
+	act = new Action("INV", _("Inventory"));
+	act->setKeyEvent(KEYCODE_F5);
+	act->addDefaultInputMapping("F5");
+	act->addDefaultInputMapping("JOY_LEFT_SHOULDER");
+	gameKeymap->addAction(act);
+
+	act = new Action("SPELL", _("Spellbook"));
+	act->setKeyEvent(KEYCODE_F6);
+	act->addDefaultInputMapping("F6");
+	act->addDefaultInputMapping("JOY_RIGHT_SHOULDER");
+	gameKeymap->addAction(act);
+
+	act = new Action("SCORE", _("Score"));
+	act->setKeyEvent(KEYCODE_F7);
+	act->addDefaultInputMapping("F7");
+	act->addDefaultInputMapping("JOY_RIGHT_TRIGGER");
+	gameKeymap->addAction(act);
+
+	act = new Action("AWAY", _("Put away object"));
+	act->setKeyEvent(KEYCODE_F8);
+	act->addDefaultInputMapping("F8");
+	act->addDefaultInputMapping("JOY_X");
+	gameKeymap->addAction(act);
+
+	act = new Action("COIN", _("Extract coin"));
+	act->setKeyEvent(KEYCODE_F9);
+	act->addDefaultInputMapping("F9");
+	act->addDefaultInputMapping("JOY_Y");
+	gameKeymap->addAction(act);
+
+	act = new Action(kStandardActionSave, _("Save"));
+	act->setCustomEngineActionEvent(kZVisionActionSave);
+	act->addDefaultInputMapping("C+s");
+	gameKeymap->addAction(act);
+
+	act = new Action(kStandardActionLoad, _("Restore"));
+	act->setCustomEngineActionEvent(kZVisionActionRestore);
+	act->addDefaultInputMapping("C+r");
+	gameKeymap->addAction(act);
+
+	act = new Action("QUIT", _("Quit"));
+	act->setCustomEngineActionEvent(kZVisionActionQuit);
+	act->addDefaultInputMapping("C+q");
+	gameKeymap->addAction(act);
+
+	act = new Action(kStandardActionOpenSettings, _("Preferences"));
+	act->setCustomEngineActionEvent(kZVisionActionPreferences);
+	act->addDefaultInputMapping("C+p");
+	gameKeymap->addAction(act);
+
+	Keymap *cutscenesKeymap = new Keymap(Keymap::kKeymapTypeGame, cutscenesKeymapId, "Z-Vision - Cutscenes");
+
+	act = new Action(kStandardActionSkip, _("Skip cutscene"));
+	act->setCustomEngineActionEvent(kZVisionActionSkipCutscene);
+	act->addDefaultInputMapping("SPACE");
+	act->addDefaultInputMapping("JOY_Y");
+	cutscenesKeymap->addAction(act);
+
+	act = new Action("QUIT", _("Quit"));
+	act->setCustomEngineActionEvent(kZVisionActionQuit);
+	act->addDefaultInputMapping("C+q");
+	cutscenesKeymap->addAction(act);
+
+	KeymapArray keymaps(3);
+	keymaps[0] = mainKeymap;
+	keymaps[1] = gameKeymap;
+	keymaps[2] = cutscenesKeymap;
+
+	return keymaps;
+}
+
+bool ZVisionMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const ZVision::ZVisionGameDescription *gd = (const ZVision::ZVisionGameDescription *)desc;
+	if (gd) {
+		*engine = new ZVision::ZVision(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList ZVisionMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	ZVision::SaveGameHeader header;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	Common::StringArray filenames;
+	filenames = saveFileMan->listSavefiles(pattern.c_str());
+
+	SaveStateList saveList;
+	// We only use readSaveGameHeader() here, which doesn't need an engine callback
+	ZVision::SaveManager *zvisionSaveMan = new ZVision::SaveManager(NULL);
+
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); file++) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
+			if (in) {
+				if (zvisionSaveMan->readSaveGameHeader(in, header)) {
+					saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
+				}
+				delete in;
+			}
+		}
+	}
+
+	delete zvisionSaveMan;
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int ZVisionMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+void ZVisionMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	saveFileMan->removeSavefile(Common::String::format("%s.%03u", target, slot));
+}
+
+SaveStateDescriptor ZVisionMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03u", target, slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
+
+	if (in) {
+		ZVision::SaveGameHeader header;
+
+		// We only use readSaveGameHeader() here, which doesn't need an engine callback
+		ZVision::SaveManager *zvisionSaveMan = new ZVision::SaveManager(NULL);
+		bool successfulRead = zvisionSaveMan->readSaveGameHeader(in, header, false);
+		delete zvisionSaveMan;
+		delete in;
+
+		if (successfulRead) {
+			SaveStateDescriptor desc(slot, header.saveName);
+
+			// Do not allow save slot 0 (used for auto-saving) to be deleted or
+			// overwritten.
+			desc.setDeletableFlag(slot != 0);
+			desc.setWriteProtectedFlag(slot == 0);
+
+			desc.setThumbnail(header.thumbnail);
+
+			if (header.version >= 1) {
+				int day = header.saveDay;
+				int month = header.saveMonth;
+				int year = header.saveYear;
+
+				desc.setSaveDate(year, month, day);
+
+				int hour = header.saveHour;
+				int minutes = header.saveMinutes;
+
+				desc.setSaveTime(hour, minutes);
+			}
+
+			if (header.version >= 2) {
+				desc.setPlayTime(header.playTime * 1000);
+			}
+
+			return desc;
+		}
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(ZVISION)
+	REGISTER_PLUGIN_DYNAMIC(ZVISION, PLUGIN_TYPE_ENGINE, ZVisionMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(ZVISION, PLUGIN_TYPE_ENGINE, ZVisionMetaEngineConnect);
+#endif
diff --git a/engines/zvision/module.mk b/engines/zvision/module.mk
index 93fba2879d..70728e39dc 100644
--- a/engines/zvision/module.mk
+++ b/engines/zvision/module.mk
@@ -4,7 +4,6 @@ MODULE_OBJS := \
 	core/console.o \
 	core/clock.o \
 	core/events.o \
-	detection.o \
 	file/lzss_read_stream.o \
 	file/save_manager.o \
 	file/search_manager.o \
@@ -16,6 +15,7 @@ MODULE_OBJS := \
 	graphics/effects/wave.o \
 	graphics/render_manager.o \
 	graphics/render_table.o \
+	metaengine.o \
 	scripting/actions.o \
 	scripting/control.o \
 	scripting/controls/fist_control.o \
@@ -60,3 +60,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 76cb0351e0710b38ca7b5c84c5a1c7b661d5e777
    https://github.com/scummvm/scummvm/commit/76cb0351e0710b38ca7b5c84c5a1c7b661d5e777
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
AGOS: Move common enum from agos.h to new header file

Changed paths:
  A engines/agos/detection_enums.h
    engines/agos/agos.h


diff --git a/engines/agos/agos.h b/engines/agos/agos.h
index cf42e78cc9..eee7406c87 100644
--- a/engines/agos/agos.h
+++ b/engines/agos/agos.h
@@ -35,6 +35,7 @@
 #include "audio/mixer.h"
 
 #include "agos/vga.h"
+#include "agos/detection_enums.h"
 
 /**
  * This is the namespace of the AGOS engine.
@@ -175,17 +176,6 @@ struct AnimTable {
 	AnimTable() { memset(this, 0, sizeof(*this)); }
 };
 
-enum SIMONGameType {
-	GType_PN = 0,
-	GType_ELVIRA1 = 1,
-	GType_ELVIRA2 = 2,
-	GType_WW = 3,
-	GType_SIMON1 = 4,
-	GType_SIMON2 = 5,
-	GType_FF = 6,
-	GType_PP = 7
-};
-
 enum EventType {
 	ANIMATE_INT   = 1 << 1,
 	ANIMATE_EVENT = 1 << 2,
diff --git a/engines/agos/detection_enums.h b/engines/agos/detection_enums.h
new file mode 100644
index 0000000000..ce0e9792c8
--- /dev/null
+++ b/engines/agos/detection_enums.h
@@ -0,0 +1,37 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace AGOS {
+
+// Enums related to detection, from the main agos/agos.h file.
+enum SIMONGameType {
+	GType_PN = 0,
+	GType_ELVIRA1 = 1,
+	GType_ELVIRA2 = 2,
+	GType_WW = 3,
+	GType_SIMON1 = 4,
+	GType_SIMON2 = 5,
+	GType_FF = 6,
+	GType_PP = 7
+};
+
+} // End of namespace AGOS


Commit: 5850987077e9f25a8594b1295fc9b7b999d5894b
    https://github.com/scummvm/scummvm/commit/5850987077e9f25a8594b1295fc9b7b999d5894b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
AGOS: Move some common detection related enums from intern.h -> intern_detection.h

- Include it in intern.h, so everything functions normally.
- However, now we can include detection-related things from intern.h in other files, without including unnecessary things.

Changed paths:
  A engines/agos/intern_detection.h
    engines/agos/intern.h


diff --git a/engines/agos/intern.h b/engines/agos/intern.h
index afc0cad08e..985394ea1a 100644
--- a/engines/agos/intern.h
+++ b/engines/agos/intern.h
@@ -23,6 +23,8 @@
 #ifndef AGOS_INTERN_H
 #define AGOS_INTERN_H
 
+#include "agos/intern_detection.h"
+
 namespace AGOS {
 
 enum ChildType {
@@ -245,58 +247,6 @@ enum SubObjectFlags {
 	kOFVoice          = 0x200  // Others
 };
 
-enum GameFeatures {
-	GF_TALKIE           = 1 << 0,
-	GF_OLD_BUNDLE       = 1 << 1,
-	GF_CRUNCHED         = 1 << 2,
-	GF_CRUNCHED_GAMEPC  = 1 << 3,
-	GF_ZLIBCOMP         = 1 << 4,
-	GF_32COLOR          = 1 << 5,
-	GF_EGA              = 1 << 6,
-	GF_PLANAR           = 1 << 7,
-	GF_DEMO             = 1 << 8,
-	GF_PACKED           = 1 << 9,
-	GF_BROKEN_FF_RATING = 1 << 10,
-	GF_WAVSFX           = 1 << 11
-};
-
-enum GameFileTypes {
-	GAME_BASEFILE = 1 << 0,
-	GAME_ICONFILE = 1 << 1,
-	GAME_GMEFILE  = 1 << 2,
-	GAME_MENUFILE = 1 << 3,
-	GAME_STRFILE  = 1 << 4,
-	GAME_RMSLFILE = 1 << 5,
-	GAME_STATFILE = 1 << 6,
-	GAME_TBLFILE  = 1 << 7,
-	GAME_XTBLFILE = 1 << 8,
-	GAME_RESTFILE = 1 << 9,
-	GAME_TEXTFILE = 1 << 10,
-	GAME_VGAFILE  = 1 << 11,
-
-	GAME_GFXIDXFILE = 1 << 12
-};
-
-enum GameIds {
-	GID_PN,
-	GID_ELVIRA1,
-	GID_ELVIRA2,
-	GID_WAXWORKS,
-
-	GID_SIMON1,
-	GID_SIMON1DOS,
-	GID_SIMON1CD32,
-
-	GID_SIMON2,
-
-	GID_FEEBLEFILES,
-
-	GID_DIMP,
-	GID_JUMBLE,
-	GID_PUZZLE,
-	GID_SWAMPY
-};
-
 } // End of namespace AGOS
 
 #endif
diff --git a/engines/agos/intern_detection.h b/engines/agos/intern_detection.h
new file mode 100644
index 0000000000..04d9d1e7a7
--- /dev/null
+++ b/engines/agos/intern_detection.h
@@ -0,0 +1,80 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+// Game detection - related enums, taken from agos/intern.h
+
+namespace AGOS {
+
+enum GameIds {
+	GID_PN,
+	GID_ELVIRA1,
+	GID_ELVIRA2,
+	GID_WAXWORKS,
+
+	GID_SIMON1,
+	GID_SIMON1DOS,
+	GID_SIMON1CD32,
+
+	GID_SIMON2,
+
+	GID_FEEBLEFILES,
+
+	GID_DIMP,
+	GID_JUMBLE,
+	GID_PUZZLE,
+	GID_SWAMPY
+};
+
+enum GameFeatures {
+	GF_TALKIE           = 1 << 0,
+	GF_OLD_BUNDLE       = 1 << 1,
+	GF_CRUNCHED         = 1 << 2,
+	GF_CRUNCHED_GAMEPC  = 1 << 3,
+	GF_ZLIBCOMP         = 1 << 4,
+	GF_32COLOR          = 1 << 5,
+	GF_EGA              = 1 << 6,
+	GF_PLANAR           = 1 << 7,
+	GF_DEMO             = 1 << 8,
+	GF_PACKED           = 1 << 9,
+	GF_BROKEN_FF_RATING = 1 << 10,
+	GF_WAVSFX           = 1 << 11
+};
+
+enum GameFileTypes {
+	GAME_BASEFILE = 1 << 0,
+	GAME_ICONFILE = 1 << 1,
+	GAME_GMEFILE  = 1 << 2,
+	GAME_MENUFILE = 1 << 3,
+	GAME_STRFILE  = 1 << 4,
+	GAME_RMSLFILE = 1 << 5,
+	GAME_STATFILE = 1 << 6,
+	GAME_TBLFILE  = 1 << 7,
+	GAME_XTBLFILE = 1 << 8,
+	GAME_RESTFILE = 1 << 9,
+	GAME_TEXTFILE = 1 << 10,
+	GAME_VGAFILE  = 1 << 11,
+
+	GAME_GFXIDXFILE = 1 << 12
+};
+
+
+} // End of namespace AGOS


Commit: 2f6453100b27a61bfc2e58b2c51ee6c002158a60
    https://github.com/scummvm/scummvm/commit/2f6453100b27a61bfc2e58b2c51ee6c002158a60
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
AGOS: Split detection code & adapt to new plugins.

- Move AGOSGameDescription -> detection.h
- Move obsoleteGameIDsTable -> obsolete.h
- Both the above points are because the detection needs them, as well as the engine.
- By moving to headers in this pattern, we avoid many unnecessary inclusions and keep everything clean.

Changed paths:
  A engines/agos/detection.h
  A engines/agos/metaengine.cpp
  A engines/agos/obsolete.h
    configure
    engines/agos/detection.cpp
    engines/agos/module.mk


diff --git a/configure b/configure
index 8aaa993451..761eb0e7d4 100755
--- a/configure
+++ b/configure
@@ -6162,7 +6162,7 @@ done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
-								  "ZVISION")
+								  "ZVISION" "AGOS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/agos/detection.cpp b/engines/agos/detection.cpp
index 174d3f109b..32dd815412 100644
--- a/engines/agos/detection.cpp
+++ b/engines/agos/detection.cpp
@@ -24,46 +24,21 @@
 
 #include "engines/advancedDetector.h"
 #include "engines/obsolete.h"
-#include "common/config-manager.h"
-#include "common/savefile.h"
+
 #include "common/system.h"
 #include "common/textconsole.h"
 #include "common/installshield_cab.h"
 
-#include "agos/intern.h"
-#include "agos/agos.h"
-
-namespace AGOS {
-
-struct AGOSGameDescription {
-	ADGameDescription desc;
-
-	int gameType;
-	int gameId;
-	uint32 features;
-};
-
-}
+#include "agos/detection.h"
+#include "agos/detection_enums.h"
+#include "agos/intern_detection.h"
+#include "agos/obsolete.h" // Obsolete ID table.
 
 /**
  * Conversion table mapping old obsolete target names to the
  * corresponding new target and platform combination.
  *
  */
-static const Engines::ObsoleteGameID obsoleteGameIDsTable[] = {
-	{"simon1acorn", "simon1", Common::kPlatformAcorn},
-	{"simon1amiga", "simon1", Common::kPlatformAmiga},
-	{"simon1cd32", "simon1", Common::kPlatformAmiga},
-	{"simon1demo", "simon1", Common::kPlatformDOS},
-	{"simon1dos", "simon1", Common::kPlatformDOS},
-	{"simon1talkie", "simon1", Common::kPlatformDOS},
-	{"simon1win", "simon1", Common::kPlatformWindows},
-	{"simon2dos", "simon2", Common::kPlatformDOS},
-	{"simon2talkie", "simon2", Common::kPlatformDOS},
-	{"simon2mac", "simon2", Common::kPlatformMacintosh},
-	{"simon2win", "simon2", Common::kPlatformWindows},
-	{0, 0, Common::kPlatformUnknown}
-};
 
 static const PlainGameDescriptor agosGames[] = {
 	{"pn", "Personal Nightmare"},
@@ -114,177 +89,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "AGOS (C) Adventure Soft";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-
-	Common::Error createInstance(OSystem *syst, Engine **engine) const override {
-		Engines::upgradeTargetIfNecessary(obsoleteGameIDsTable);
-		return AdvancedMetaEngine::createInstance(syst, engine);
-	}
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
 };
 
-bool AgosMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSimpleSavesNames);
-}
-
-bool AGOS::AGOSEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher);
-}
-
-bool AgosMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const AGOS::AGOSGameDescription *gd = (const AGOS::AGOSGameDescription *)desc;
-	bool res = true;
-
-	switch (gd->gameType) {
-	case AGOS::GType_PN:
-		*engine = new AGOS::AGOSEngine_PN(syst, gd);
-		break;
-	case AGOS::GType_ELVIRA1:
-		*engine = new AGOS::AGOSEngine_Elvira1(syst, gd);
-		break;
-	case AGOS::GType_ELVIRA2:
-		*engine = new AGOS::AGOSEngine_Elvira2(syst, gd);
-		break;
-	case AGOS::GType_WW:
-		*engine = new AGOS::AGOSEngine_Waxworks(syst, gd);
-		break;
-	case AGOS::GType_SIMON1:
-		*engine = new AGOS::AGOSEngine_Simon1(syst, gd);
-		break;
-	case AGOS::GType_SIMON2:
-		*engine = new AGOS::AGOSEngine_Simon2(syst, gd);
-		break;
-#ifdef ENABLE_AGOS2
-	case AGOS::GType_FF:
-		if (gd->features & GF_DEMO)
-			*engine = new AGOS::AGOSEngine_FeebleDemo(syst, gd);
-		else
-			*engine = new AGOS::AGOSEngine_Feeble(syst, gd);
-		break;
-	case AGOS::GType_PP:
-		if (gd->gameId == GID_DIMP)
-			*engine = new AGOS::AGOSEngine_DIMP(syst, gd);
-		else
-			*engine = new AGOS::AGOSEngine_PuzzlePack(syst, gd);
-		break;
-#endif
-	default:
-		res = false;
-		error("AGOS engine: unknown gameType");
-	}
-
-	return res;
-}
-
-SaveStateList AgosMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				saveDesc = file->c_str();
-				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int AgosMetaEngine::getMaximumSaveSlot() const { return 999; }
-
-#if PLUGIN_ENABLED_DYNAMIC(AGOS)
-	REGISTER_PLUGIN_DYNAMIC(AGOS, PLUGIN_TYPE_ENGINE, AgosMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(AGOS, PLUGIN_TYPE_ENGINE, AgosMetaEngine);
-#endif
-
-namespace AGOS {
-
-int AGOSEngine::getGameId() const {
-	return _gameDescription->gameId;
-}
-
-int AGOSEngine::getGameType() const {
-	return _gameDescription->gameType;
-}
-
-uint32 AGOSEngine::getFeatures() const {
-	return _gameDescription->features;
-}
-
-const char *AGOSEngine::getExtra() const {
-	return _gameDescription->desc.extra;
-}
-
-Common::Language AGOSEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-Common::Platform AGOSEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-const char *AGOSEngine::getFileName(int type) const {
-	// Required if the InstallShield cab is been used
-	if (getGameType() == GType_PP) {
-		if (type == GAME_BASEFILE)
-			return gss->base_filename;
-	}
-
-	// Required if the InstallShield cab is been used
-	if (getGameType() == GType_FF && getPlatform() == Common::kPlatformWindows) {
-		if (type == GAME_BASEFILE)
-			return gss->base_filename;
-		if (type == GAME_RESTFILE)
-			return gss->restore_filename;
-		if (type == GAME_TBLFILE)
-			return gss->tbl_filename;
-	}
-
-	for (int i = 0; _gameDescription->desc.filesDescriptions[i].fileType; i++) {
-		if (_gameDescription->desc.filesDescriptions[i].fileType == type)
-			return _gameDescription->desc.filesDescriptions[i].fileName;
-	}
-	return NULL;
-}
-
-#ifdef ENABLE_AGOS2
-void AGOSEngine::loadArchives() {
-	const ADGameFileDescription *ag;
-
-	if (getFeatures() & GF_PACKED) {
-		for (ag = _gameDescription->desc.filesDescriptions; ag->fileName; ag++) {
-			if (!SearchMan.hasArchive(ag->fileName)) {
-				Common::SeekableReadStream *stream = SearchMan.createReadStreamForMember(ag->fileName);
-
-				if (stream)
-					SearchMan.add(ag->fileName, Common::makeInstallShieldArchive(stream, DisposeAfterUse::YES), ag->fileType);
-			}
-		}
-	}
-}
-#endif
-
-} // End of namespace AGOS
+REGISTER_PLUGIN_STATIC(AGOS_DETECTION, PLUGIN_TYPE_METAENGINE, AgosMetaEngine);
diff --git a/engines/agos/detection.h b/engines/agos/detection.h
new file mode 100644
index 0000000000..304d7fc4ef
--- /dev/null
+++ b/engines/agos/detection.h
@@ -0,0 +1,33 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace AGOS {
+
+struct AGOSGameDescription {
+	ADGameDescription desc;
+
+	int gameType;
+	int gameId;
+	uint32 features;
+};
+
+} // End of namespace AGOS
diff --git a/engines/agos/metaengine.cpp b/engines/agos/metaengine.cpp
new file mode 100644
index 0000000000..7bac156118
--- /dev/null
+++ b/engines/agos/metaengine.cpp
@@ -0,0 +1,214 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/config-manager.h"
+#include "common/savefile.h"
+#include "common/system.h"
+#include "common/installshield_cab.h"
+
+#include "engines/advancedDetector.h"
+#include "engines/obsolete.h"
+
+#include "agos/intern.h"
+#include "agos/agos.h"
+#include "agos/detection.h"
+#include "agos/obsolete.h"
+
+class AgosMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "agos";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+	Common::Error createInstance(OSystem *syst, Engine **engine) const override {
+		Engines::upgradeTargetIfNecessary(obsoleteGameIDsTable);
+		return AdvancedMetaEngineConnect::createInstance(syst, engine);
+	}
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+};
+
+bool AgosMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSimpleSavesNames);
+}
+
+bool AGOS::AGOSEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher);
+}
+
+bool AgosMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const AGOS::AGOSGameDescription *gd = (const AGOS::AGOSGameDescription *)desc;
+	bool res = true;
+
+	switch (gd->gameType) {
+	case AGOS::GType_PN:
+		*engine = new AGOS::AGOSEngine_PN(syst, gd);
+		break;
+	case AGOS::GType_ELVIRA1:
+		*engine = new AGOS::AGOSEngine_Elvira1(syst, gd);
+		break;
+	case AGOS::GType_ELVIRA2:
+		*engine = new AGOS::AGOSEngine_Elvira2(syst, gd);
+		break;
+	case AGOS::GType_WW:
+		*engine = new AGOS::AGOSEngine_Waxworks(syst, gd);
+		break;
+	case AGOS::GType_SIMON1:
+		*engine = new AGOS::AGOSEngine_Simon1(syst, gd);
+		break;
+	case AGOS::GType_SIMON2:
+		*engine = new AGOS::AGOSEngine_Simon2(syst, gd);
+		break;
+#ifdef ENABLE_AGOS2
+	case AGOS::GType_FF:
+		if (gd->features & AGOS::GF_DEMO)
+			*engine = new AGOS::AGOSEngine_FeebleDemo(syst, gd);
+		else
+			*engine = new AGOS::AGOSEngine_Feeble(syst, gd);
+		break;
+	case AGOS::GType_PP:
+		if (gd->gameId == AGOS::GID_DIMP)
+			*engine = new AGOS::AGOSEngine_DIMP(syst, gd);
+		else
+			*engine = new AGOS::AGOSEngine_PuzzlePack(syst, gd);
+		break;
+#endif
+	default:
+		res = false;
+		error("AGOS engine: unknown gameType");
+	}
+
+	return res;
+}
+
+SaveStateList AgosMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				saveDesc = file->c_str();
+				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int AgosMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+
+#if PLUGIN_ENABLED_DYNAMIC(AGOS)
+	REGISTER_PLUGIN_DYNAMIC(AGOS, PLUGIN_TYPE_ENGINE, AgosMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(AGOS, PLUGIN_TYPE_ENGINE, AgosMetaEngineConnect);
+#endif
+
+namespace AGOS {
+
+int AGOSEngine::getGameId() const {
+	return _gameDescription->gameId;
+}
+
+int AGOSEngine::getGameType() const {
+	return _gameDescription->gameType;
+}
+
+uint32 AGOSEngine::getFeatures() const {
+	return _gameDescription->features;
+}
+
+const char *AGOSEngine::getExtra() const {
+	return _gameDescription->desc.extra;
+}
+
+Common::Language AGOSEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+Common::Platform AGOSEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+const char *AGOSEngine::getFileName(int type) const {
+	// Required if the InstallShield cab is been used
+	if (getGameType() == GType_PP) {
+		if (type == GAME_BASEFILE)
+			return gss->base_filename;
+	}
+
+	// Required if the InstallShield cab is been used
+	if (getGameType() == GType_FF && getPlatform() == Common::kPlatformWindows) {
+		if (type == GAME_BASEFILE)
+			return gss->base_filename;
+		if (type == GAME_RESTFILE)
+			return gss->restore_filename;
+		if (type == GAME_TBLFILE)
+			return gss->tbl_filename;
+	}
+
+	for (int i = 0; _gameDescription->desc.filesDescriptions[i].fileType; i++) {
+		if (_gameDescription->desc.filesDescriptions[i].fileType == type)
+			return _gameDescription->desc.filesDescriptions[i].fileName;
+	}
+	return NULL;
+}
+
+#ifdef ENABLE_AGOS2
+void AGOSEngine::loadArchives() {
+	const ADGameFileDescription *ag;
+
+	if (getFeatures() & GF_PACKED) {
+		for (ag = _gameDescription->desc.filesDescriptions; ag->fileName; ag++) {
+			if (!SearchMan.hasArchive(ag->fileName)) {
+				Common::SeekableReadStream *stream = SearchMan.createReadStreamForMember(ag->fileName);
+
+				if (stream)
+					SearchMan.add(ag->fileName, Common::makeInstallShieldArchive(stream, DisposeAfterUse::YES), ag->fileType);
+			}
+		}
+	}
+}
+#endif
+
+} // End of namespace AGOS
diff --git a/engines/agos/module.mk b/engines/agos/module.mk
index e7b773d76f..919f819c1c 100644
--- a/engines/agos/module.mk
+++ b/engines/agos/module.mk
@@ -12,7 +12,6 @@ MODULE_OBJS := \
 	cursor.o \
 	debug.o \
 	debugger.o \
-	detection.o \
 	draw.o \
 	event.o \
 	gfx.o \
@@ -21,6 +20,7 @@ MODULE_OBJS := \
 	input_pn.o \
 	items.o \
 	menus.o \
+	metaengine.o \
 	midi.o \
 	midiparser_s1d.o \
 	pn.o \
@@ -69,3 +69,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/agos/obsolete.h b/engines/agos/obsolete.h
new file mode 100644
index 0000000000..00ea8ef2cd
--- /dev/null
+++ b/engines/agos/obsolete.h
@@ -0,0 +1,37 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+static const Engines::ObsoleteGameID obsoleteGameIDsTable[] = {
+	{"simon1acorn", "simon1", Common::kPlatformAcorn},
+	{"simon1amiga", "simon1", Common::kPlatformAmiga},
+	{"simon1cd32", "simon1", Common::kPlatformAmiga},
+	{"simon1demo", "simon1", Common::kPlatformDOS},
+	{"simon1dos", "simon1", Common::kPlatformDOS},
+	{"simon1talkie", "simon1", Common::kPlatformDOS},
+	{"simon1win", "simon1", Common::kPlatformWindows},
+	{"simon2dos", "simon2", Common::kPlatformDOS},
+	{"simon2talkie", "simon2", Common::kPlatformDOS},
+	{"simon2mac", "simon2", Common::kPlatformMacintosh},
+	{"simon2win", "simon2", Common::kPlatformWindows},
+	{0, 0, Common::kPlatformUnknown}
+};


Commit: bd9514ffa8c88819a72faa361eb6250b44013eca
    https://github.com/scummvm/scummvm/commit/bd9514ffa8c88819a72faa361eb6250b44013eca
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GOB: Remove gob engine file dependencies from dataio.cpp

- DataIO is a class that helps with fallback detection for MetaEngines.
- To prepare it for being included in the executable, get rid of unneeded engine dependencies & headers.
- A utility function is being used from util.cpp, simply prepare a static copy in fileio.cpp
- Leave a comment saying a copy is being used in util.cpp.

Changed paths:
    engines/gob/dataio.cpp
    engines/gob/util.cpp


diff --git a/engines/gob/dataio.cpp b/engines/gob/dataio.cpp
index 6deaef417e..443d262fb4 100644
--- a/engines/gob/dataio.cpp
+++ b/engines/gob/dataio.cpp
@@ -25,10 +25,7 @@
 #include "common/memstream.h"
 #include "common/substream.h"
 
-#include "gob/gob.h"
 #include "gob/dataio.h"
-#include "gob/global.h"
-#include "gob/util.h"
 
 namespace Gob {
 
@@ -242,6 +239,12 @@ bool DataIO::openArchive(Common::String name, bool base) {
 	return true;
 }
 
+// A copy of replaceChar utlity function from util.cpp
+static void replaceChar(char *str, char c1, char c2) {
+	while ((str = strchr(str, c1)))
+		*str = c2;
+}
+
 DataIO::Archive *DataIO::openArchive(const Common::String &name) {
 	Archive *archive = new Archive;
 	if (!archive->file.open(name)) {
@@ -265,11 +268,11 @@ DataIO::Archive *DataIO::openArchive(const Common::String &name) {
 		file.compression = archive->file.readByte() != 0;
 
 		// Replacing cyrillic characters
-		Util::replaceChar(fileName, (char) 0x85, 'E');
-		Util::replaceChar(fileName, (char) 0x8A, 'K');
-		Util::replaceChar(fileName, (char) 0x8E, 'O');
-		Util::replaceChar(fileName, (char) 0x91, 'C');
-		Util::replaceChar(fileName, (char) 0x92, 'T');
+		replaceChar(fileName, (char) 0x85, 'E');
+		replaceChar(fileName, (char) 0x8A, 'K');
+		replaceChar(fileName, (char) 0x8E, 'O');
+		replaceChar(fileName, (char) 0x91, 'C');
+		replaceChar(fileName, (char) 0x92, 'T');
 
 		file.name = fileName;
 
diff --git a/engines/gob/util.cpp b/engines/gob/util.cpp
index 19840d8c98..6d32e4c262 100644
--- a/engines/gob/util.cpp
+++ b/engines/gob/util.cpp
@@ -517,6 +517,7 @@ void Util::cutFromStr(char *str, int16 from, int16 cutlen) {
 	} while (str[i] != 0);
 }
 
+// A copy of this utility function is used by fileio.cpp.
 void Util::replaceChar(char *str, char c1, char c2) {
 	while ((str = strchr(str, c1)))
 		*str = c2;


Commit: 9b774c6b6ffb7a2033e73649e1698bc4bc9f16f6
    https://github.com/scummvm/scummvm/commit/9b774c6b6ffb7a2033e73649e1698bc4bc9f16f6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GOB: Move detection-related enums from gob.h -> detection/detection_enums.h

- This way, we won't have to include the whole gob.h file.

Changed paths:
  A engines/gob/detection/detection_enums.h
    engines/gob/gob.h


diff --git a/engines/gob/detection/detection_enums.h b/engines/gob/detection/detection_enums.h
new file mode 100644
index 0000000000..212258a693
--- /dev/null
+++ b/engines/gob/detection/detection_enums.h
@@ -0,0 +1,69 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+// Taken from gob/gob.h
+namespace Gob {
+
+// WARNING: Reordering these will invalidate save games!
+//          Add new games to the bottom of the list.
+enum GameType {
+	kGameTypeNone = 0,
+	kGameTypeGob1,
+	kGameTypeGob2,
+	kGameTypeGob3,
+	kGameTypeWoodruff,
+	kGameTypeBargon,
+	kGameTypeWeen,
+	kGameTypeLostInTime,
+	kGameTypeInca2,
+	kGameTypeDynasty,
+	kGameTypeUrban,
+	kGameTypePlaytoons,
+	kGameTypeBambou,
+	kGameTypeFascination,
+	kGameTypeGeisha,
+	kGameTypeAdi2,
+	kGameTypeAdi4,
+	kGameTypeAdibou2,
+	kGameTypeAdibou1,
+	kGameTypeAbracadabra,
+	kGameTypeBabaYaga,
+	kGameTypeLittleRed,
+	kGameTypeOnceUponATime, // Need more inspection to see if Baba Yaga or Abracadabra
+	kGameTypeAJWorld,
+	kGameTypeCrousti
+};
+
+enum Features {
+	kFeaturesNone      =      0,
+	kFeaturesCD        = 1 << 0,
+	kFeaturesEGA       = 1 << 1,
+	kFeaturesAdLib     = 1 << 2,
+	kFeaturesSCNDemo   = 1 << 3,
+	kFeaturesBATDemo   = 1 << 4,
+	kFeatures640x480   = 1 << 5,
+	kFeatures800x600   = 1 << 6,
+	kFeaturesTrueColor = 1 << 7
+};
+
+} // End of namespace Gob
diff --git a/engines/gob/gob.h b/engines/gob/gob.h
index b5287b85cb..a5275fbb77 100644
--- a/engines/gob/gob.h
+++ b/engines/gob/gob.h
@@ -31,6 +31,7 @@
 #include "engines/engine.h"
 
 #include "gob/console.h"
+#include "gob/detection/detection_enums.h"
 
 /**
  * This is the namespace of the Gob engine.
@@ -103,48 +104,6 @@ enum Endianness {
 	kEndiannessBE
 };
 
-// WARNING: Reordering these will invalidate save games!
-//          Add new games to the bottom of the list.
-enum GameType {
-	kGameTypeNone = 0,
-	kGameTypeGob1,
-	kGameTypeGob2,
-	kGameTypeGob3,
-	kGameTypeWoodruff,
-	kGameTypeBargon,
-	kGameTypeWeen,
-	kGameTypeLostInTime,
-	kGameTypeInca2,
-	kGameTypeDynasty,
-	kGameTypeUrban,
-	kGameTypePlaytoons,
-	kGameTypeBambou,
-	kGameTypeFascination,
-	kGameTypeGeisha,
-	kGameTypeAdi2,
-	kGameTypeAdi4,
-	kGameTypeAdibou2,
-	kGameTypeAdibou1,
-	kGameTypeAbracadabra,
-	kGameTypeBabaYaga,
-	kGameTypeLittleRed,
-	kGameTypeOnceUponATime, // Need more inspection to see if Baba Yaga or Abracadabra
-	kGameTypeAJWorld,
-	kGameTypeCrousti
-};
-
-enum Features {
-	kFeaturesNone      =      0,
-	kFeaturesCD        = 1 << 0,
-	kFeaturesEGA       = 1 << 1,
-	kFeaturesAdLib     = 1 << 2,
-	kFeaturesSCNDemo   = 1 << 3,
-	kFeaturesBATDemo   = 1 << 4,
-	kFeatures640x480   = 1 << 5,
-	kFeatures800x600   = 1 << 6,
-	kFeaturesTrueColor = 1 << 7
-};
-
 enum EndiannessMethod {
 	kEndiannessMethodLE,     ///< Always little endian.
 	kEndiannessMethodBE,     ///< Always big endian.


Commit: ce07bd711fbb9142b2b5566923d185b5f0704224
    https://github.com/scummvm/scummvm/commit/ce07bd711fbb9142b2b5566923d185b5f0704224
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GOB: Split detection code & adapt to new plugins.

Changed paths:
  A engines/gob/detection/detection.h
  A engines/gob/metaengine.cpp
    configure
    engines/gob/detection/detection.cpp
    engines/gob/detection/tables.h
    engines/gob/module.mk


diff --git a/configure b/configure
index 761eb0e7d4..c4c92cc2fa 100755
--- a/configure
+++ b/configure
@@ -6162,7 +6162,7 @@ done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
-								  "ZVISION" "AGOS")
+								  "ZVISION" "AGOS" "GOB")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/gob/detection/detection.cpp b/engines/gob/detection/detection.cpp
index cdc74848f6..9cb9fea4ec 100644
--- a/engines/gob/detection/detection.cpp
+++ b/engines/gob/detection/detection.cpp
@@ -23,9 +23,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "gob/gob.h"
 #include "gob/dataio.h"
-
+#include "gob/detection/detection_enums.h"
 #include "gob/detection/tables.h"
 
 class GobMetaEngine : public AdvancedMetaEngine {
@@ -36,15 +35,10 @@ public:
 		return "gob";
 	}
 
-	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
-
 	const char *getName() const override;
 	const char *getOriginalCopyright() const override;
 
-	bool hasFeature(MetaEngineFeature f) const override;
-
-	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
 
 private:
 	/**
@@ -162,54 +156,4 @@ const char *GobMetaEngine::getOriginalCopyright() const {
 	return "Goblins Games (C) Coktel Vision";
 }
 
-bool GobMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return false;
-}
-
-bool Gob::GobEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher);
-}
-
-Common::Error GobMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
-	return AdvancedMetaEngine::createInstance(syst, engine);
-}
-
-bool GobMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Gob::GOBGameDescription *gd = (const Gob::GOBGameDescription *)desc;
-	if (gd) {
-		*engine = new Gob::GobEngine(syst);
-		((Gob::GobEngine *)*engine)->initGame(gd);
-	}
-	return gd != 0;
-}
-
-
-#if PLUGIN_ENABLED_DYNAMIC(GOB)
-	REGISTER_PLUGIN_DYNAMIC(GOB, PLUGIN_TYPE_ENGINE, GobMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(GOB, PLUGIN_TYPE_ENGINE, GobMetaEngine);
-#endif
-
-namespace Gob {
-
-void GobEngine::initGame(const GOBGameDescription *gd) {
-	if (gd->startTotBase == 0)
-		_startTot = "intro.tot";
-	else
-		_startTot = gd->startTotBase;
-
-	if (gd->startStkBase == 0)
-		_startStk = "intro.stk";
-	else
-		_startStk = gd->startStkBase;
-
-	_demoIndex = gd->demoIndex;
-
-	_gameType = gd->gameType;
-	_features = gd->features;
-	_language = gd->desc.language;
-	_platform = gd->desc.platform;
-}
-
-} // End of namespace Gob
+REGISTER_PLUGIN_STATIC(GOB_DETECTION, PLUGIN_TYPE_METAENGINE, GobMetaEngine);
diff --git a/engines/gob/detection/detection.h b/engines/gob/detection/detection.h
new file mode 100644
index 0000000000..0166116730
--- /dev/null
+++ b/engines/gob/detection/detection.h
@@ -0,0 +1,36 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+namespace Gob {
+
+struct GOBGameDescription {
+	ADGameDescription desc;
+
+	GameType gameType;
+	int32 features;
+	const char *startStkBase;
+	const char *startTotBase;
+	uint32 demoIndex;
+};
+
+} // End of namespace Gob
diff --git a/engines/gob/detection/tables.h b/engines/gob/detection/tables.h
index 031ea627e0..30c1e04f17 100644
--- a/engines/gob/detection/tables.h
+++ b/engines/gob/detection/tables.h
@@ -23,19 +23,8 @@
 #ifndef GOB_DETECTION_TABLES_H
 #define GOB_DETECTION_TABLES_H
 
-namespace Gob {
-
-struct GOBGameDescription {
-	ADGameDescription desc;
-
-	GameType gameType;
-	int32 features;
-	const char *startStkBase;
-	const char *startTotBase;
-	uint32 demoIndex;
-};
-
-}
+// Struct "GOBGameDescription"
+#include "gob/detection/detection.h"
 
 using namespace Common;
 
diff --git a/engines/gob/metaengine.cpp b/engines/gob/metaengine.cpp
new file mode 100644
index 0000000000..4ec0a04cf8
--- /dev/null
+++ b/engines/gob/metaengine.cpp
@@ -0,0 +1,93 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/advancedDetector.h"
+
+#include "gob/gob.h"
+
+// For struct GOBGameDescription.
+#include "gob/detection/detection.h"
+
+class GobMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "gob";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool GobMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return false;
+}
+
+bool Gob::GobEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher);
+}
+
+Common::Error GobMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+	return AdvancedMetaEngineConnect::createInstance(syst, engine);
+}
+
+bool GobMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Gob::GOBGameDescription *gd = (const Gob::GOBGameDescription *)desc;
+	if (gd) {
+		*engine = new Gob::GobEngine(syst);
+		((Gob::GobEngine *)*engine)->initGame(gd);
+	}
+	return gd != 0;
+}
+
+
+#if PLUGIN_ENABLED_DYNAMIC(GOB)
+	REGISTER_PLUGIN_DYNAMIC(GOB, PLUGIN_TYPE_ENGINE, GobMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(GOB, PLUGIN_TYPE_ENGINE, GobMetaEngineConnect);
+#endif
+
+namespace Gob {
+
+void GobEngine::initGame(const GOBGameDescription *gd) {
+	if (gd->startTotBase == 0)
+		_startTot = "intro.tot";
+	else
+		_startTot = gd->startTotBase;
+
+	if (gd->startStkBase == 0)
+		_startStk = "intro.stk";
+	else
+		_startStk = gd->startStkBase;
+
+	_demoIndex = gd->demoIndex;
+
+	_gameType = gd->gameType;
+	_features = gd->features;
+	_language = gd->desc.language;
+	_platform = gd->desc.platform;
+}
+
+} // End of namespace Gob
+
diff --git a/engines/gob/module.mk b/engines/gob/module.mk
index d5ee6478be..171c935262 100644
--- a/engines/gob/module.mk
+++ b/engines/gob/module.mk
@@ -8,8 +8,8 @@ MODULE_OBJS := \
 	cheater_geisha.o \
 	cmpfile.o \
 	console.o \
-	dataio.o \
 	databases.o \
+	dataio.o \
 	dbase.o \
 	decfile.o \
 	draw.o \
@@ -55,6 +55,7 @@ MODULE_OBJS := \
 	map.o \
 	map_v1.o \
 	map_v2.o \
+	metaengine.o \
 	mult.o \
 	mult_v1.o \
 	mult_v2.o \
@@ -77,7 +78,6 @@ MODULE_OBJS := \
 	demos/demoplayer.o \
 	demos/scnplayer.o \
 	demos/batplayer.o \
-	detection/detection.o \
 	pregob/pregob.o \
 	pregob/txtfile.o \
 	pregob/gctfile.o \
@@ -133,3 +133,13 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection/detection.o
+
+# Only include if building as a dynamic module.
+# Static module already has the contents.
+ifeq ($(ENABLE_GOB), DYNAMIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/dataio.o
+endif


Commit: 7bdc910cc8143af01bd099f67d8ba16e3b1f690d
    https://github.com/scummvm/scummvm/commit/7bdc910cc8143af01bd099f67d8ba16e3b1f690d
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
COMPOSER: Split detection features & adapt to new plugins.

Changed paths:
  A engines/composer/detection.h
  A engines/composer/detection_enums.h
  A engines/composer/metaengine.cpp
    configure
    engines/composer/composer.h
    engines/composer/detection.cpp
    engines/composer/module.mk


diff --git a/configure b/configure
index c4c92cc2fa..c053585ca8 100755
--- a/configure
+++ b/configure
@@ -6162,7 +6162,7 @@ done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
-								  "ZVISION" "AGOS" "GOB")
+								  "ZVISION" "AGOS" "GOB" "COMPOSER")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/composer/composer.h b/engines/composer/composer.h
index a5e3278f4d..43716d648b 100644
--- a/engines/composer/composer.h
+++ b/engines/composer/composer.h
@@ -44,6 +44,7 @@
 
 #include "composer/resource.h"
 #include "composer/console.h"
+#include "composer/detection_enums.h"
 
 namespace Audio {
 	class QueuingAudioStream;
@@ -53,17 +54,6 @@ namespace Composer {
 
 struct ComposerGameDescription;
 
-enum GameType {
-	GType_ComposerV1,
-	GType_ComposerV2
-};
-
-enum GameFileTypes {
-	GAME_CONFIGFILE     = 1 << 0,    // Game configuration
-	GAME_SCRIPTFILE     = 1 << 1,    // Game script
-	GAME_EXECUTABLE     = 1 << 2     // Game executable
-};
-
 class Archive;
 struct Animation;
 class ComposerEngine;
diff --git a/engines/composer/detection.cpp b/engines/composer/detection.cpp
index 1cc8a148d6..8144d0e17a 100644
--- a/engines/composer/detection.cpp
+++ b/engines/composer/detection.cpp
@@ -21,54 +21,10 @@
  */
 
 #include "base/plugins.h"
-#include "common/savefile.h"
-#include "common/serializer.h"
-#include "common/str-array.h"
 #include "engines/advancedDetector.h"
 
-#include "composer/composer.h"
-
-namespace Composer {
-
-struct ComposerGameDescription {
-	ADGameDescription desc;
-
-	int gameType;
-};
-
-int ComposerEngine::getGameType() const {
-	return _gameDescription->gameType;
-}
-
-const char *ComposerEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-uint32 ComposerEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language ComposerEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-Common::Platform ComposerEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-bool ComposerEngine::loadDetectedConfigFile(Common::INIFile &configFile) const {
-	const ADGameFileDescription *res = _gameDescription->desc.filesDescriptions;
-	while (res->fileName != NULL) {
-		if (res->fileType == GAME_CONFIGFILE) {
-			return configFile.loadFromFile(res->fileName);
-		}
-		res++;
-	}
-	// default config file name
-	return configFile.loadFromFile("book.ini") || configFile.loadFromFile("book.mac");
-}
-
-}
+#include "composer/detection_enums.h"
+#include "composer/detection.h"
 
 static const PlainGameDescriptor composerGames[] = {
 	{"babayaga", "Magic Tales: Baba Yaga and the Magic Geese"},
@@ -115,72 +71,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Copyright (C) 1995-1999 Animation Magic";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char* target) const override;
 };
 
-bool ComposerMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Composer::ComposerGameDescription *gd = (const Composer::ComposerGameDescription *)desc;
-	if (gd) {
-		*engine = new Composer::ComposerEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-bool ComposerMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return ((f == kSupportsListSaves) || (f == kSupportsLoadingDuringStartup));
-}
-
-Common::String getSaveName(Common::InSaveFile *in) {
-	Common::Serializer ser(in, NULL);
-	Common::String name;
-	uint32 tmp;
-	ser.syncAsUint32LE(tmp);
-	ser.syncAsUint32LE(tmp);
-	ser.syncString(name);
-	return name;
-}
-int ComposerMetaEngine::getMaximumSaveSlot() const {
-	return 99;
-}
-SaveStateList ComposerMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.##", target);
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-
-		if (slotNum >= 0 && slotNum <= 99) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				saveDesc = getSaveName(in);
-				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-				delete in;
-			}
-		}
-	}
-
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-bool Composer::ComposerEngine::hasFeature(EngineFeature f) const {
-	return (f == kSupportsReturnToLauncher
-		|| f == kSupportsSavingDuringRuntime
-		|| f == kSupportsLoadingDuringRuntime);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(COMPOSER)
-	REGISTER_PLUGIN_DYNAMIC(COMPOSER, PLUGIN_TYPE_ENGINE, ComposerMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(COMPOSER, PLUGIN_TYPE_ENGINE, ComposerMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(COMPOSER_DETECTION, PLUGIN_TYPE_METAENGINE, ComposerMetaEngine);
\ No newline at end of file
diff --git a/engines/composer/detection.h b/engines/composer/detection.h
new file mode 100644
index 0000000000..91271c7ad5
--- /dev/null
+++ b/engines/composer/detection.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Composer {
+
+struct ComposerGameDescription {
+	ADGameDescription desc;
+
+	int gameType;
+};
+
+} // End of namespace Composer
diff --git a/engines/composer/detection_enums.h b/engines/composer/detection_enums.h
new file mode 100644
index 0000000000..7dee54a1d8
--- /dev/null
+++ b/engines/composer/detection_enums.h
@@ -0,0 +1,36 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Composer {
+
+enum GameType {
+	GType_ComposerV1,
+	GType_ComposerV2
+};
+
+enum GameFileTypes {
+	GAME_CONFIGFILE     = 1 << 0,    // Game configuration
+	GAME_SCRIPTFILE     = 1 << 1,    // Game script
+	GAME_EXECUTABLE     = 1 << 2     // Game executable
+};
+
+} // End of namespace Composer
diff --git a/engines/composer/metaengine.cpp b/engines/composer/metaengine.cpp
new file mode 100644
index 0000000000..bb70d1bdc4
--- /dev/null
+++ b/engines/composer/metaengine.cpp
@@ -0,0 +1,142 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+#include "common/savefile.h"
+#include "common/serializer.h"
+#include "common/str-array.h"
+#include "engines/advancedDetector.h"
+
+#include "composer/composer.h"
+#include "composer/detection.h"
+
+namespace Composer {
+
+int ComposerEngine::getGameType() const {
+	return _gameDescription->gameType;
+}
+
+const char *ComposerEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+uint32 ComposerEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language ComposerEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+Common::Platform ComposerEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+bool ComposerEngine::loadDetectedConfigFile(Common::INIFile &configFile) const {
+	const ADGameFileDescription *res = _gameDescription->desc.filesDescriptions;
+	while (res->fileName != NULL) {
+		if (res->fileType == GAME_CONFIGFILE) {
+			return configFile.loadFromFile(res->fileName);
+		}
+		res++;
+	}
+	// default config file name
+	return configFile.loadFromFile("book.ini") || configFile.loadFromFile("book.mac");
+}
+
+} // End of namespace Composer
+
+class ComposerMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "composer";
+	}
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char* target) const override;
+};
+
+bool ComposerMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Composer::ComposerGameDescription *gd = (const Composer::ComposerGameDescription *)desc;
+	if (gd) {
+		*engine = new Composer::ComposerEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+bool ComposerMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return ((f == kSupportsListSaves) || (f == kSupportsLoadingDuringStartup));
+}
+
+Common::String getSaveName(Common::InSaveFile *in) {
+	Common::Serializer ser(in, NULL);
+	Common::String name;
+	uint32 tmp;
+	ser.syncAsUint32LE(tmp);
+	ser.syncAsUint32LE(tmp);
+	ser.syncString(name);
+	return name;
+}
+int ComposerMetaEngineConnect::getMaximumSaveSlot() const {
+	return 99;
+}
+SaveStateList ComposerMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.##", target);
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+
+		if (slotNum >= 0 && slotNum <= 99) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				saveDesc = getSaveName(in);
+				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+				delete in;
+			}
+		}
+	}
+
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+bool Composer::ComposerEngine::hasFeature(EngineFeature f) const {
+	return (f == kSupportsReturnToLauncher
+		|| f == kSupportsSavingDuringRuntime
+		|| f == kSupportsLoadingDuringRuntime);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(COMPOSER)
+	REGISTER_PLUGIN_DYNAMIC(COMPOSER, PLUGIN_TYPE_ENGINE, ComposerMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(COMPOSER, PLUGIN_TYPE_ENGINE, ComposerMetaEngineConnect);
+#endif
diff --git a/engines/composer/module.mk b/engines/composer/module.mk
index 74465cf156..6fdcc59d05 100644
--- a/engines/composer/module.mk
+++ b/engines/composer/module.mk
@@ -3,8 +3,8 @@ MODULE := engines/composer
 MODULE_OBJS = \
 	console.o \
 	composer.o \
-	detection.o \
 	graphics.o \
+	metaengine.o \
 	resource.o \
 	saveload.o \
 	scripting.o
@@ -16,3 +16,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: b027c8f11e4bfaffca4267471cdf7c3cedf40516
    https://github.com/scummvm/scummvm/commit/b027c8f11e4bfaffca4267471cdf7c3cedf40516
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DM: Move common-game & detection code to header files from dm.h

- Move enums to detection_enums.h
- Move DM..GameDescription struct to detection.h

Changed paths:
  A engines/dm/detection.h
  A engines/dm/detection_enums.h
    engines/dm/dm.h


diff --git a/engines/dm/detection.h b/engines/dm/detection.h
new file mode 100644
index 0000000000..f2b106be5c
--- /dev/null
+++ b/engines/dm/detection.h
@@ -0,0 +1,42 @@
+/* ScummVM - Graphic Adventure Engine
+*
+* ScummVM is the legal property of its developers, whose names
+* are too numerous to list here. Please refer to the COPYRIGHT
+* file distributed with this source distribution.
+*
+* This program is free software; you can redistribute it and/or
+* modify it under the terms of the GNU General Public License
+* as published by the Free Software Foundation; either version 2
+* of the License, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+*
+*/
+
+/*
+* Based on the Reverse Engineering work of Christophe Fontanel,
+* maintainer of the Dungeon Master Encyclopaedia (http://dmweb.free.fr/)
+*/
+
+namespace DM {
+
+struct DMADGameDescription {
+	ADGameDescription _desc;
+
+	SaveTarget _saveTargetToWrite;
+	OriginalSaveFormat _origSaveFormatToWrite;
+	OriginalSavePlatform _origPlatformToWrite;
+
+	SaveTarget _saveTargetToAccept[kDMSaveTargetTotal + 1];
+	OriginalSaveFormat _saveFormatToAccept[kDMSaveFormatTotal + 1];
+	OriginalSavePlatform _origPlatformToAccept[kDMSavePlatformTotal + 1];
+};
+
+} // End of namespace DM
diff --git a/engines/dm/detection_enums.h b/engines/dm/detection_enums.h
new file mode 100644
index 0000000000..6c20025210
--- /dev/null
+++ b/engines/dm/detection_enums.h
@@ -0,0 +1,66 @@
+/* ScummVM - Graphic Adventure Engine
+*
+* ScummVM is the legal property of its developers, whose names
+* are too numerous to list here. Please refer to the COPYRIGHT
+* file distributed with this source distribution.
+*
+* This program is free software; you can redistribute it and/or
+* modify it under the terms of the GNU General Public License
+* as published by the Free Software Foundation; either version 2
+* of the License, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+*
+*/
+
+/*
+* Based on the Reverse Engineering work of Christophe Fontanel,
+* maintainer of the Dungeon Master Encyclopaedia (http://dmweb.free.fr/)
+*/
+
+namespace DM {
+
+enum OriginalSaveFormat {
+	kDMSaveFormatAcceptAny = -1,
+	kDMSaveFormatEndOfList = 0,
+	kDMSaveFormatNone = 0,
+	kDMSaveFormatAtari = 1,
+	kDMSaveFormatAmigaPC98FmTowns = 2,
+	kCSBSaveFormatAtari = 2,
+	kDMSaveFormatAppleIIgs = 3,
+	kDMSaveFormatAmiga36PC = 5,
+	kCSBSaveFormatAmigaPC98FmTowns = 5,
+	kDMSaveFormatTotal
+};
+
+enum OriginalSavePlatform {
+	kDMSavePlatformAcceptAny = -1,
+	kDMSavePlatformEndOfList = 0,
+	kDMSavePlatformNone = 0,
+	kDMSavePlatformAtariSt = 1, // @ C1_PLATFORM_ATARI_ST
+	kDMSavePlatformAppleIIgs = 2, // @ C2_PLATFORM_APPLE_IIGS
+	kDMSavePlatformAmiga = 3, // @ C3_PLATFORM_AMIGA
+	kDMSavePlatformPC98 = 5, // @ C5_PLATFORM_PC98
+	kDMSavePlatformX68000 = 6, // @ C6_PLATFORM_X68000
+	kDMSavePlatformFmTownsEN = 7, // @ C7_PLATFORM_FM_TOWNS_EN
+	kDMSavePlatformFmTownsJP = 8, // @ C8_PLATFORM_FM_TOWNS_JP
+	kDMSavePlatformPC = 9, // @ C9_PLATFORM_PC
+	kDMSavePlatformTotal
+};
+
+enum SaveTarget {
+	kDMSaveTargetAcceptAny = -1,
+	kDMSaveTargetEndOfList = 0,
+	kDMSaveTargetNone = 0,
+	kDMSaveTargetDM21 = 1,
+	kDMSaveTargetTotal
+};
+
+} // End of namespace DM
diff --git a/engines/dm/dm.h b/engines/dm/dm.h
index 839dc8fdff..029b671c23 100644
--- a/engines/dm/dm.h
+++ b/engines/dm/dm.h
@@ -39,6 +39,8 @@
 #include "advancedDetector.h"
 
 #include "dm/console.h"
+#include "dm/detection_enums.h"
+#include "dm/detection.h"
 
 struct ADGameDescription;
 
@@ -59,42 +61,6 @@ class ProjExpl;
 class DialogMan;
 class SoundMan;
 
-enum OriginalSaveFormat {
-	kDMSaveFormatAcceptAny = -1,
-	kDMSaveFormatEndOfList = 0,
-	kDMSaveFormatNone = 0,
-	kDMSaveFormatAtari = 1,
-	kDMSaveFormatAmigaPC98FmTowns = 2,
-	kCSBSaveFormatAtari = 2,
-	kDMSaveFormatAppleIIgs = 3,
-	kDMSaveFormatAmiga36PC = 5,
-	kCSBSaveFormatAmigaPC98FmTowns = 5,
-	kDMSaveFormatTotal
-};
-
-enum OriginalSavePlatform {
-	kDMSavePlatformAcceptAny = -1,
-	kDMSavePlatformEndOfList = 0,
-	kDMSavePlatformNone = 0,
-	kDMSavePlatformAtariSt = 1, // @ C1_PLATFORM_ATARI_ST
-	kDMSavePlatformAppleIIgs = 2, // @ C2_PLATFORM_APPLE_IIGS
-	kDMSavePlatformAmiga = 3, // @ C3_PLATFORM_AMIGA
-	kDMSavePlatformPC98 = 5, // @ C5_PLATFORM_PC98
-	kDMSavePlatformX68000 = 6, // @ C6_PLATFORM_X68000
-	kDMSavePlatformFmTownsEN = 7, // @ C7_PLATFORM_FM_TOWNS_EN
-	kDMSavePlatformFmTownsJP = 8, // @ C8_PLATFORM_FM_TOWNS_JP
-	kDMSavePlatformPC = 9, // @ C9_PLATFORM_PC
-	kDMSavePlatformTotal
-};
-
-enum SaveTarget {
-	kDMSaveTargetAcceptAny = -1,
-	kDMSaveTargetEndOfList = 0,
-	kDMSaveTargetNone = 0,
-	kDMSaveTargetDM21 = 1,
-	kDMSaveTargetTotal
-};
-
 enum Direction {
 	kDMDirNorth = 0,
 	kDMDirEast = 1,
@@ -152,18 +118,6 @@ enum MapIndice {
 #define kDMSlotBoxInventoryActionHand 9 // @ C09_SLOT_BOX_INVENTORY_ACTION_HAND
 #define kDMSlotBoxChestFirstSlot 38     // @ C38_SLOT_BOX_CHEST_FIRST_SLOT
 
-struct DMADGameDescription {
-	ADGameDescription _desc;
-
-	SaveTarget _saveTargetToWrite;
-	OriginalSaveFormat _origSaveFormatToWrite;
-	OriginalSavePlatform _origPlatformToWrite;
-
-	SaveTarget _saveTargetToAccept[kDMSaveTargetTotal + 1];
-	OriginalSaveFormat _saveFormatToAccept[kDMSaveFormatTotal + 1];
-	OriginalSavePlatform _origPlatformToAccept[kDMSavePlatformTotal + 1];
-};
-
 class Thing {
 public:
 	uint16 _data;


Commit: 26c475b784664c9da6abde0728fdf59f72335778
    https://github.com/scummvm/scummvm/commit/26c475b784664c9da6abde0728fdf59f72335778
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DM: Split detection features & adapt to new plugins.

Changed paths:
  A engines/dm/metaengine.cpp
    configure
    engines/dm/detection.cpp
    engines/dm/module.mk


diff --git a/configure b/configure
index c053585ca8..529829d481 100755
--- a/configure
+++ b/configure
@@ -6162,7 +6162,7 @@ done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
-								  "ZVISION" "AGOS" "GOB" "COMPOSER")
+								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/dm/detection.cpp b/engines/dm/detection.cpp
index beaaca3f36..aa051815f8 100644
--- a/engines/dm/detection.cpp
+++ b/engines/dm/detection.cpp
@@ -26,16 +26,14 @@
 */
 
 
-#include "common/config-manager.h"
-#include "common/error.h"
-#include "common/fs.h"
-#include "common/system.h"
-
+#include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "dm/dm.h"
+#include "dm/detection_enums.h"
+#include "dm/detection.h"
 
 namespace DM {
+
 static const PlainGameDescriptor DMGames[] = {
 	{"dm", "Dungeon Master"},
 	{0, 0}
@@ -112,79 +110,9 @@ public:
 		return "Dungeon Master (C) 1987 FTL Games";
 	}
 
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
-		if (desc)
-			*engine = new DM::DMEngine(syst, (const DMADGameDescription*)desc);
-		return desc != nullptr;
-	}
-
-	bool hasFeature(MetaEngineFeature f) const override {
-		return
-			(f == kSupportsListSaves) ||
-			(f == kSupportsLoadingDuringStartup) ||
-			(f == kSavesSupportThumbnail) ||
-			(f == kSavesSupportMetaInfo) ||
-			(f == kSavesSupportCreationDate);
-	}
-
-	int getMaximumSaveSlot() const override { return 99; }
-
-	SaveStateList listSaves(const char *target) const override {
-		Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-		SaveGameHeader header;
-		Common::String pattern = target;
-		pattern += ".###";
-
-		Common::StringArray filenames;
-		filenames = saveFileMan->listSavefiles(pattern.c_str());
-
-		SaveStateList saveList;
-
-		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-			// Obtain the last 3 digits of the filename, since they correspond to the save slot
-			int slotNum = atoi(file->c_str() + file->size() - 3);
-
-			if ((slotNum >= 0) && (slotNum <= 999)) {
-				Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
-				if (in) {
-					if (DM::readSaveGameHeader(in, &header))
-						saveList.push_back(SaveStateDescriptor(slotNum, header._descr.getDescription()));
-					delete in;
-				}
-			}
-		}
 
-		// Sort saves based on slot number.
-		Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-		return saveList;
-	}
-
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
-		Common::String filename = Common::String::format("%s.%03u", target, slot);
-		Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
-
-		if (in) {
-			DM::SaveGameHeader header;
-
-			bool successfulRead = DM::readSaveGameHeader(in, &header);
-			delete in;
-
-			if (successfulRead) {
-				SaveStateDescriptor desc(slot, header._descr.getDescription());
-
-				return header._descr;
-			}
-		}
-
-		return SaveStateDescriptor();
-	}
-
-	void removeSaveState(const char *target, int slot) const override {}
 };
 
-}
-#if PLUGIN_ENABLED_DYNAMIC(DM)
-REGISTER_PLUGIN_DYNAMIC(DM, PLUGIN_TYPE_ENGINE, DM::DMMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(DM, PLUGIN_TYPE_ENGINE, DM::DMMetaEngine);
-#endif
+} // End of namespace DM
+
+REGISTER_PLUGIN_STATIC(DM_DETECTION, PLUGIN_TYPE_METAENGINE, DM::DMMetaEngine);
diff --git a/engines/dm/metaengine.cpp b/engines/dm/metaengine.cpp
new file mode 100644
index 0000000000..853034313c
--- /dev/null
+++ b/engines/dm/metaengine.cpp
@@ -0,0 +1,122 @@
+/* ScummVM - Graphic Adventure Engine
+*
+* ScummVM is the legal property of its developers, whose names
+* are too numerous to list here. Please refer to the COPYRIGHT
+* file distributed with this source distribution.
+*
+* This program is free software; you can redistribute it and/or
+* modify it under the terms of the GNU General Public License
+* as published by the Free Software Foundation; either version 2
+* of the License, or (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program; if not, write to the Free Software
+* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+*
+*/
+
+/*
+* Based on the Reverse Engineering work of Christophe Fontanel,
+* maintainer of the Dungeon Master Encyclopaedia (http://dmweb.free.fr/)
+*/
+
+#include "common/config-manager.h"
+#include "common/error.h"
+#include "common/fs.h"
+#include "common/system.h"
+
+#include "engines/advancedDetector.h"
+
+#include "dm/dm.h"
+
+namespace DM {
+
+class DMMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "dm";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
+		if (desc)
+			*engine = new DM::DMEngine(syst, (const DMADGameDescription*)desc);
+		return desc != nullptr;
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override {
+		return
+			(f == kSupportsListSaves) ||
+			(f == kSupportsLoadingDuringStartup) ||
+			(f == kSavesSupportThumbnail) ||
+			(f == kSavesSupportMetaInfo) ||
+			(f == kSavesSupportCreationDate);
+	}
+
+	int getMaximumSaveSlot() const override { return 99; }
+
+	SaveStateList listSaves(const char *target) const override {
+		Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+		SaveGameHeader header;
+		Common::String pattern = target;
+		pattern += ".###";
+
+		Common::StringArray filenames;
+		filenames = saveFileMan->listSavefiles(pattern.c_str());
+
+		SaveStateList saveList;
+
+		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+			// Obtain the last 3 digits of the filename, since they correspond to the save slot
+			int slotNum = atoi(file->c_str() + file->size() - 3);
+
+			if ((slotNum >= 0) && (slotNum <= 999)) {
+				Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
+				if (in) {
+					if (DM::readSaveGameHeader(in, &header))
+						saveList.push_back(SaveStateDescriptor(slotNum, header._descr.getDescription()));
+					delete in;
+				}
+			}
+		}
+
+		// Sort saves based on slot number.
+		Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+		return saveList;
+	}
+
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
+		Common::String filename = Common::String::format("%s.%03u", target, slot);
+		Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
+
+		if (in) {
+			DM::SaveGameHeader header;
+
+			bool successfulRead = DM::readSaveGameHeader(in, &header);
+			delete in;
+
+			if (successfulRead) {
+				SaveStateDescriptor desc(slot, header._descr.getDescription());
+
+				return header._descr;
+			}
+		}
+
+		return SaveStateDescriptor();
+	}
+
+	void removeSaveState(const char *target, int slot) const override {}
+
+};
+
+} // End of namespace DM
+
+#if PLUGIN_ENABLED_DYNAMIC(DM)
+	REGISTER_PLUGIN_DYNAMIC(DM, PLUGIN_TYPE_ENGINE, DM::DMMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(DM, PLUGIN_TYPE_ENGINE, DM::DMMetaEngineConnect);
+#endif
diff --git a/engines/dm/module.mk b/engines/dm/module.mk
index d495284da5..95688dada9 100644
--- a/engines/dm/module.mk
+++ b/engines/dm/module.mk
@@ -31,7 +31,6 @@ MODULE := engines/dm
 MODULE_OBJS := \
 	champion.o \
 	console.o \
-	detection.o \
 	dialog.o \
 	dm.o \
 	dmglobals.o \
@@ -43,6 +42,7 @@ MODULE_OBJS := \
 	loadsave.o \
 	lzw.o \
 	menus.o \
+	metaengine.o \
 	movesens.o \
 	objectman.o \
 	projexpl.o \
@@ -61,3 +61,5 @@ endif
 # Include common rules
 include $(srcdir)/rules.mk
 
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 8eb9ae7c984ac8059b2cb3db244f440f446b4f5c
    https://github.com/scummvm/scummvm/commit/8eb9ae7c984ac8059b2cb3db244f440f446b4f5c
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DRACI: Split detection features & adapt to new plugins.

Changed paths:
  A engines/draci/metaengine.cpp
    configure
    engines/draci/detection.cpp
    engines/draci/module.mk


diff --git a/configure b/configure
index 529829d481..56bc853798 100755
--- a/configure
+++ b/configure
@@ -6162,7 +6162,7 @@ done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
-								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM")
+								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/draci/detection.cpp b/engines/draci/detection.cpp
index 06e230b5bc..d34cbf3ba2 100644
--- a/engines/draci/detection.cpp
+++ b/engines/draci/detection.cpp
@@ -20,11 +20,8 @@
  *
  */
 
-#include "draci/draci.h"
-#include "draci/saveload.h"
-
 #include "base/plugins.h"
-#include "common/system.h"
+
 #include "engines/advancedDetector.h"
 #include "engines/metaengine.h"
 
@@ -97,102 +94,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Draci Historie (C) 1995 NoSense";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	int getMaximumSaveSlot() const override { return 99; }
-	SaveStateList listSaves(const char *target) const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool DraciMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSupportsLoadingDuringStartup);
-}
-
-SaveStateList DraciMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern("draci.s##");
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-
-		if (slotNum >= 0 && slotNum <= 99) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				Draci::DraciSavegameHeader header;
-				if (Draci::readSavegameHeader(in, header)) {
-					saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
-				}
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void DraciMetaEngine::removeSaveState(const char *target, int slot) const {
-	g_system->getSavefileManager()->removeSavefile(Draci::DraciEngine::getSavegameFile(slot));
-}
-
-SaveStateDescriptor DraciMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(
-		Draci::DraciEngine::getSavegameFile(slot));
-
-	if (f) {
-		Draci::DraciSavegameHeader header;
-		if (!Draci::readSavegameHeader(f, header, false)) {
-			delete f;
-			return SaveStateDescriptor();
-		}
-
-		delete f;
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header.saveName);
-		desc.setThumbnail(header.thumbnail);
-
-		int day = (header.date >> 24) & 0xFF;
-		int month = (header.date >> 16) & 0xFF;
-		int year = header.date & 0xFFFF;
-		desc.setSaveDate(year, month, day);
-
-		int hour = (header.time >> 8) & 0xFF;
-		int minutes = header.time & 0xFF;
-		desc.setSaveTime(hour, minutes);
-
-		desc.setPlayTime(header.playtime * 1000);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-bool DraciMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Draci::DraciEngine(syst, desc);
-	}
-	return desc != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(DRACI)
-	REGISTER_PLUGIN_DYNAMIC(DRACI, PLUGIN_TYPE_ENGINE, DraciMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(DRACI, PLUGIN_TYPE_ENGINE, DraciMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(DRACI_DETECTION, PLUGIN_TYPE_METAENGINE, DraciMetaEngine);
diff --git a/engines/draci/metaengine.cpp b/engines/draci/metaengine.cpp
new file mode 100644
index 0000000000..1a2bfdfb80
--- /dev/null
+++ b/engines/draci/metaengine.cpp
@@ -0,0 +1,134 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "draci/draci.h"
+#include "draci/saveload.h"
+
+#include "base/plugins.h"
+#include "common/system.h"
+#include "engines/advancedDetector.h"
+#include "engines/metaengine.h"
+
+class DraciMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "draci";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	int getMaximumSaveSlot() const override { return 99; }
+	SaveStateList listSaves(const char *target) const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool DraciMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSupportsLoadingDuringStartup);
+}
+
+SaveStateList DraciMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern("draci.s##");
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+
+		if (slotNum >= 0 && slotNum <= 99) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				Draci::DraciSavegameHeader header;
+				if (Draci::readSavegameHeader(in, header)) {
+					saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
+				}
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void DraciMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	g_system->getSavefileManager()->removeSavefile(Draci::DraciEngine::getSavegameFile(slot));
+}
+
+SaveStateDescriptor DraciMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(
+		Draci::DraciEngine::getSavegameFile(slot));
+
+	if (f) {
+		Draci::DraciSavegameHeader header;
+		if (!Draci::readSavegameHeader(f, header, false)) {
+			delete f;
+			return SaveStateDescriptor();
+		}
+
+		delete f;
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header.saveName);
+		desc.setThumbnail(header.thumbnail);
+
+		int day = (header.date >> 24) & 0xFF;
+		int month = (header.date >> 16) & 0xFF;
+		int year = header.date & 0xFFFF;
+		desc.setSaveDate(year, month, day);
+
+		int hour = (header.time >> 8) & 0xFF;
+		int minutes = header.time & 0xFF;
+		desc.setSaveTime(hour, minutes);
+
+		desc.setPlayTime(header.playtime * 1000);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+bool DraciMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Draci::DraciEngine(syst, desc);
+	}
+	return desc != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(DRACI)
+	REGISTER_PLUGIN_DYNAMIC(DRACI, PLUGIN_TYPE_ENGINE, DraciMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(DRACI, PLUGIN_TYPE_ENGINE, DraciMetaEngineConnect);
+#endif
diff --git a/engines/draci/module.mk b/engines/draci/module.mk
index 9bac1d9ddc..43afb8cbe3 100644
--- a/engines/draci/module.mk
+++ b/engines/draci/module.mk
@@ -4,10 +4,10 @@ MODULE_OBJS := \
 	animation.o \
 	barchive.o \
 	console.o \
-	detection.o \
 	draci.o \
 	font.o \
 	game.o \
+	metaengine.o \
 	mouse.o \
 	music.o \
 	saveload.o \
@@ -25,3 +25,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 794909c7fc78deb1120884131a7850b3c3bbc781
    https://github.com/scummvm/scummvm/commit/794909c7fc78deb1120884131a7850b3c3bbc781
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DRAGONS: Move common game-detection code to new header files.

Changed paths:
  A engines/dragons/detection.h
  A engines/dragons/detection_enums.h
    engines/dragons/dragons.h


diff --git a/engines/dragons/detection.h b/engines/dragons/detection.h
new file mode 100644
index 0000000000..aee353b6ec
--- /dev/null
+++ b/engines/dragons/detection.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Dragons {
+
+struct DragonsGameDescription {
+	ADGameDescription desc;
+	int gameId;
+};
+
+} // End of namespace Dragons
diff --git a/engines/dragons/detection_enums.h b/engines/dragons/detection_enums.h
new file mode 100644
index 0000000000..8f595b2616
--- /dev/null
+++ b/engines/dragons/detection_enums.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Dragons {
+
+enum {
+	kGameIdDragons = 1,
+	kGameIdDragonsBadExtraction = 2
+};
+
+} // End of namespace Dragons
diff --git a/engines/dragons/dragons.h b/engines/dragons/dragons.h
index 44feeed7b8..c3b2883c93 100644
--- a/engines/dragons/dragons.h
+++ b/engines/dragons/dragons.h
@@ -25,19 +25,11 @@
 #include "gui/EventRecorder.h"
 #include "engines/engine.h"
 #include "dragons/specialopcodes.h"
+#include "dragons/detection_enums.h"
+#include "dragons/detection.h"
 
 namespace Dragons {
 
-enum {
-	kGameIdDragons = 1,
-	kGameIdDragonsBadExtraction = 2
-};
-
-struct DragonsGameDescription {
-	ADGameDescription desc;
-	int gameId;
-};
-
 struct SaveHeader {
 	Common::String description;
 	uint32 version;


Commit: cf69fce865f282473c7a105a9a6e7b65ea40561f
    https://github.com/scummvm/scummvm/commit/cf69fce865f282473c7a105a9a6e7b65ea40561f
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DRAGONS: Split detection features & adapt to new plugins.

Changed paths:
  A engines/dragons/metaengine.cpp
    configure
    engines/dragons/detection.cpp
    engines/dragons/module.mk


diff --git a/configure b/configure
index 56bc853798..210cb3ce87 100755
--- a/configure
+++ b/configure
@@ -6162,7 +6162,7 @@ done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
-								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI")
+								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/dragons/detection.cpp b/engines/dragons/detection.cpp
index 245eaf0984..75c6f1861a 100644
--- a/engines/dragons/detection.cpp
+++ b/engines/dragons/detection.cpp
@@ -20,16 +20,10 @@
  *
  */
 
-#include "dragons/dragons.h"
 #include "engines/advancedDetector.h"
-#include "common/savefile.h"
-#include "common/system.h"
-#include "common/translation.h"
-#include "backends/keymapper/action.h"
-#include "backends/keymapper/keymapper.h"
-#include "backends/keymapper/standard-actions.h"
 #include "base/plugins.h"
-#include "graphics/thumbnail.h"
+#include "dragons/detection_enums.h"
+#include "dragons/detection.h"
 
 static const PlainGameDescriptor dragonsGames[] = {
 		{ "dragons", "Blazing Dragons" },
@@ -148,207 +142,6 @@ public:
 	virtual const char *getOriginalCopyright() const override {
 		return "(C) 1996 The Illusions Gaming Company";
 	}
-
-	virtual bool hasFeature(MetaEngineFeature f) const override;
-	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	virtual int getMaximumSaveSlot() const override;
-	virtual SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	virtual void removeSaveState(const char *target, int slot) const override;
-	Common::KeymapArray initKeymaps(const char *target) const override;
 };
 
-bool DragonsMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-			(f == kSupportsListSaves) ||
-			(f == kSupportsDeleteSave) ||
-			(f == kSupportsLoadingDuringStartup) ||
-			(f == kSavesSupportMetaInfo) ||
-			(f == kSavesSupportThumbnail) ||
-			(f == kSavesSupportCreationDate);
-}
-
-void DragonsMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-int DragonsMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-SaveStateList DragonsMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Dragons::SaveHeader header;
-	Common::String pattern = target;
-	pattern += ".???";
-	Common::StringArray filenames;
-	filenames = saveFileMan->listSavefiles(pattern.c_str());
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
-			if (in) {
-				if (Dragons::DragonsEngine::readSaveHeader(in, header) == Dragons::kRSHENoError) {
-					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
-				}
-				delete in;
-			}
-		}
-	}
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor DragonsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Dragons::DragonsEngine::getSavegameFilename(target, slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
-	if (in) {
-		Dragons::SaveHeader header;
-		Dragons::kReadSaveHeaderError error;
-		error = Dragons::DragonsEngine::readSaveHeader(in, header, false);
-		delete in;
-		if (error == Dragons::kRSHENoError) {
-			SaveStateDescriptor desc(slot, header.description);
-			// Slot 0 is used for the "Continue" save
-			desc.setDeletableFlag(slot != 0);
-			desc.setWriteProtectedFlag(slot == 0);
-			desc.setThumbnail(header.thumbnail);
-			desc.setSaveDate(header.saveDate & 0xFFFF, (header.saveDate >> 16) & 0xFF, (header.saveDate >> 24) & 0xFF);
-			desc.setSaveTime((header.saveTime >> 16) & 0xFF, (header.saveTime >> 8) & 0xFF);
-			desc.setPlayTime(header.playTime * 1000);
-			return desc;
-		}
-	}
-	return SaveStateDescriptor();
-}
-
-bool DragonsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Dragons::DragonsGameDescription *gd = (const Dragons::DragonsGameDescription *)desc;
-	if (gd) {
-		switch (gd->gameId) {
-		case Dragons::kGameIdDragons:
-			*engine = new Dragons::DragonsEngine(syst, desc);
-			break;
-		case Dragons::kGameIdDragonsBadExtraction:
-			GUIErrorMessageWithURL(_("Error: It appears that the game data files were extracted incorrectly.\n\nYou should only extract STR and XA files using the special method. The rest should be copied normally from your game CD.\n\n See https://wiki.scummvm.org/index.php?title=Datafiles#Blazing_Dragons"),
-								   "https://wiki.scummvm.org/index.php?title=Datafiles#Blazing_Dragons");
-			break;
-		default:
-			error("Unknown game id");
-			break;
-		}
-	}
-	return desc != 0;
-}
-
-Common::KeymapArray DragonsMetaEngine::initKeymaps(const char *target) const {
-	using namespace Common;
-
-	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "dragons", "Blazing Dragons");
-
-	Action *act;
-
-	act = new Action("LCLK", _("Action"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionSelect);
-	act->addDefaultInputMapping("MOUSE_LEFT");
-	act->addDefaultInputMapping("JOY_A");
-	engineKeyMap->addAction(act);
-
-	act = new Action("CHANGECOMMAND", _("Change Command"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionChangeCommand);
-	act->addDefaultInputMapping("MOUSE_RIGHT");
-	act->addDefaultInputMapping("JOY_B");
-	engineKeyMap->addAction(act);
-
-	act = new Action("INVENTORY", _("Inventory"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionInventory);
-	act->addDefaultInputMapping("i");
-	engineKeyMap->addAction(act);
-
-	act = new Action("ENTER", _("Enter"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionEnter);
-	act->addDefaultInputMapping("RETURN");
-	act->addDefaultInputMapping("KP_ENTER");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveUp, _("Up"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionUp);
-	act->addDefaultInputMapping("UP");
-	act->addDefaultInputMapping("JOY_UP");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveDown, _("Down"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionDown);
-	act->addDefaultInputMapping("DOWN");
-	act->addDefaultInputMapping("JOY_DOWN");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveLeft, _("Left"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionLeft);
-	act->addDefaultInputMapping("LEFT");
-	act->addDefaultInputMapping("JOY_LEFT");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveRight, _("Right"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionRight);
-	act->addDefaultInputMapping("RIGHT");
-	act->addDefaultInputMapping("JOY_RIGHT");
-	engineKeyMap->addAction(act);
-
-	act = new Action("SQUARE", _("Square"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionSquare);
-	act->addDefaultInputMapping("a");
-	act->addDefaultInputMapping("JOY_X");
-	engineKeyMap->addAction(act);
-
-	act = new Action("TRIANGLE", _("Triangle"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionTriangle);
-	act->addDefaultInputMapping("w");
-	act->addDefaultInputMapping("JOY_Y");
-	engineKeyMap->addAction(act);
-
-	act = new Action("CIRCLE", _("Circle"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionCircle);
-	act->addDefaultInputMapping("d");
-	act->addDefaultInputMapping("JOY_B");
-	engineKeyMap->addAction(act);
-
-	act = new Action("CROSS", _("Cross"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionCross);
-	act->addDefaultInputMapping("s");
-	act->addDefaultInputMapping("JOY_A");
-	engineKeyMap->addAction(act);
-
-	act = new Action("L1", _("Left Shoulder"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionL1);
-	act->addDefaultInputMapping("o");
-	act->addDefaultInputMapping("JOY_LEFT_SHOULDER");
-	engineKeyMap->addAction(act);
-
-	act = new Action("R1", _("Right Shoulder"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionR1);
-	act->addDefaultInputMapping("p");
-	act->addDefaultInputMapping("JOY_RIGHT_SHOULDER");
-	engineKeyMap->addAction(act);
-
-	act = new Action("DEBUGGFX", _("Debug Graphics"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionDebugGfx);
-	act->addDefaultInputMapping("TAB");
-	engineKeyMap->addAction(act);
-
-	act = new Action("QUIT", _("Quit Game"));
-	act->setCustomEngineActionEvent(Dragons::kDragonsActionQuit);
-	act->addDefaultInputMapping("C+q");
-	engineKeyMap->addAction(act);
-
-	return Keymap::arrayOf(engineKeyMap);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(DRAGONS)
-	REGISTER_PLUGIN_DYNAMIC(DRAGONS, PLUGIN_TYPE_ENGINE, DragonsMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(DRAGONS, PLUGIN_TYPE_ENGINE, DragonsMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(DRAGONS_DETECTION, PLUGIN_TYPE_METAENGINE, DragonsMetaEngine);
diff --git a/engines/dragons/metaengine.cpp b/engines/dragons/metaengine.cpp
new file mode 100644
index 0000000000..d8d3ef7066
--- /dev/null
+++ b/engines/dragons/metaengine.cpp
@@ -0,0 +1,242 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "dragons/dragons.h"
+#include "engines/advancedDetector.h"
+#include "common/savefile.h"
+#include "common/system.h"
+#include "common/translation.h"
+#include "backends/keymapper/action.h"
+#include "backends/keymapper/keymapper.h"
+#include "backends/keymapper/standard-actions.h"
+#include "base/plugins.h"
+#include "graphics/thumbnail.h"
+
+class DragonsMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const {
+		return "dragons";
+	}
+
+	virtual bool hasFeature(MetaEngineFeature f) const override;
+	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	virtual int getMaximumSaveSlot() const override;
+	virtual SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	virtual void removeSaveState(const char *target, int slot) const override;
+	Common::KeymapArray initKeymaps(const char *target) const override;
+};
+
+bool DragonsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+			(f == kSupportsListSaves) ||
+			(f == kSupportsDeleteSave) ||
+			(f == kSupportsLoadingDuringStartup) ||
+			(f == kSavesSupportMetaInfo) ||
+			(f == kSavesSupportThumbnail) ||
+			(f == kSavesSupportCreationDate);
+}
+
+void DragonsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+int DragonsMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+SaveStateList DragonsMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Dragons::SaveHeader header;
+	Common::String pattern = target;
+	pattern += ".???";
+	Common::StringArray filenames;
+	filenames = saveFileMan->listSavefiles(pattern.c_str());
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
+			if (in) {
+				if (Dragons::DragonsEngine::readSaveHeader(in, header) == Dragons::kRSHENoError) {
+					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
+				}
+				delete in;
+			}
+		}
+	}
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor DragonsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Dragons::DragonsEngine::getSavegameFilename(target, slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
+	if (in) {
+		Dragons::SaveHeader header;
+		Dragons::kReadSaveHeaderError error;
+		error = Dragons::DragonsEngine::readSaveHeader(in, header, false);
+		delete in;
+		if (error == Dragons::kRSHENoError) {
+			SaveStateDescriptor desc(slot, header.description);
+			// Slot 0 is used for the "Continue" save
+			desc.setDeletableFlag(slot != 0);
+			desc.setWriteProtectedFlag(slot == 0);
+			desc.setThumbnail(header.thumbnail);
+			desc.setSaveDate(header.saveDate & 0xFFFF, (header.saveDate >> 16) & 0xFF, (header.saveDate >> 24) & 0xFF);
+			desc.setSaveTime((header.saveTime >> 16) & 0xFF, (header.saveTime >> 8) & 0xFF);
+			desc.setPlayTime(header.playTime * 1000);
+			return desc;
+		}
+	}
+	return SaveStateDescriptor();
+}
+
+bool DragonsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Dragons::DragonsGameDescription *gd = (const Dragons::DragonsGameDescription *)desc;
+	if (gd) {
+		switch (gd->gameId) {
+		case Dragons::kGameIdDragons:
+			*engine = new Dragons::DragonsEngine(syst, desc);
+			break;
+		case Dragons::kGameIdDragonsBadExtraction:
+			GUIErrorMessageWithURL(_("Error: It appears that the game data files were extracted incorrectly.\n\nYou should only extract STR and XA files using the special method. The rest should be copied normally from your game CD.\n\n See https://wiki.scummvm.org/index.php?title=Datafiles#Blazing_Dragons"),
+								   "https://wiki.scummvm.org/index.php?title=Datafiles#Blazing_Dragons");
+			break;
+		default:
+			error("Unknown game id");
+			break;
+		}
+	}
+	return desc != 0;
+}
+
+Common::KeymapArray DragonsMetaEngineConnect::initKeymaps(const char *target) const {
+	using namespace Common;
+
+	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "dragons", "Blazing Dragons");
+
+	Action *act;
+
+	act = new Action("LCLK", _("Action"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionSelect);
+	act->addDefaultInputMapping("MOUSE_LEFT");
+	act->addDefaultInputMapping("JOY_A");
+	engineKeyMap->addAction(act);
+
+	act = new Action("CHANGECOMMAND", _("Change Command"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionChangeCommand);
+	act->addDefaultInputMapping("MOUSE_RIGHT");
+	act->addDefaultInputMapping("JOY_B");
+	engineKeyMap->addAction(act);
+
+	act = new Action("INVENTORY", _("Inventory"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionInventory);
+	act->addDefaultInputMapping("i");
+	engineKeyMap->addAction(act);
+
+	act = new Action("ENTER", _("Enter"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionEnter);
+	act->addDefaultInputMapping("RETURN");
+	act->addDefaultInputMapping("KP_ENTER");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveUp, _("Up"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionUp);
+	act->addDefaultInputMapping("UP");
+	act->addDefaultInputMapping("JOY_UP");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveDown, _("Down"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionDown);
+	act->addDefaultInputMapping("DOWN");
+	act->addDefaultInputMapping("JOY_DOWN");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveLeft, _("Left"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionLeft);
+	act->addDefaultInputMapping("LEFT");
+	act->addDefaultInputMapping("JOY_LEFT");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveRight, _("Right"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionRight);
+	act->addDefaultInputMapping("RIGHT");
+	act->addDefaultInputMapping("JOY_RIGHT");
+	engineKeyMap->addAction(act);
+
+	act = new Action("SQUARE", _("Square"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionSquare);
+	act->addDefaultInputMapping("a");
+	act->addDefaultInputMapping("JOY_X");
+	engineKeyMap->addAction(act);
+
+	act = new Action("TRIANGLE", _("Triangle"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionTriangle);
+	act->addDefaultInputMapping("w");
+	act->addDefaultInputMapping("JOY_Y");
+	engineKeyMap->addAction(act);
+
+	act = new Action("CIRCLE", _("Circle"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionCircle);
+	act->addDefaultInputMapping("d");
+	act->addDefaultInputMapping("JOY_B");
+	engineKeyMap->addAction(act);
+
+	act = new Action("CROSS", _("Cross"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionCross);
+	act->addDefaultInputMapping("s");
+	act->addDefaultInputMapping("JOY_A");
+	engineKeyMap->addAction(act);
+
+	act = new Action("L1", _("Left Shoulder"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionL1);
+	act->addDefaultInputMapping("o");
+	act->addDefaultInputMapping("JOY_LEFT_SHOULDER");
+	engineKeyMap->addAction(act);
+
+	act = new Action("R1", _("Right Shoulder"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionR1);
+	act->addDefaultInputMapping("p");
+	act->addDefaultInputMapping("JOY_RIGHT_SHOULDER");
+	engineKeyMap->addAction(act);
+
+	act = new Action("DEBUGGFX", _("Debug Graphics"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionDebugGfx);
+	act->addDefaultInputMapping("TAB");
+	engineKeyMap->addAction(act);
+
+	act = new Action("QUIT", _("Quit Game"));
+	act->setCustomEngineActionEvent(Dragons::kDragonsActionQuit);
+	act->addDefaultInputMapping("C+q");
+	engineKeyMap->addAction(act);
+
+	return Keymap::arrayOf(engineKeyMap);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(DRAGONS)
+	REGISTER_PLUGIN_DYNAMIC(DRAGONS, PLUGIN_TYPE_ENGINE, DragonsMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(DRAGONS, PLUGIN_TYPE_ENGINE, DragonsMetaEngineConnect);
+#endif
diff --git a/engines/dragons/module.mk b/engines/dragons/module.mk
index d87d67b15b..e05786f525 100644
--- a/engines/dragons/module.mk
+++ b/engines/dragons/module.mk
@@ -9,7 +9,6 @@ MODULE_OBJS := \
 	credits.o \
 	cursor.o \
 	cutscene.o \
-	detection.o \
 	dragonflg.o \
 	dragonimg.o \
 	dragonini.o \
@@ -19,6 +18,7 @@ MODULE_OBJS := \
 	dragons.o \
 	font.o \
 	inventory.o \
+	metaengine.o \
 	midimusicplayer.o \
 	minigame1.o \
 	minigame2.o \
@@ -43,3 +43,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 1c06bc6e75db634ec919a2d81572bff04f687c86
    https://github.com/scummvm/scummvm/commit/1c06bc6e75db634ec919a2d81572bff04f687c86
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GNAP: Split detection features & adapt to new plugins.

Changed paths:
  A engines/gnap/metaengine.cpp
    configure
    engines/gnap/detection.cpp
    engines/gnap/module.mk


diff --git a/configure b/configure
index 210cb3ce87..6dfb99971b 100755
--- a/configure
+++ b/configure
@@ -6162,7 +6162,7 @@ done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
-								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS")
+								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/gnap/detection.cpp b/engines/gnap/detection.cpp
index 10b7a7438e..deeed2a0db 100644
--- a/engines/gnap/detection.cpp
+++ b/engines/gnap/detection.cpp
@@ -100,124 +100,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Gnap (C) Artech Digital Entertainment 1997";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool GnapMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Gnap::GnapEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-void GnapMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-int GnapMetaEngine::getMaximumSaveSlot() const { return 99; }
-
-SaveStateList GnapMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.0##", target);
-	Gnap::GnapSavegameHeader header;
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		const char *ext = strrchr(file->c_str(), '.');
-		int slot = ext ? atoi(ext + 1) : -1;
-
-		if (slot >= 0 && slot < getMaximumSaveSlot()) {
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-			if (in) {
-				if (Gnap::GnapEngine::readSavegameHeader(in, header))
-					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor GnapMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
-	if (file) {
-		char saveIdentBuffer[5];
-		file->read(saveIdentBuffer, 5);
-
-		int32 version = file->readByte();
-		if (version > GNAP_SAVEGAME_VERSION) {
-			delete file;
-			return SaveStateDescriptor();
-		}
-
-		Common::String saveName;
-		char ch;
-		while ((ch = (char)file->readByte()) != '\0')
-			saveName += ch;
-
-		SaveStateDescriptor desc(slot, saveName);
-
-		if (version != 1) {
-			Graphics::Surface *thumbnail;
-			if (!Graphics::loadThumbnail(*file, thumbnail)) {
-				delete file;
-				return SaveStateDescriptor();
-			}
-			desc.setThumbnail(thumbnail);
-		}
-
-		int year = file->readSint16LE();
-		int month = file->readSint16LE();
-		int day = file->readSint16LE();
-		int hour = file->readSint16LE();
-		int minutes = file->readSint16LE();
-
-		desc.setSaveDate(year, month, day);
-		desc.setSaveTime(hour, minutes);
-
-		delete file;
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-bool GnapMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Gnap::GnapEngine(syst, desc);
-	}
-	return desc != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(GNAP)
-	REGISTER_PLUGIN_DYNAMIC(GNAP, PLUGIN_TYPE_ENGINE, GnapMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(GNAP, PLUGIN_TYPE_ENGINE, GnapMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(GNAP_DETECTION, PLUGIN_TYPE_METAENGINE, GnapMetaEngine);
diff --git a/engines/gnap/metaengine.cpp b/engines/gnap/metaengine.cpp
new file mode 100644
index 0000000000..7d981081d7
--- /dev/null
+++ b/engines/gnap/metaengine.cpp
@@ -0,0 +1,158 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "gnap/gnap.h"
+
+#include "common/config-manager.h"
+#include "engines/advancedDetector.h"
+#include "common/savefile.h"
+#include "common/system.h"
+#include "base/plugins.h"
+#include "graphics/thumbnail.h"
+
+class GnapMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "gnap";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool GnapMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Gnap::GnapEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+void GnapMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+int GnapMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+
+SaveStateList GnapMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.0##", target);
+	Gnap::GnapSavegameHeader header;
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		const char *ext = strrchr(file->c_str(), '.');
+		int slot = ext ? atoi(ext + 1) : -1;
+
+		if (slot >= 0 && slot < getMaximumSaveSlot()) {
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+			if (in) {
+				if (Gnap::GnapEngine::readSavegameHeader(in, header))
+					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor GnapMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
+	if (file) {
+		char saveIdentBuffer[5];
+		file->read(saveIdentBuffer, 5);
+
+		int32 version = file->readByte();
+		if (version > GNAP_SAVEGAME_VERSION) {
+			delete file;
+			return SaveStateDescriptor();
+		}
+
+		Common::String saveName;
+		char ch;
+		while ((ch = (char)file->readByte()) != '\0')
+			saveName += ch;
+
+		SaveStateDescriptor desc(slot, saveName);
+
+		if (version != 1) {
+			Graphics::Surface *thumbnail;
+			if (!Graphics::loadThumbnail(*file, thumbnail)) {
+				delete file;
+				return SaveStateDescriptor();
+			}
+			desc.setThumbnail(thumbnail);
+		}
+
+		int year = file->readSint16LE();
+		int month = file->readSint16LE();
+		int day = file->readSint16LE();
+		int hour = file->readSint16LE();
+		int minutes = file->readSint16LE();
+
+		desc.setSaveDate(year, month, day);
+		desc.setSaveTime(hour, minutes);
+
+		delete file;
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+bool GnapMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Gnap::GnapEngine(syst, desc);
+	}
+	return desc != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(GNAP)
+	REGISTER_PLUGIN_DYNAMIC(GNAP, PLUGIN_TYPE_ENGINE, GnapMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(GNAP, PLUGIN_TYPE_ENGINE, GnapMetaEngineConnect);
+#endif
diff --git a/engines/gnap/module.mk b/engines/gnap/module.mk
index ab507cbf94..14f3aa5003 100644
--- a/engines/gnap/module.mk
+++ b/engines/gnap/module.mk
@@ -4,11 +4,11 @@ MODULE_OBJS := \
 	character.o \
 	datarchive.o \
 	debugger.o \
-	detection.o \
 	gamesys.o \
 	gnap.o \
 	grid.o \
 	menu.o \
+	metaengine.o \
 	music.o \
 	resource.o \
 	sound.o \
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 854a499307beeb6e64bba20c35b9528ae6cfd8a6
    https://github.com/scummvm/scummvm/commit/854a499307beeb6e64bba20c35b9528ae6cfd8a6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GRIFFON: Split detection features & adapt to new plugins.

Changed paths:
  A engines/griffon/metaengine.cpp
    configure
    engines/griffon/detection.cpp
    engines/griffon/module.mk


diff --git a/configure b/configure
index 6dfb99971b..bc867ae4bc 100755
--- a/configure
+++ b/configure
@@ -6162,7 +6162,8 @@ done
 
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
-								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP")
+								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
+								  "GRIFFON")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/griffon/detection.cpp b/engines/griffon/detection.cpp
index 282a40ec87..a41c397a10 100644
--- a/engines/griffon/detection.cpp
+++ b/engines/griffon/detection.cpp
@@ -21,22 +21,15 @@
  */
 
 #include "base/plugins.h"
-#include "common/config-manager.h"
-#include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "backends/keymapper/action.h"
-#include "backends/keymapper/keymap.h"
-#include "backends/keymapper/standard-actions.h"
-
-#include "griffon/griffon.h"
-
 static const PlainGameDescriptor griffonGames[] = {
 	{"griffon", "The Griffon Legend"},
 	{NULL, NULL}
 };
 
 namespace Griffon {
+
 static const ADGameDescription gameDescriptions[] = {
 	{
 		"griffon",
@@ -50,6 +43,7 @@ static const ADGameDescription gameDescriptions[] = {
 
 	AD_TABLE_END_MARKER
 };
+
 }
 
 class GriffonMetaEngine: public AdvancedMetaEngine {
@@ -65,116 +59,9 @@ public:
 		return "Griffon Engine";
 	}
 
-	int getMaximumSaveSlot() const override {
-		return ConfMan.getInt("autosave_period") ? 4 : 3;
-	}
-
 	const char *getOriginalCopyright() const override {
 		return "The Griffon Legend (c) 2005 Syn9 (Daniel Kennedy)";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-
-	virtual int getAutosaveSlot() const override {
-		return 4;
-	}
-	Common::String getSavegameFile(int saveGameIdx, const char *target = nullptr) const override;
-
-	Common::KeymapArray initKeymaps(const char *target) const override;
 };
 
-Common::String GriffonMetaEngine::getSavegameFile(int saveGameIdx, const char *target) const {
-	if (saveGameIdx == kSavegameFilePattern) {
-		// Pattern requested
-		return Common::String::format("%s.s##", target == nullptr ? getEngineId() : target);
-	} else {
-		// Specific filename requested
-		return Common::String::format("%s.s%02d", target == nullptr ? getEngineId() : target, saveGameIdx);
-	}
-}
-
-bool Griffon::GriffonEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool GriffonMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc)
-		*engine = new Griffon::GriffonEngine(syst);
-
-	return desc != nullptr;
-}
-
-Common::KeymapArray GriffonMetaEngine::initKeymaps(const char *target) const {
-	using namespace Common;
-
-	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "griffon", "The Griffon Legend");
-
-	Action *act;
-
-	act = new Action(kStandardActionSkip, _("Menu / Skip"));
-	act->setCustomEngineActionEvent(Griffon::kGriffonMenu);
-	act->addDefaultInputMapping("ESCAPE");
-	act->addDefaultInputMapping("JOY_Y");
-	engineKeyMap->addAction(act);
-
-	act = new Action("RETURN", _("Confirm"));
-	act->setCustomEngineActionEvent(Griffon::kGriffonConfirm);
-	act->addDefaultInputMapping("RETURN");
-	act->addDefaultInputMapping("JOY_X");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveUp, _("Up"));
-	act->setCustomEngineActionEvent(Griffon::kGriffonUp);
-	act->addDefaultInputMapping("UP");
-	act->addDefaultInputMapping("JOY_UP");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveDown, _("Down"));
-	act->setCustomEngineActionEvent(Griffon::kGriffonDown);
-	act->addDefaultInputMapping("DOWN");
-	act->addDefaultInputMapping("JOY_DOWN");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveLeft, _("Left"));
-	act->setCustomEngineActionEvent(Griffon::kGriffonLeft);
-	act->addDefaultInputMapping("LEFT");
-	act->addDefaultInputMapping("JOY_LEFT");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveRight, _("Right"));
-	act->setCustomEngineActionEvent(Griffon::kGriffonRight);
-	act->addDefaultInputMapping("RIGHT");
-	act->addDefaultInputMapping("JOY_RIGHT");
-	engineKeyMap->addAction(act);
-
-	act = new Action("ATTACK", _("Attack"));
-	act->setCustomEngineActionEvent(Griffon::kGriffonAttack);
-	act->addDefaultInputMapping("LCTRL");
-	act->addDefaultInputMapping("RCTRL");
-	act->addDefaultInputMapping("JOY_A");
-	engineKeyMap->addAction(act);
-
-	act = new Action("INVENTORY", _("Inventory"));
-	act->setCustomEngineActionEvent(Griffon::kGriffonInventory);
-	act->addDefaultInputMapping("LALT");
-	act->addDefaultInputMapping("RALT");
-	act->addDefaultInputMapping("JOY_B");
-	engineKeyMap->addAction(act);
-
-	act = new Action("SPEEDUP", _("Speed Up Cutscene"));
-	act->setCustomEngineActionEvent(Griffon::kGriffonCutsceneSpeedUp);
-	act->addDefaultInputMapping("LSHIFT");
-	act->addDefaultInputMapping("RSHIFT");
-	engineKeyMap->addAction(act);
-
-	return Keymap::arrayOf(engineKeyMap);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(GRIFFON)
-REGISTER_PLUGIN_DYNAMIC(GRIFFON, PLUGIN_TYPE_ENGINE, GriffonMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(GRIFFON, PLUGIN_TYPE_ENGINE, GriffonMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(GRIFFON_DETECTION, PLUGIN_TYPE_METAENGINE, GriffonMetaEngine);
diff --git a/engines/griffon/metaengine.cpp b/engines/griffon/metaengine.cpp
new file mode 100644
index 0000000000..1d63afd814
--- /dev/null
+++ b/engines/griffon/metaengine.cpp
@@ -0,0 +1,148 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+#include "common/config-manager.h"
+#include "engines/advancedDetector.h"
+
+#include "backends/keymapper/action.h"
+#include "backends/keymapper/keymap.h"
+#include "backends/keymapper/standard-actions.h"
+
+#include "griffon/griffon.h"
+
+class GriffonMetaEngineConnect: public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "griffon";
+	}
+
+    int getMaximumSaveSlot() const override {
+		return ConfMan.getInt("autosave_period") ? 4 : 3;
+	}
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	virtual int getAutosaveSlot() const override {
+		return 4;
+	}
+	Common::String getSavegameFile(int saveGameIdx, const char *target = nullptr) const override;
+
+	Common::KeymapArray initKeymaps(const char *target) const override;
+
+};
+
+Common::String GriffonMetaEngineConnect::getSavegameFile(int saveGameIdx, const char *target) const {
+	if (saveGameIdx == kSavegameFilePattern) {
+		// Pattern requested
+		return Common::String::format("%s.s##", target == nullptr ? getEngineId() : target);
+	} else {
+		// Specific filename requested
+		return Common::String::format("%s.s%02d", target == nullptr ? getEngineId() : target, saveGameIdx);
+	}
+}
+
+bool Griffon::GriffonEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool GriffonMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc)
+		*engine = new Griffon::GriffonEngine(syst);
+
+	return desc != nullptr;
+}
+
+Common::KeymapArray GriffonMetaEngineConnect::initKeymaps(const char *target) const {
+	using namespace Common;
+
+	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "griffon", "The Griffon Legend");
+
+	Action *act;
+
+	act = new Action(kStandardActionSkip, _("Menu / Skip"));
+	act->setCustomEngineActionEvent(Griffon::kGriffonMenu);
+	act->addDefaultInputMapping("ESCAPE");
+	act->addDefaultInputMapping("JOY_Y");
+	engineKeyMap->addAction(act);
+
+	act = new Action("RETURN", _("Confirm"));
+	act->setCustomEngineActionEvent(Griffon::kGriffonConfirm);
+	act->addDefaultInputMapping("RETURN");
+	act->addDefaultInputMapping("JOY_X");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveUp, _("Up"));
+	act->setCustomEngineActionEvent(Griffon::kGriffonUp);
+	act->addDefaultInputMapping("UP");
+	act->addDefaultInputMapping("JOY_UP");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveDown, _("Down"));
+	act->setCustomEngineActionEvent(Griffon::kGriffonDown);
+	act->addDefaultInputMapping("DOWN");
+	act->addDefaultInputMapping("JOY_DOWN");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveLeft, _("Left"));
+	act->setCustomEngineActionEvent(Griffon::kGriffonLeft);
+	act->addDefaultInputMapping("LEFT");
+	act->addDefaultInputMapping("JOY_LEFT");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveRight, _("Right"));
+	act->setCustomEngineActionEvent(Griffon::kGriffonRight);
+	act->addDefaultInputMapping("RIGHT");
+	act->addDefaultInputMapping("JOY_RIGHT");
+	engineKeyMap->addAction(act);
+
+	act = new Action("ATTACK", _("Attack"));
+	act->setCustomEngineActionEvent(Griffon::kGriffonAttack);
+	act->addDefaultInputMapping("LCTRL");
+	act->addDefaultInputMapping("RCTRL");
+	act->addDefaultInputMapping("JOY_A");
+	engineKeyMap->addAction(act);
+
+	act = new Action("INVENTORY", _("Inventory"));
+	act->setCustomEngineActionEvent(Griffon::kGriffonInventory);
+	act->addDefaultInputMapping("LALT");
+	act->addDefaultInputMapping("RALT");
+	act->addDefaultInputMapping("JOY_B");
+	engineKeyMap->addAction(act);
+
+	act = new Action("SPEEDUP", _("Speed Up Cutscene"));
+	act->setCustomEngineActionEvent(Griffon::kGriffonCutsceneSpeedUp);
+	act->addDefaultInputMapping("LSHIFT");
+	act->addDefaultInputMapping("RSHIFT");
+	engineKeyMap->addAction(act);
+
+	return Keymap::arrayOf(engineKeyMap);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(GRIFFON)
+	REGISTER_PLUGIN_DYNAMIC(GRIFFON, PLUGIN_TYPE_ENGINE, GriffonMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(GRIFFON, PLUGIN_TYPE_ENGINE, GriffonMetaEngineConnect);
+#endif
diff --git a/engines/griffon/module.mk b/engines/griffon/module.mk
index 0c6edeb0ae..a3ed512096 100644
--- a/engines/griffon/module.mk
+++ b/engines/griffon/module.mk
@@ -4,7 +4,6 @@ MODULE_OBJS := \
 	combat.o \
 	console.o \
 	cutscenes.o \
-	detection.o \
 	dialogs.o \
 	draw.o \
 	engine.o \
@@ -12,6 +11,7 @@ MODULE_OBJS := \
 	griffon.o \
 	input.o \
 	logic.o \
+	metaengine.o \
 	resources.o \
 	saveload.o \
 	sound.o
@@ -26,3 +26,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 563cef10710d7881da48fc1d054976aa2c9906a5
    https://github.com/scummvm/scummvm/commit/563cef10710d7881da48fc1d054976aa2c9906a5
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GROOVIE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/groovie/detection_enums.h
  A engines/groovie/metaengine.cpp
    configure
    engines/groovie/detection.cpp
    engines/groovie/detection.h
    engines/groovie/module.mk
    engines/groovie/script.h


diff --git a/configure b/configure
index bc867ae4bc..f5e433aeaf 100755
--- a/configure
+++ b/configure
@@ -6163,7 +6163,7 @@ done
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
-								  "GRIFFON")
+								  "GRIFFON" "GROOVIE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/groovie/detection.cpp b/engines/groovie/detection.cpp
index de4571c18f..e0e4479860 100644
--- a/engines/groovie/detection.cpp
+++ b/engines/groovie/detection.cpp
@@ -20,13 +20,12 @@
  *
  */
 
-#include "groovie/groovie.h"
-#include "groovie/detection.h"
-#include "groovie/saveload.h"
-
 #include "common/system.h"
 #include "common/translation.h"
 
+#include "engines/advancedDetector.h"
+#include "groovie/detection.h"
+
 namespace Groovie {
 
 #define GAMEOPTION_T7G_FAST_MOVIE_SPEED  GUIO_GAMEOPTIONS1
@@ -358,62 +357,8 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Groovie Engine (C) 1990-1996 Trilobyte";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool GroovieMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
-	if (gd) {
-		*engine = new GroovieEngine(syst, (const GroovieGameDescription *)gd);
-	}
-	return gd != 0;
-}
-
-bool GroovieMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo);
-}
-
-SaveStateList GroovieMetaEngine::listSaves(const char *target) const {
-	return SaveLoad::listValidSaves(target);
-}
-
-int GroovieMetaEngine::getMaximumSaveSlot() const {
-	return SaveLoad::getMaximumSlot();
-}
-
-void GroovieMetaEngine::removeSaveState(const char *target, int slot) const {
-	if (!SaveLoad::isSlotValid(slot)) {
-		// Invalid slot, do nothing
-		return;
-	}
-
-	Common::String filename = SaveLoad::getSlotSaveName(target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor GroovieMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	SaveStateDescriptor desc;
-
-	Common::InSaveFile *savefile = SaveLoad::openForLoading(target, slot, &desc);
-	delete savefile;
-
-	return desc;
-}
-
 } // End of namespace Groovie
 
-#if PLUGIN_ENABLED_DYNAMIC(GROOVIE)
-	REGISTER_PLUGIN_DYNAMIC(GROOVIE, PLUGIN_TYPE_ENGINE, Groovie::GroovieMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(GROOVIE, PLUGIN_TYPE_ENGINE, Groovie::GroovieMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(GROOVIE_DETECTION, PLUGIN_TYPE_METAENGINE, Groovie::GroovieMetaEngine);
diff --git a/engines/groovie/detection.h b/engines/groovie/detection.h
index e49474474b..9a61b36f3a 100644
--- a/engines/groovie/detection.h
+++ b/engines/groovie/detection.h
@@ -24,7 +24,7 @@
 #define GROOVIE_DETECTION_H
 
 #include "engines/advancedDetector.h"
-#include "groovie/script.h"	// for EngineVersion
+#include "groovie/detection_enums.h"	// for EngineVersion
 
 namespace Groovie {
 
diff --git a/engines/groovie/detection_enums.h b/engines/groovie/detection_enums.h
new file mode 100644
index 0000000000..1e23a0b463
--- /dev/null
+++ b/engines/groovie/detection_enums.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Groovie {
+
+enum EngineVersion {
+	kGroovieT7G,
+	kGroovieV2
+};
+
+} // End of namespace Groovie
diff --git a/engines/groovie/metaengine.cpp b/engines/groovie/metaengine.cpp
new file mode 100644
index 0000000000..316237f6a7
--- /dev/null
+++ b/engines/groovie/metaengine.cpp
@@ -0,0 +1,97 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "groovie/groovie.h"
+#include "groovie/saveload.h"
+
+#include "common/system.h"
+#include "common/translation.h"
+
+#include "engines/advancedDetector.h"
+#include "groovie/detection.h"
+
+namespace Groovie {
+
+class GroovieMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "groovie";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool GroovieMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+	if (gd) {
+		*engine = new GroovieEngine(syst, (const GroovieGameDescription *)gd);
+	}
+	return gd != 0;
+}
+
+bool GroovieMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo);
+}
+
+SaveStateList GroovieMetaEngineConnect::listSaves(const char *target) const {
+	return SaveLoad::listValidSaves(target);
+}
+
+int GroovieMetaEngineConnect::getMaximumSaveSlot() const {
+	return SaveLoad::getMaximumSlot();
+}
+
+void GroovieMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	if (!SaveLoad::isSlotValid(slot)) {
+		// Invalid slot, do nothing
+		return;
+	}
+
+	Common::String filename = SaveLoad::getSlotSaveName(target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor GroovieMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	SaveStateDescriptor desc;
+
+	Common::InSaveFile *savefile = SaveLoad::openForLoading(target, slot, &desc);
+	delete savefile;
+
+	return desc;
+}
+
+} // End of namespace Groovie
+
+#if PLUGIN_ENABLED_DYNAMIC(GROOVIE)
+	REGISTER_PLUGIN_DYNAMIC(GROOVIE, PLUGIN_TYPE_ENGINE, Groovie::GroovieMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(GROOVIE, PLUGIN_TYPE_ENGINE, Groovie::GroovieMetaEngineConnect);
+#endif
diff --git a/engines/groovie/module.mk b/engines/groovie/module.mk
index 84d6222c59..b01ac47a11 100644
--- a/engines/groovie/module.mk
+++ b/engines/groovie/module.mk
@@ -4,11 +4,11 @@ MODULE_OBJS := \
 	cell.o \
 	cursor.o \
 	debug.o \
-	detection.o \
 	font.o \
 	graphics.o \
 	groovie.o \
 	lzss.o \
+	metaengine.o \
 	music.o \
 	player.o \
 	resource.o \
@@ -29,3 +29,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/groovie/script.h b/engines/groovie/script.h
index a3bc5724e2..4b82a8ef50 100644
--- a/engines/groovie/script.h
+++ b/engines/groovie/script.h
@@ -24,6 +24,7 @@
 #define GROOVIE_SCRIPT_H
 
 #include "groovie/groovie.h"
+#include "groovie/detection_enums.h"
 
 #include "common/random.h"
 #include "common/rect.h"
@@ -38,11 +39,6 @@ struct Surface;
 
 namespace Groovie {
 
-enum EngineVersion {
-	kGroovieT7G,
-	kGroovieV2
-};
-
 class CellGame;
 class Debugger;
 


Commit: 509fd698276e54f700c97db3fabe4b5e7772cb41
    https://github.com/scummvm/scummvm/commit/509fd698276e54f700c97db3fabe4b5e7772cb41
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GROOVIE: Solve missing header dependencies.

Changed paths:
    engines/groovie/detection.cpp
    engines/groovie/detection.h
    engines/groovie/detection_enums.h
    engines/groovie/groovie.cpp
    engines/groovie/groovie.h


diff --git a/engines/groovie/detection.cpp b/engines/groovie/detection.cpp
index e0e4479860..c607181551 100644
--- a/engines/groovie/detection.cpp
+++ b/engines/groovie/detection.cpp
@@ -24,6 +24,7 @@
 #include "common/translation.h"
 
 #include "engines/advancedDetector.h"
+#include "groovie/detection_enums.h"
 #include "groovie/detection.h"
 
 namespace Groovie {
diff --git a/engines/groovie/detection.h b/engines/groovie/detection.h
index 9a61b36f3a..d840d06f15 100644
--- a/engines/groovie/detection.h
+++ b/engines/groovie/detection.h
@@ -24,7 +24,6 @@
 #define GROOVIE_DETECTION_H
 
 #include "engines/advancedDetector.h"
-#include "groovie/detection_enums.h"	// for EngineVersion
 
 namespace Groovie {
 
diff --git a/engines/groovie/detection_enums.h b/engines/groovie/detection_enums.h
index 1e23a0b463..57bcb89567 100644
--- a/engines/groovie/detection_enums.h
+++ b/engines/groovie/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef GROOVIE_DETECTION_ENUMS_H
+#define GROOVIE_DETECTION_ENUMS_H
+
 namespace Groovie {
 
 enum EngineVersion {
@@ -28,3 +31,5 @@ enum EngineVersion {
 };
 
 } // End of namespace Groovie
+
+#endif // !GROOVIE_DETECTION_ENUMS_H
diff --git a/engines/groovie/groovie.cpp b/engines/groovie/groovie.cpp
index 94bfa26766..f44a0a2759 100644
--- a/engines/groovie/groovie.cpp
+++ b/engines/groovie/groovie.cpp
@@ -24,6 +24,7 @@
 #include "groovie/cursor.h"
 #include "groovie/detection.h"
 #include "groovie/graphics.h"
+#include "groovie/script.h"
 #include "groovie/music.h"
 #include "groovie/resource.h"
 #include "groovie/stuffit.h"
diff --git a/engines/groovie/groovie.h b/engines/groovie/groovie.h
index 90696c5758..4d26552bf8 100644
--- a/engines/groovie/groovie.h
+++ b/engines/groovie/groovie.h
@@ -28,6 +28,7 @@
 
 #include "engines/engine.h"
 #include "graphics/pixelformat.h"
+#include "groovie/detection_enums.h"
 
 namespace Common {
 class MacResManager;


Commit: eb781526642fcd89698a048b20392623baba2fba
    https://github.com/scummvm/scummvm/commit/eb781526642fcd89698a048b20392623baba2fba
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
HDB: Split detection features & adapt to new plugins.

Changed paths:
  A engines/hdb/detection_enums.h
  A engines/hdb/metaengine.cpp
    configure
    engines/hdb/detection.cpp
    engines/hdb/module.mk


diff --git a/configure b/configure
index f5e433aeaf..e2e31a0cb2 100755
--- a/configure
+++ b/configure
@@ -6163,7 +6163,7 @@ done
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
-								  "GRIFFON" "GROOVIE")
+								  "GRIFFON" "GROOVIE" "HDB")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/hdb/detection.cpp b/engines/hdb/detection.cpp
index 438ec89e03..8f995787ae 100644
--- a/engines/hdb/detection.cpp
+++ b/engines/hdb/detection.cpp
@@ -21,50 +21,10 @@
  */
 
 #include "base/plugins.h"
-
-#include "common/debug.h"
 #include "common/translation.h"
-
-#include "backends/keymapper/action.h"
-#include "backends/keymapper/keymapper.h"
-#include "backends/keymapper/standard-actions.h"
-
 #include "engines/advancedDetector.h"
-#include "graphics/thumbnail.h"
-
-#include "hdb/hdb.h"
-#include "hdb/input.h"
-
-namespace HDB {
-
-enum HDBGameFeatures {
-	GF_HANDANGO = (1 << 0)
-};
 
-const char *HDBGame::getGameId() const { return _gameDescription->gameId; }
-Common::Platform HDBGame::getPlatform() const { return _gameDescription->platform; }
-
-const char *HDBGame::getGameFile() const {
-	return _gameDescription->filesDescriptions[0].fileName;
-}
-
-uint32 HDBGame::getGameFlags() const {
-	return _gameDescription->flags;
-}
-
-bool HDBGame::isDemo() const {
-	return (getGameFlags() & ADGF_DEMO);
-}
-
-bool HDBGame::isPPC() const {
-	return (getPlatform() == Common::kPlatformPocketPC);
-}
-
-bool HDBGame::isHandango() const {
-	return (getGameFlags() & GF_HANDANGO);
-}
-
-} // End of namespace HDB
+#include "hdb/detection_enums.h"
 
 static const PlainGameDescriptor hdbGames[] = {
 	{"hdb", "Hyperspace Delivery Boy!"},
@@ -74,6 +34,7 @@ static const PlainGameDescriptor hdbGames[] = {
 #define GAMEOPTION_CHEATMODE GUIO_GAMEOPTIONS1
 
 namespace HDB {
+
 static const ADGameDescription gameDescriptions[] = {
 	{
 		"hdb",
@@ -153,6 +114,7 @@ static const ADGameDescription gameDescriptions[] = {
 	},
 	AD_TABLE_END_MARKER
 };
+
 } // End of namespace HDB
 
 static const ADExtraGuiOptionsMap optionsList[] = {
@@ -185,207 +147,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Hyperspace Delivery Boy! (C) 2001 Monkeystone Games";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	Common::KeymapArray initKeymaps(const char *target) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool HDBMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsListSaves) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportPlayTime);
-}
-
-bool HDB::HDBGame::hasFeature(Engine::EngineFeature f) const {
-	return (f == kSupportsReturnToLauncher) ||
-		   (f == kSupportsLoadingDuringRuntime) ||
-		   (f == kSupportsSavingDuringRuntime);
-}
-
-void HDBMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-int HDBMetaEngine::getMaximumSaveSlot() const { return 99; }
-
-SaveStateList HDBMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-
-		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
-			Common::ScopedPtr<Common::InSaveFile> in(saveFileMan->openForLoading(*file));
-			if (in) {
-				SaveStateDescriptor desc;
-				char mapName[32];
-				Graphics::Surface *thumbnail;
-
-				if (!Graphics::loadThumbnail(*in, thumbnail)) {
-					warning("Error loading thumbnail for %s", file->c_str());
-				}
-				desc.setThumbnail(thumbnail);
-
-				uint32 timeSeconds = in->readUint32LE();;
-				in->read(mapName, 32);
-
-				debug(1, "mapName: %s playtime: %d", mapName, timeSeconds);
-
-				desc.setSaveSlot(slotNum);
-				desc.setPlayTime(timeSeconds * 1000);
-
-				if (slotNum < 8)
-					desc.setDescription(Common::String::format("Auto: %s", mapName));
-				else
-					desc.setDescription(mapName);
-
-				saveList.push_back(desc);
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor HDBMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::ScopedPtr<Common::InSaveFile> in(g_system->getSavefileManager()->openForLoading(Common::String::format("%s.%03d", target, slot)));
-
-	if (in) {
-		SaveStateDescriptor desc;
-		char mapName[32];
-		Graphics::Surface *thumbnail;
-
-		if (!Graphics::loadThumbnail(*in, thumbnail)) {
-			warning("Error loading thumbnail");
-		}
-		desc.setThumbnail(thumbnail);
-
-		uint32 timeSeconds = in->readUint32LE();
-		in->read(mapName, 32);
-
-		desc.setSaveSlot(slot);
-		desc.setPlayTime(timeSeconds * 1000);
-		desc.setDescription(mapName);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-Common::KeymapArray HDBMetaEngine::initKeymaps(const char *target) const {
-	using namespace Common;
-	using namespace HDB;
-
-	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "hdb", "Hyperspace Delivery Boy!");
-
-	Action *act;
-
-	act = new Action("LCLK", _("Left Click"));
-	act->setLeftClickEvent();
-	act->addDefaultInputMapping("MOUSE_LEFT");
-	act->addDefaultInputMapping("JOY_A");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveUp, _("Move up"));
-	act->setCustomEngineActionEvent(kHDBActionUp);
-	act->addDefaultInputMapping("UP");
-	act->addDefaultInputMapping("JOY_UP");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveDown, _("Move down"));
-	act->setCustomEngineActionEvent(kHDBActionDown);
-	act->addDefaultInputMapping("DOWN");
-	act->addDefaultInputMapping("JOY_DOWN");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveLeft, _("Move left"));
-	act->setCustomEngineActionEvent(kHDBActionLeft);
-	act->addDefaultInputMapping("LEFT");
-	act->addDefaultInputMapping("JOY_LEFT");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionMoveRight, _("Move right"));
-	act->setCustomEngineActionEvent(kHDBActionRight);
-	act->addDefaultInputMapping("RIGHT");
-	act->addDefaultInputMapping("JOY_RIGHT");
-	engineKeyMap->addAction(act);
-
-	act = new Action("USE", _("Use"));
-	act->setCustomEngineActionEvent(kHDBActionUse);
-	act->addDefaultInputMapping("RETURN");
-	act->addDefaultInputMapping("MOUSE_RIGHT");
-	act->addDefaultInputMapping("JOY_B");
-	engineKeyMap->addAction(act);
-
-	act = new Action("CLEAR", _("Clear waypoints"));
-	act->setCustomEngineActionEvent(kHDBActionClearWaypoints);
-	act->addDefaultInputMapping("MOUSE_MIDDLE");
-	act->addDefaultInputMapping("JOY_X");
-	engineKeyMap->addAction(act);
-
-#if 0
-	act = new Action("INV", _("Inventory"));
-	act->setCustomEngineActionEvent(kHDBActionInventory);
-	act->addDefaultInputMapping("SPACE");
-	act->addDefaultInputMapping("JOY_Y");
-	engineKeyMap->addAction(act);
-#endif
-
-	act = new Action(kStandardActionPause, _("Pause"));
-	act->setCustomEngineActionEvent(kHDBActionPause);
-	act->addDefaultInputMapping("p");
-	act->addDefaultInputMapping("JOY_LEFT_SHOULDER");
-	engineKeyMap->addAction(act);
-
-	act = new Action(kStandardActionOpenMainMenu, _("Menu"));
-	act->setCustomEngineActionEvent(kHDBActionMenu);
-	act->addDefaultInputMapping("ESCAPE");
-	act->addDefaultInputMapping("JOY_RIGHT_SHOULDER");
-	engineKeyMap->addAction(act);
-
-	act = new Action("DEBUG", _("Debug"));
-	act->setCustomEngineActionEvent(kHDBActionDebug);
-	act->addDefaultInputMapping("F1");
-	engineKeyMap->addAction(act);
-
-	act = new Action("QUIT", _("Quit"));
-	act->setCustomEngineActionEvent(kHDBActionQuit);
-	act->addDefaultInputMapping("F10");
-	engineKeyMap->addAction(act);
-
-	return Keymap::arrayOf(engineKeyMap);
-}
-
-bool HDBMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new HDB::HDBGame(syst, desc);
-	}
-
-	return desc != nullptr;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(HDB)
-REGISTER_PLUGIN_DYNAMIC(HDB, PLUGIN_TYPE_ENGINE, HDBMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(HDB, PLUGIN_TYPE_ENGINE, HDBMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(HDB_DETECTION, PLUGIN_TYPE_METAENGINE, HDBMetaEngine);
diff --git a/engines/hdb/detection_enums.h b/engines/hdb/detection_enums.h
new file mode 100644
index 0000000000..6ff21969d1
--- /dev/null
+++ b/engines/hdb/detection_enums.h
@@ -0,0 +1,9 @@
+
+
+namespace HDB {
+
+enum HDBGameFeatures {
+	GF_HANDANGO = (1 << 0)
+};
+
+} // End of namespace HDB
\ No newline at end of file
diff --git a/engines/hdb/metaengine.cpp b/engines/hdb/metaengine.cpp
new file mode 100644
index 0000000000..a83a0402fa
--- /dev/null
+++ b/engines/hdb/metaengine.cpp
@@ -0,0 +1,275 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "common/debug.h"
+#include "common/translation.h"
+
+#include "backends/keymapper/action.h"
+#include "backends/keymapper/keymapper.h"
+#include "backends/keymapper/standard-actions.h"
+
+#include "engines/advancedDetector.h"
+#include "graphics/thumbnail.h"
+
+#include "hdb/hdb.h"
+#include "hdb/input.h"
+#include "hdb/detection_enums.h"
+
+namespace HDB {
+
+const char *HDBGame::getGameId() const { return _gameDescription->gameId; }
+Common::Platform HDBGame::getPlatform() const { return _gameDescription->platform; }
+
+const char *HDBGame::getGameFile() const {
+	return _gameDescription->filesDescriptions[0].fileName;
+}
+
+uint32 HDBGame::getGameFlags() const {
+	return _gameDescription->flags;
+}
+
+bool HDBGame::isDemo() const {
+	return (getGameFlags() & ADGF_DEMO);
+}
+
+bool HDBGame::isPPC() const {
+	return (getPlatform() == Common::kPlatformPocketPC);
+}
+
+bool HDBGame::isHandango() const {
+	return (getGameFlags() & GF_HANDANGO);
+}
+
+} // End of namespace HDB
+
+class HDBMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "hdb";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	int getMaximumSaveSlot() const override;
+
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	Common::KeymapArray initKeymaps(const char *target) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool HDBMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsListSaves) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportPlayTime);
+}
+
+bool HDB::HDBGame::hasFeature(Engine::EngineFeature f) const {
+	return (f == kSupportsReturnToLauncher) ||
+		   (f == kSupportsLoadingDuringRuntime) ||
+		   (f == kSupportsSavingDuringRuntime);
+}
+
+void HDBMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+int HDBMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+
+SaveStateList HDBMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+
+		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
+			Common::ScopedPtr<Common::InSaveFile> in(saveFileMan->openForLoading(*file));
+			if (in) {
+				SaveStateDescriptor desc;
+				char mapName[32];
+				Graphics::Surface *thumbnail;
+
+				if (!Graphics::loadThumbnail(*in, thumbnail)) {
+					warning("Error loading thumbnail for %s", file->c_str());
+				}
+				desc.setThumbnail(thumbnail);
+
+				uint32 timeSeconds = in->readUint32LE();;
+				in->read(mapName, 32);
+
+				debug(1, "mapName: %s playtime: %d", mapName, timeSeconds);
+
+				desc.setSaveSlot(slotNum);
+				desc.setPlayTime(timeSeconds * 1000);
+
+				if (slotNum < 8)
+					desc.setDescription(Common::String::format("Auto: %s", mapName));
+				else
+					desc.setDescription(mapName);
+
+				saveList.push_back(desc);
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor HDBMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::ScopedPtr<Common::InSaveFile> in(g_system->getSavefileManager()->openForLoading(Common::String::format("%s.%03d", target, slot)));
+
+	if (in) {
+		SaveStateDescriptor desc;
+		char mapName[32];
+		Graphics::Surface *thumbnail;
+
+		if (!Graphics::loadThumbnail(*in, thumbnail)) {
+			warning("Error loading thumbnail");
+		}
+		desc.setThumbnail(thumbnail);
+
+		uint32 timeSeconds = in->readUint32LE();
+		in->read(mapName, 32);
+
+		desc.setSaveSlot(slot);
+		desc.setPlayTime(timeSeconds * 1000);
+		desc.setDescription(mapName);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+Common::KeymapArray HDBMetaEngineConnect::initKeymaps(const char *target) const {
+	using namespace Common;
+	using namespace HDB;
+
+	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "hdb", "Hyperspace Delivery Boy!");
+
+	Action *act;
+
+	act = new Action("LCLK", _("Left Click"));
+	act->setLeftClickEvent();
+	act->addDefaultInputMapping("MOUSE_LEFT");
+	act->addDefaultInputMapping("JOY_A");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveUp, _("Move up"));
+	act->setCustomEngineActionEvent(kHDBActionUp);
+	act->addDefaultInputMapping("UP");
+	act->addDefaultInputMapping("JOY_UP");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveDown, _("Move down"));
+	act->setCustomEngineActionEvent(kHDBActionDown);
+	act->addDefaultInputMapping("DOWN");
+	act->addDefaultInputMapping("JOY_DOWN");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveLeft, _("Move left"));
+	act->setCustomEngineActionEvent(kHDBActionLeft);
+	act->addDefaultInputMapping("LEFT");
+	act->addDefaultInputMapping("JOY_LEFT");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionMoveRight, _("Move right"));
+	act->setCustomEngineActionEvent(kHDBActionRight);
+	act->addDefaultInputMapping("RIGHT");
+	act->addDefaultInputMapping("JOY_RIGHT");
+	engineKeyMap->addAction(act);
+
+	act = new Action("USE", _("Use"));
+	act->setCustomEngineActionEvent(kHDBActionUse);
+	act->addDefaultInputMapping("RETURN");
+	act->addDefaultInputMapping("MOUSE_RIGHT");
+	act->addDefaultInputMapping("JOY_B");
+	engineKeyMap->addAction(act);
+
+	act = new Action("CLEAR", _("Clear waypoints"));
+	act->setCustomEngineActionEvent(kHDBActionClearWaypoints);
+	act->addDefaultInputMapping("MOUSE_MIDDLE");
+	act->addDefaultInputMapping("JOY_X");
+	engineKeyMap->addAction(act);
+
+#if 0
+	act = new Action("INV", _("Inventory"));
+	act->setCustomEngineActionEvent(kHDBActionInventory);
+	act->addDefaultInputMapping("SPACE");
+	act->addDefaultInputMapping("JOY_Y");
+	engineKeyMap->addAction(act);
+#endif
+
+	act = new Action(kStandardActionPause, _("Pause"));
+	act->setCustomEngineActionEvent(kHDBActionPause);
+	act->addDefaultInputMapping("p");
+	act->addDefaultInputMapping("JOY_LEFT_SHOULDER");
+	engineKeyMap->addAction(act);
+
+	act = new Action(kStandardActionOpenMainMenu, _("Menu"));
+	act->setCustomEngineActionEvent(kHDBActionMenu);
+	act->addDefaultInputMapping("ESCAPE");
+	act->addDefaultInputMapping("JOY_RIGHT_SHOULDER");
+	engineKeyMap->addAction(act);
+
+	act = new Action("DEBUG", _("Debug"));
+	act->setCustomEngineActionEvent(kHDBActionDebug);
+	act->addDefaultInputMapping("F1");
+	engineKeyMap->addAction(act);
+
+	act = new Action("QUIT", _("Quit"));
+	act->setCustomEngineActionEvent(kHDBActionQuit);
+	act->addDefaultInputMapping("F10");
+	engineKeyMap->addAction(act);
+
+	return Keymap::arrayOf(engineKeyMap);
+}
+
+bool HDBMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new HDB::HDBGame(syst, desc);
+	}
+
+	return desc != nullptr;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(HDB)
+	REGISTER_PLUGIN_DYNAMIC(HDB, PLUGIN_TYPE_ENGINE, HDBMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(HDB, PLUGIN_TYPE_ENGINE, HDBMetaEngineConnect);
+#endif
diff --git a/engines/hdb/module.mk b/engines/hdb/module.mk
index e3d95dbbae..24cc53bd41 100644
--- a/engines/hdb/module.mk
+++ b/engines/hdb/module.mk
@@ -10,7 +10,6 @@ MODULE_OBJS := \
 	ai-player.o \
 	ai-use.o \
 	ai-waypoint.o \
-	detection.o \
 	file-manager.o \
 	gfx.o \
 	hdb.o \
@@ -18,6 +17,7 @@ MODULE_OBJS := \
 	lua-script.o \
 	map.o \
 	menu.o \
+	metaengine.o \
 	sound.o \
 	saveload.o \
 	window.o
@@ -32,3 +32,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: eaa1ef09a5766e8f0f29c850effc9726f2d0fcf6
    https://github.com/scummvm/scummvm/commit/eaa1ef09a5766e8f0f29c850effc9726f2d0fcf6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
HOPKINS: Split detection features & adapt to new plugins.

Changed paths:
  A engines/hopkins/detection.h
  A engines/hopkins/metaengine.cpp
    configure
    engines/hopkins/detection.cpp
    engines/hopkins/module.mk


diff --git a/configure b/configure
index e2e31a0cb2..a22b05566a 100755
--- a/configure
+++ b/configure
@@ -6163,7 +6163,7 @@ done
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
-								  "GRIFFON" "GROOVIE" "HDB")
+								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/hopkins/detection.cpp b/engines/hopkins/detection.cpp
index 9e8fb5b90c..97fcb86eb9 100644
--- a/engines/hopkins/detection.cpp
+++ b/engines/hopkins/detection.cpp
@@ -20,46 +20,11 @@
  *
  */
 
-#include "hopkins/hopkins.h"
-
 #include "base/plugins.h"
-#include "common/savefile.h"
-#include "common/str-array.h"
-#include "common/memstream.h"
 #include "engines/advancedDetector.h"
-#include "common/system.h"
 #include "common/translation.h"
-#include "graphics/surface.h"
-
-#define MAX_SAVES 99
-
-namespace Hopkins {
-
-struct HopkinsGameDescription {
-	ADGameDescription desc;
-};
-
-uint32 HopkinsEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language HopkinsEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-Common::Platform HopkinsEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-bool HopkinsEngine::getIsDemo() const {
-	return _gameDescription->desc.flags & ADGF_DEMO;
-}
 
-const Common::String &HopkinsEngine::getTargetName() const {
-	return _targetName;
-}
-
-} // End of namespace Hopkins
+#include "hopkins/detection.h"
 
 static const PlainGameDescriptor hopkinsGames[] = {
 	{"hopkins", "Hopkins FBI"},
@@ -116,111 +81,7 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Hopkins FBI (C) 1997-2003 MP Entertainment";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool HopkinsMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Hopkins::HopkinsEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool HopkinsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Hopkins::HopkinsGameDescription *gd = (const Hopkins::HopkinsGameDescription *)desc;
-	if (gd) {
-		*engine = new Hopkins::HopkinsEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList HopkinsMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.0##", target);
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	Hopkins::hopkinsSavegameHeader header;
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		const char *ext = strrchr(file->c_str(), '.');
-		int slot = ext ? atoi(ext + 1) : -1;
-
-		if (slot >= 0 && slot < MAX_SAVES) {
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-			if (in) {
-				if (Hopkins::SaveLoadManager::readSavegameHeader(in, header)) {
-					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
-				}
-
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int HopkinsMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVES;
-}
-
-void HopkinsMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor HopkinsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
-
-	if (f) {
-		Hopkins::hopkinsSavegameHeader header;
-		if (!Hopkins::SaveLoadManager::readSavegameHeader(f, header, false)) {
-			delete f;
-			return SaveStateDescriptor();
-		}
-
-		delete f;
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header._saveName);
-		desc.setThumbnail(header._thumbnail);
-		desc.setSaveDate(header._year, header._month, header._day);
-		desc.setSaveTime(header._hour, header._minute);
-		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
 
-#if PLUGIN_ENABLED_DYNAMIC(HOPKINS)
-	REGISTER_PLUGIN_DYNAMIC(HOPKINS, PLUGIN_TYPE_ENGINE, HopkinsMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(HOPKINS, PLUGIN_TYPE_ENGINE, HopkinsMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(HOPKINS_DETECTION, PLUGIN_TYPE_METAENGINE, HopkinsMetaEngine);
diff --git a/engines/hopkins/detection.h b/engines/hopkins/detection.h
new file mode 100644
index 0000000000..678b570022
--- /dev/null
+++ b/engines/hopkins/detection.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Hopkins {
+
+struct HopkinsGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Hopkins
diff --git a/engines/hopkins/metaengine.cpp b/engines/hopkins/metaengine.cpp
new file mode 100644
index 0000000000..bc07ba1599
--- /dev/null
+++ b/engines/hopkins/metaengine.cpp
@@ -0,0 +1,174 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "hopkins/hopkins.h"
+
+#include "base/plugins.h"
+#include "common/savefile.h"
+#include "common/str-array.h"
+#include "common/memstream.h"
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+#include "common/translation.h"
+#include "graphics/surface.h"
+
+#include "hopkins/detection.h"
+
+#define MAX_SAVES 99
+
+namespace Hopkins {
+
+uint32 HopkinsEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language HopkinsEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+Common::Platform HopkinsEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+bool HopkinsEngine::getIsDemo() const {
+	return _gameDescription->desc.flags & ADGF_DEMO;
+}
+
+const Common::String &HopkinsEngine::getTargetName() const {
+	return _targetName;
+}
+
+} // End of namespace Hopkins
+
+class HopkinsMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "hopkins";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool HopkinsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Hopkins::HopkinsEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool HopkinsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Hopkins::HopkinsGameDescription *gd = (const Hopkins::HopkinsGameDescription *)desc;
+	if (gd) {
+		*engine = new Hopkins::HopkinsEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList HopkinsMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.0##", target);
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	Hopkins::hopkinsSavegameHeader header;
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		const char *ext = strrchr(file->c_str(), '.');
+		int slot = ext ? atoi(ext + 1) : -1;
+
+		if (slot >= 0 && slot < MAX_SAVES) {
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+			if (in) {
+				if (Hopkins::SaveLoadManager::readSavegameHeader(in, header)) {
+					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
+				}
+
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int HopkinsMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVES;
+}
+
+void HopkinsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor HopkinsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
+
+	if (f) {
+		Hopkins::hopkinsSavegameHeader header;
+		if (!Hopkins::SaveLoadManager::readSavegameHeader(f, header, false)) {
+			delete f;
+			return SaveStateDescriptor();
+		}
+
+		delete f;
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header._saveName);
+		desc.setThumbnail(header._thumbnail);
+		desc.setSaveDate(header._year, header._month, header._day);
+		desc.setSaveTime(header._hour, header._minute);
+		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(HOPKINS)
+	REGISTER_PLUGIN_DYNAMIC(HOPKINS, PLUGIN_TYPE_ENGINE, HopkinsMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(HOPKINS, PLUGIN_TYPE_ENGINE, HopkinsMetaEngineConnect);
+#endif
diff --git a/engines/hopkins/module.mk b/engines/hopkins/module.mk
index 5c1a7dd478..2110a45e2c 100644
--- a/engines/hopkins/module.mk
+++ b/engines/hopkins/module.mk
@@ -4,7 +4,6 @@ MODULE_OBJS := \
 	anim.o \
 	computer.o \
 	debugger.o \
-	detection.o \
 	dialogs.o \
 	events.o \
 	files.o \
@@ -14,6 +13,7 @@ MODULE_OBJS := \
 	hopkins.o \
 	lines.o \
 	menu.o \
+	metaengine.o \
 	objects.o \
 	saveload.o \
 	script.o \
@@ -27,3 +27,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: d02d53e9a3b3caa337777d549ece0d24c1260329
    https://github.com/scummvm/scummvm/commit/d02d53e9a3b3caa337777d549ece0d24c1260329
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
HUGO: Move common game-detection related enums to new header file.

Changed paths:
  A engines/hugo/detection_enums.h
    engines/hugo/hugo.h


diff --git a/engines/hugo/detection_enums.h b/engines/hugo/detection_enums.h
new file mode 100644
index 0000000000..f8ce67ca84
--- /dev/null
+++ b/engines/hugo/detection_enums.h
@@ -0,0 +1,46 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Hugo {
+
+enum HugoGameFeatures {
+	GF_PACKED = (1 << 0) // Database
+};
+
+enum GameType {
+	kGameTypeNone  = 0,
+	kGameTypeHugo1,
+	kGameTypeHugo2,
+	kGameTypeHugo3
+};
+
+enum GameVariant {
+	kGameVariantH1Win = 0,
+	kGameVariantH2Win,
+	kGameVariantH3Win,
+	kGameVariantH1Dos,
+	kGameVariantH2Dos,
+	kGameVariantH3Dos,
+	kGameVariantNone
+};
+
+} // End of namespace Hugo
diff --git a/engines/hugo/hugo.h b/engines/hugo/hugo.h
index 15576ee7de..288d73b20c 100644
--- a/engines/hugo/hugo.h
+++ b/engines/hugo/hugo.h
@@ -27,6 +27,7 @@
 
 // This include is here temporarily while the engine is being refactored.
 #include "hugo/game.h"
+#include "hugo/detection_enums.h"
 
 #define HUGO_DAT_VER_MAJ 0                          // 1 byte
 #define HUGO_DAT_VER_MIN 42                         // 1 byte
@@ -90,23 +91,6 @@ typedef byte Icondib[kXPix * kInvDy];               // Icon bar dib
 typedef byte Viewdib[(long)kXPix * kYPix];          // Viewport dib
 typedef byte Overlay[kOvlSize];                     // Overlay file
 
-enum GameType {
-	kGameTypeNone  = 0,
-	kGameTypeHugo1,
-	kGameTypeHugo2,
-	kGameTypeHugo3
-};
-
-enum GameVariant {
-	kGameVariantH1Win = 0,
-	kGameVariantH2Win,
-	kGameVariantH3Win,
-	kGameVariantH1Dos,
-	kGameVariantH2Dos,
-	kGameVariantH3Dos,
-	kGameVariantNone
-};
-
 enum HugoDebugChannels {
 	kDebugSchedule  = 1 <<  0,
 	kDebugEngine    = 1 <<  1,
@@ -157,10 +141,6 @@ enum Dupdate {kDisplayInit, kDisplayAdd, kDisplayDisplay, kDisplayRestore};
  */
 enum Priority {kSoundPriorityLow, kSoundPriorityMedium, kSoundPriorityHigh};
 
-enum HugoGameFeatures {
-	GF_PACKED = (1 << 0) // Database
-};
-
 // Strings used by the engine
 enum seqTextEngine {
 	kEsAdvertise = 0


Commit: 242e01bb0226b2b205d4c0b43d6856c57fc03216
    https://github.com/scummvm/scummvm/commit/242e01bb0226b2b205d4c0b43d6856c57fc03216
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
HUGO: Split detection features & adapt to new plugins.

Changed paths:
  A engines/hugo/detection.h
  A engines/hugo/metaengine.cpp
    configure
    engines/hugo/detection.cpp
    engines/hugo/module.mk


diff --git a/configure b/configure
index a22b05566a..b795c8b7b9 100755
--- a/configure
+++ b/configure
@@ -6163,7 +6163,7 @@ done
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
-								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS")
+								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/hugo/detection.cpp b/engines/hugo/detection.cpp
index 25d8e18d38..1b261eeb2d 100644
--- a/engines/hugo/detection.cpp
+++ b/engines/hugo/detection.cpp
@@ -20,31 +20,14 @@
  *
  */
 
+#include "base/plugins.h"
 #include "engines/advancedDetector.h"
-#include "common/system.h"
-#include "common/savefile.h"
-#include "common/textconsole.h"
-#include "graphics/thumbnail.h"
-#include "graphics/surface.h"
 
-#include "hugo/hugo.h"
+#include "hugo/detection_enums.h"
+#include "hugo/detection.h"
 
 namespace Hugo {
 
-struct HugoGameDescription {
-	ADGameDescription desc;
-	GameType gameType;
-};
-
-uint32 HugoEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-const char *HugoEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-
 static const PlainGameDescriptor hugoGames[] = {
 	// Games
 	{"hugo1", "Hugo 1: Hugo's House of Horrors"},
@@ -147,156 +130,8 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Hugo Engine (C) 1989-1997 David P. Gray";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool HugoMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
-	if (gd) {
-		*engine = new HugoEngine(syst, (const HugoGameDescription *)gd);
-		((HugoEngine *)*engine)->initGame((const HugoGameDescription *)gd);
-	}
-	return gd != 0;
-}
-
-bool HugoMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-	    (f == kSupportsLoadingDuringStartup) ||
-	    (f == kSupportsDeleteSave) ||
-	    (f == kSavesSupportMetaInfo) ||
-	    (f == kSavesSupportThumbnail) ||
-	    (f == kSavesSupportCreationDate);
-}
-
-int HugoMetaEngine::getMaximumSaveSlot() const { return 99; }
-
-SaveStateList HugoMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += "-##.SAV";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	char slot[3];
-	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
-		slot[0] = filename->c_str()[filename->size() - 6];
-		slot[1] = filename->c_str()[filename->size() - 5];
-		slot[2] = '\0';
-		// Obtain the last 2 digits of the filename (without extension), since they correspond to the save slot
-		int slotNum = atoi(slot);
-		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
-			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
-			if (file) {
-				int saveVersion = file->readByte();
-
-				if (saveVersion != kSavegameVersion) {
-					warning("Savegame of incompatible version");
-					delete file;
-					continue;
-				}
-
-				// read name
-				uint16 nameSize = file->readUint16BE();
-				if (nameSize >= 255) {
-					delete file;
-					continue;
-				}
-				char name[256];
-				file->read(name, nameSize);
-				name[nameSize] = 0;
-
-				saveList.push_back(SaveStateDescriptor(slotNum, name));
-				delete file;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor HugoMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
-	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (file) {
-		int saveVersion = file->readByte();
-
-		if (saveVersion != kSavegameVersion) {
-			warning("Savegame of incompatible version");
-			delete file;
-			return SaveStateDescriptor();
-		}
-
-		uint32 saveNameLength = file->readUint16BE();
-		char saveName[256];
-		file->read(saveName, saveNameLength);
-		saveName[saveNameLength] = 0;
-
-		SaveStateDescriptor desc(slot, saveName);
-
-		Graphics::Surface *thumbnail;
-		if (!Graphics::loadThumbnail(*file, thumbnail)) {
-			warning("Missing or broken savegame thumbnail");
-			delete file;
-			return SaveStateDescriptor();
-		}
-		desc.setThumbnail(thumbnail);
-
-		uint32 saveDate = file->readUint32BE();
-		uint16 saveTime = file->readUint16BE();
-
-		int day = (saveDate >> 24) & 0xFF;
-		int month = (saveDate >> 16) & 0xFF;
-		int year = saveDate & 0xFFFF;
-
-		desc.setSaveDate(year, month, day);
-
-		int hour = (saveTime >> 8) & 0xFF;
-		int minutes = saveTime & 0xFF;
-
-		desc.setSaveTime(hour, minutes);
-
-		// Slot 0 is used for the 'restart game' save in all Hugo games, thus
-		// we prevent it from being deleted.
-		desc.setDeletableFlag(slot != 0);
-		desc.setWriteProtectedFlag(slot == 0);
-
-		delete file;
-		return desc;
-	}
-	return SaveStateDescriptor();
-}
-
-void HugoMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
 } // End of namespace Hugo
 
-#if PLUGIN_ENABLED_DYNAMIC(HUGO)
-	REGISTER_PLUGIN_DYNAMIC(HUGO, PLUGIN_TYPE_ENGINE, Hugo::HugoMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(HUGO, PLUGIN_TYPE_ENGINE, Hugo::HugoMetaEngine);
-#endif
-
-namespace Hugo {
-
-void HugoEngine::initGame(const HugoGameDescription *gd) {
-	_gameType = gd->gameType;
-	_platform = gd->desc.platform;
-	_packedFl = (getFeatures() & GF_PACKED);
-	_gameVariant = _gameType - 1 + ((_platform == Common::kPlatformWindows) ? 0 : 3);
-}
-
-} // End of namespace Hugo
+REGISTER_PLUGIN_STATIC(HUGO_DETECTION, PLUGIN_TYPE_METAENGINE, Hugo::HugoMetaEngine);
diff --git a/engines/hugo/detection.h b/engines/hugo/detection.h
new file mode 100644
index 0000000000..d457ec5279
--- /dev/null
+++ b/engines/hugo/detection.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Hugo {
+
+struct HugoGameDescription {
+	ADGameDescription desc;
+	GameType gameType;
+};
+
+} // End of namespace Hugo
diff --git a/engines/hugo/metaengine.cpp b/engines/hugo/metaengine.cpp
new file mode 100644
index 0000000000..8deb53be2c
--- /dev/null
+++ b/engines/hugo/metaengine.cpp
@@ -0,0 +1,202 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+#include "common/savefile.h"
+#include "common/textconsole.h"
+#include "graphics/thumbnail.h"
+#include "graphics/surface.h"
+
+#include "hugo/hugo.h"
+#include "hugo/detection.h"
+
+namespace Hugo {
+
+uint32 HugoEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+const char *HugoEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+class HugoMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "hugo";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+
+};
+
+bool HugoMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+	if (gd) {
+		*engine = new HugoEngine(syst, (const HugoGameDescription *)gd);
+		((HugoEngine *)*engine)->initGame((const HugoGameDescription *)gd);
+	}
+	return gd != 0;
+}
+
+bool HugoMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+	    (f == kSupportsLoadingDuringStartup) ||
+	    (f == kSupportsDeleteSave) ||
+	    (f == kSavesSupportMetaInfo) ||
+	    (f == kSavesSupportThumbnail) ||
+	    (f == kSavesSupportCreationDate);
+}
+
+int HugoMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+
+SaveStateList HugoMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += "-##.SAV";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	char slot[3];
+	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
+		slot[0] = filename->c_str()[filename->size() - 6];
+		slot[1] = filename->c_str()[filename->size() - 5];
+		slot[2] = '\0';
+		// Obtain the last 2 digits of the filename (without extension), since they correspond to the save slot
+		int slotNum = atoi(slot);
+		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
+			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
+			if (file) {
+				int saveVersion = file->readByte();
+
+				if (saveVersion != kSavegameVersion) {
+					warning("Savegame of incompatible version");
+					delete file;
+					continue;
+				}
+
+				// read name
+				uint16 nameSize = file->readUint16BE();
+				if (nameSize >= 255) {
+					delete file;
+					continue;
+				}
+				char name[256];
+				file->read(name, nameSize);
+				name[nameSize] = 0;
+
+				saveList.push_back(SaveStateDescriptor(slotNum, name));
+				delete file;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor HugoMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
+	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (file) {
+		int saveVersion = file->readByte();
+
+		if (saveVersion != kSavegameVersion) {
+			warning("Savegame of incompatible version");
+			delete file;
+			return SaveStateDescriptor();
+		}
+
+		uint32 saveNameLength = file->readUint16BE();
+		char saveName[256];
+		file->read(saveName, saveNameLength);
+		saveName[saveNameLength] = 0;
+
+		SaveStateDescriptor desc(slot, saveName);
+
+		Graphics::Surface *thumbnail;
+		if (!Graphics::loadThumbnail(*file, thumbnail)) {
+			warning("Missing or broken savegame thumbnail");
+			delete file;
+			return SaveStateDescriptor();
+		}
+		desc.setThumbnail(thumbnail);
+
+		uint32 saveDate = file->readUint32BE();
+		uint16 saveTime = file->readUint16BE();
+
+		int day = (saveDate >> 24) & 0xFF;
+		int month = (saveDate >> 16) & 0xFF;
+		int year = saveDate & 0xFFFF;
+
+		desc.setSaveDate(year, month, day);
+
+		int hour = (saveTime >> 8) & 0xFF;
+		int minutes = saveTime & 0xFF;
+
+		desc.setSaveTime(hour, minutes);
+
+		// Slot 0 is used for the 'restart game' save in all Hugo games, thus
+		// we prevent it from being deleted.
+		desc.setDeletableFlag(slot != 0);
+		desc.setWriteProtectedFlag(slot == 0);
+
+		delete file;
+		return desc;
+	}
+	return SaveStateDescriptor();
+}
+
+void HugoMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+} // End of namespace Hugo
+
+#if PLUGIN_ENABLED_DYNAMIC(HUGO)
+	REGISTER_PLUGIN_DYNAMIC(HUGO, PLUGIN_TYPE_ENGINE, Hugo::HugoMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(HUGO, PLUGIN_TYPE_ENGINE, Hugo::HugoMetaEngineConnect);
+#endif
+
+namespace Hugo {
+
+void HugoEngine::initGame(const HugoGameDescription *gd) {
+	_gameType = gd->gameType;
+	_platform = gd->desc.platform;
+	_packedFl = (getFeatures() & GF_PACKED);
+	_gameVariant = _gameType - 1 + ((_platform == Common::kPlatformWindows) ? 0 : 3);
+}
+
+} // End of namespace Hugo
diff --git a/engines/hugo/module.mk b/engines/hugo/module.mk
index 2ded997437..1f5c5f41ec 100644
--- a/engines/hugo/module.mk
+++ b/engines/hugo/module.mk
@@ -2,7 +2,6 @@ MODULE := engines/hugo
 
 MODULE_OBJS := \
 	console.o \
-	detection.o \
 	dialogs.o \
 	display.o \
 	file.o \
@@ -14,6 +13,7 @@ MODULE_OBJS := \
 	hugo.o \
 	intro.o \
 	inventory.o \
+	metaengine.o \
 	mouse.o \
 	object.o \
 	object_v1d.o \
@@ -38,3 +38,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: fe37efbca2624872b6601b96c318d8feabbdb2a8
    https://github.com/scummvm/scummvm/commit/fe37efbca2624872b6601b96c318d8feabbdb2a8
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ILLUSIONS: Split detection features & adapt to new plugins.

Changed paths:
  A engines/illusions/detection.h
  A engines/illusions/detection_enums.h
  A engines/illusions/metaengine.cpp
    configure
    engines/illusions/detection.cpp
    engines/illusions/illusions.h
    engines/illusions/module.mk


diff --git a/configure b/configure
index b795c8b7b9..0fce30772a 100755
--- a/configure
+++ b/configure
@@ -6163,7 +6163,7 @@ done
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
-								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO")
+								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/illusions/detection.cpp b/engines/illusions/detection.cpp
index ae942beb1e..4d04a6f7db 100644
--- a/engines/illusions/detection.cpp
+++ b/engines/illusions/detection.cpp
@@ -20,16 +20,12 @@
  *
  */
 
-#include "illusions/illusions.h"
-#include "illusions/bbdou/illusions_bbdou.h"
-#include "illusions/duckman/illusions_duckman.h"
-
-#include "common/config-manager.h"
 #include "engines/advancedDetector.h"
-#include "common/savefile.h"
-#include "common/system.h"
+
 #include "base/plugins.h"
-#include "graphics/thumbnail.h"
+
+#include "illusions/detection_enums.h"
+#include "illusions/detection.h"
 
 static const PlainGameDescriptor illusionsGames[] = {
 	{ "bbdou", "Beavis and Butt-head Do U" },
@@ -39,19 +35,6 @@ static const PlainGameDescriptor illusionsGames[] = {
 
 namespace Illusions {
 
-struct IllusionsGameDescription {
-	ADGameDescription desc;
-	int gameId;
-};
-
-int IllusionsEngine::getGameId() const {
-	return _gameDescription->gameId;
-}
-
-Common::Language IllusionsEngine::getGameLanguage() const {
-	return _gameDescription->desc.language;
-}
-
 static const IllusionsGameDescription gameDescriptions[] = {
 	{
 		{
@@ -146,102 +129,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "(C) The Illusions Gaming Company";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool IllusionsMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate);
-}
-
-void IllusionsMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-int IllusionsMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-SaveStateList IllusionsMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Illusions::IllusionsEngine::SaveHeader header;
-	Common::String pattern = target;
-	pattern += ".???";
-	Common::StringArray filenames;
-	filenames = saveFileMan->listSavefiles(pattern.c_str());
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
-			if (in) {
-				if (Illusions::IllusionsEngine::readSaveHeader(in, header) == Illusions::IllusionsEngine::kRSHENoError) {
-					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
-				}
-				delete in;
-			}
-		}
-	}
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor IllusionsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Illusions::IllusionsEngine::getSavegameFilename(target, slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
-	if (in) {
-		Illusions::IllusionsEngine::SaveHeader header;
-		Illusions::IllusionsEngine::kReadSaveHeaderError error;
-		error = Illusions::IllusionsEngine::readSaveHeader(in, header, false);
-		delete in;
-		if (error == Illusions::IllusionsEngine::kRSHENoError) {
-			SaveStateDescriptor desc(slot, header.description);
-			// Slot 0 is used for the "Continue" save
-			desc.setDeletableFlag(slot != 0);
-			desc.setWriteProtectedFlag(slot == 0);
-			desc.setThumbnail(header.thumbnail);
-			desc.setSaveDate(header.saveDate & 0xFFFF, (header.saveDate >> 16) & 0xFF, (header.saveDate >> 24) & 0xFF);
-			desc.setSaveTime((header.saveTime >> 16) & 0xFF, (header.saveTime >> 8) & 0xFF);
-			desc.setPlayTime(header.playTime * 1000);
-			return desc;
-		}
-	}
-	return SaveStateDescriptor();
-}
-
-bool IllusionsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Illusions::IllusionsGameDescription *gd = (const Illusions::IllusionsGameDescription *)desc;
-	if (gd) {
-		switch (gd->gameId) {
-		case Illusions::kGameIdBBDOU:
-			*engine = new Illusions::IllusionsEngine_BBDOU(syst, gd);
-			break;
-		case Illusions::kGameIdDuckman:
-			*engine = new Illusions::IllusionsEngine_Duckman(syst, gd);
-			break;
-		default:
-			error("Unknown game id");
-			break;
-		}
-	}
-	return desc != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(ILLUSIONS)
-	REGISTER_PLUGIN_DYNAMIC(ILLUSIONS, PLUGIN_TYPE_ENGINE, IllusionsMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(ILLUSIONS, PLUGIN_TYPE_ENGINE, IllusionsMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(ILLUSIONS_DETECTION, PLUGIN_TYPE_METAENGINE, IllusionsMetaEngine);
diff --git a/engines/illusions/detection.h b/engines/illusions/detection.h
new file mode 100644
index 0000000000..f1d1c30b54
--- /dev/null
+++ b/engines/illusions/detection.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Illusions {
+
+struct IllusionsGameDescription {
+	ADGameDescription desc;
+	int gameId;
+};
+
+} // End of namespace Illusions
+
diff --git a/engines/illusions/detection_enums.h b/engines/illusions/detection_enums.h
new file mode 100644
index 0000000000..c8691d7551
--- /dev/null
+++ b/engines/illusions/detection_enums.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+namespace Illusions {
+
+enum {
+	kGameIdBBDOU   = 1,
+	kGameIdDuckman = 2
+};
+
+} // End of namespace Illusions
diff --git a/engines/illusions/illusions.h b/engines/illusions/illusions.h
index 5fb4344023..73d6eced49 100644
--- a/engines/illusions/illusions.h
+++ b/engines/illusions/illusions.h
@@ -26,6 +26,7 @@
 #include "illusions/graphics.h"
 #include "audio/mixer.h"
 #include "audio/decoders/aiff.h"
+
 #include "common/array.h"
 #include "common/events.h"
 #include "common/file.h"
@@ -34,8 +35,10 @@
 #include "common/str.h"
 #include "common/substream.h"
 #include "common/system.h"
+
 #include "engines/engine.h"
 #include "graphics/surface.h"
+#include "illusions/detection_enums.h"
 
 namespace Illusions {
 
@@ -76,11 +79,6 @@ class UpdateFunctions;
 class GameState;
 class ScreenPaletteBase;
 
-enum {
-	kGameIdBBDOU   = 1,
-	kGameIdDuckman = 2
-};
-
 class IllusionsEngine : public Engine {
 public:
 	IllusionsEngine(OSystem *syst, const IllusionsGameDescription *gd);
diff --git a/engines/illusions/metaengine.cpp b/engines/illusions/metaengine.cpp
new file mode 100644
index 0000000000..b01997b873
--- /dev/null
+++ b/engines/illusions/metaengine.cpp
@@ -0,0 +1,152 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "illusions/illusions.h"
+#include "illusions/bbdou/illusions_bbdou.h"
+#include "illusions/duckman/illusions_duckman.h"
+
+#include "common/config-manager.h"
+#include "engines/advancedDetector.h"
+#include "common/savefile.h"
+#include "common/system.h"
+#include "base/plugins.h"
+#include "graphics/thumbnail.h"
+
+#include "illusions/detection.h"
+
+namespace Illusions {
+
+int IllusionsEngine::getGameId() const {
+	return _gameDescription->gameId;
+}
+
+Common::Language IllusionsEngine::getGameLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+} // End of namespace Illusions
+
+class IllusionsMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "illusions";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool IllusionsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate);
+}
+
+void IllusionsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+int IllusionsMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+SaveStateList IllusionsMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Illusions::IllusionsEngine::SaveHeader header;
+	Common::String pattern = target;
+	pattern += ".???";
+	Common::StringArray filenames;
+	filenames = saveFileMan->listSavefiles(pattern.c_str());
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
+			if (in) {
+				if (Illusions::IllusionsEngine::readSaveHeader(in, header) == Illusions::IllusionsEngine::kRSHENoError) {
+					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
+				}
+				delete in;
+			}
+		}
+	}
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor IllusionsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Illusions::IllusionsEngine::getSavegameFilename(target, slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
+	if (in) {
+		Illusions::IllusionsEngine::SaveHeader header;
+		Illusions::IllusionsEngine::kReadSaveHeaderError error;
+		error = Illusions::IllusionsEngine::readSaveHeader(in, header, false);
+		delete in;
+		if (error == Illusions::IllusionsEngine::kRSHENoError) {
+			SaveStateDescriptor desc(slot, header.description);
+			// Slot 0 is used for the "Continue" save
+			desc.setDeletableFlag(slot != 0);
+			desc.setWriteProtectedFlag(slot == 0);
+			desc.setThumbnail(header.thumbnail);
+			desc.setSaveDate(header.saveDate & 0xFFFF, (header.saveDate >> 16) & 0xFF, (header.saveDate >> 24) & 0xFF);
+			desc.setSaveTime((header.saveTime >> 16) & 0xFF, (header.saveTime >> 8) & 0xFF);
+			desc.setPlayTime(header.playTime * 1000);
+			return desc;
+		}
+	}
+	return SaveStateDescriptor();
+}
+
+bool IllusionsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Illusions::IllusionsGameDescription *gd = (const Illusions::IllusionsGameDescription *)desc;
+	if (gd) {
+		switch (gd->gameId) {
+		case Illusions::kGameIdBBDOU:
+			*engine = new Illusions::IllusionsEngine_BBDOU(syst, gd);
+			break;
+		case Illusions::kGameIdDuckman:
+			*engine = new Illusions::IllusionsEngine_Duckman(syst, gd);
+			break;
+		default:
+			error("Unknown game id");
+			break;
+		}
+	}
+	return desc != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(ILLUSIONS)
+	REGISTER_PLUGIN_DYNAMIC(ILLUSIONS, PLUGIN_TYPE_ENGINE, IllusionsMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(ILLUSIONS, PLUGIN_TYPE_ENGINE, IllusionsMetaEngineConnect);
+#endif
diff --git a/engines/illusions/module.mk b/engines/illusions/module.mk
index 6d2a5aa163..752cfdbbf6 100644
--- a/engines/illusions/module.mk
+++ b/engines/illusions/module.mk
@@ -18,7 +18,6 @@ MODULE_OBJS := \
 	bbdou/scriptopcodes_bbdou.o \
 	camera.o \
 	cursor.o \
-	detection.o \
 	dictionary.o \
 	duckman/duckman_credits.o \
 	duckman/duckman_dialog.o \
@@ -39,6 +38,7 @@ MODULE_OBJS := \
 	graphics.o \
 	illusions.o \
 	input.o \
+	metaengine.o \
 	menusystem.o \
 	pathfinder.o \
 	resources/actorresource.o \
@@ -76,3 +76,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 033ad0baa1abb53c179953b777c2ffcd6e34bb62
    https://github.com/scummvm/scummvm/commit/033ad0baa1abb53c179953b777c2ffcd6e34bb62
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
KINGDOM: Split detection features & adapt to new plugins.

Changed paths:
  A engines/kingdom/metaengine.cpp
    configure
    engines/kingdom/detection.cpp
    engines/kingdom/module.mk


diff --git a/configure b/configure
index 0fce30772a..bca8ae47ef 100755
--- a/configure
+++ b/configure
@@ -6163,7 +6163,7 @@ done
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
-								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS")
+								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/kingdom/detection.cpp b/engines/kingdom/detection.cpp
index 3bdd81b5fd..4cf93a596e 100644
--- a/engines/kingdom/detection.cpp
+++ b/engines/kingdom/detection.cpp
@@ -22,18 +22,9 @@
 
 #include "base/plugins.h"
 
-#include "common/savefile.h"
 #include "engines/advancedDetector.h"
 #include "common/file.h"
 
-#include "kingdom/kingdom.h"
-
-
-namespace Kingdom {
-const char *KingdomGame::getGameId() const { return _gameDescription->gameId; }
-Common::Platform KingdomGame::getPlatform() const { return _gameDescription->platform; }
-}
-
 static const PlainGameDescriptor kingdomGames[] = {
 	{"kingdom", "Kingdom: The Far Reaches"},
 	{0, 0}
@@ -41,8 +32,6 @@ static const PlainGameDescriptor kingdomGames[] = {
 
 namespace Kingdom {
 
-#define MAX_SAVES 99
-
 static const ADGameDescription gameDescriptions[] = {
 	// Kingdom PC DOS Demo version, provided by Strangerke
 	{
@@ -99,100 +88,6 @@ public:
 	virtual const char *getOriginalCopyright() const override {
 		return "Kingdom: The far Reaches (C) 1995 Virtual Image Productions";
 	}
-
-	virtual bool hasFeature(MetaEngineFeature f) const override;
-	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	virtual int getMaximumSaveSlot() const override;
-	virtual SaveStateList listSaves(const char *target) const override;
-	virtual void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool KingdomMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-	    (f == kSupportsLoadingDuringStartup) ||
-	    (f == kSupportsDeleteSave) ||
-	    (f == kSavesSupportMetaInfo) ||
-	    (f == kSavesSupportThumbnail) ||
-	    (f == kSavesSupportCreationDate);
-}
-
-bool KingdomMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc)
-		*engine = new Kingdom::KingdomGame(syst, desc);
-
-	return desc != nullptr;
-}
-
-int KingdomMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVES;
-}
-
-SaveStateList KingdomMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.0##", target);
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	Kingdom::KingdomSavegameHeader header;
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		const char *ext = strrchr(file->c_str(), '.');
-		int slot = ext ? atoi(ext + 1) : -1;
-
-		if (slot >= 0 && slot < MAX_SAVES) {
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-			if (in) {
-				if (Kingdom::KingdomGame::readSavegameHeader(in, header)) {
-					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
-
-					header._thumbnail->free();
-					delete header._thumbnail;
-				}
-
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void KingdomMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor KingdomMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
-
-	if (f) {
-		Kingdom::KingdomSavegameHeader header;
-		Kingdom::KingdomGame::readSavegameHeader(f, header);
-		delete f;
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header._saveName);
-		desc.setThumbnail(header._thumbnail);
-		desc.setSaveDate(header._year, header._month, header._day);
-		desc.setSaveTime(header._hour, header._minute);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(KINGDOM)
-REGISTER_PLUGIN_DYNAMIC(KINGDOM, PLUGIN_TYPE_ENGINE, KingdomMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(KINGDOM, PLUGIN_TYPE_ENGINE, KingdomMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(KINGDOM_DETECTION, PLUGIN_TYPE_METAENGINE, KingdomMetaEngine);
diff --git a/engines/kingdom/metaengine.cpp b/engines/kingdom/metaengine.cpp
new file mode 100644
index 0000000000..78c13dec6e
--- /dev/null
+++ b/engines/kingdom/metaengine.cpp
@@ -0,0 +1,143 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "common/savefile.h"
+#include "engines/advancedDetector.h"
+#include "common/file.h"
+
+#include "kingdom/kingdom.h"
+
+#define MAX_SAVES 99
+
+namespace Kingdom {
+
+const char *KingdomGame::getGameId() const { return _gameDescription->gameId; }
+Common::Platform KingdomGame::getPlatform() const { return _gameDescription->platform; }
+
+} // End of namespace Kingdom
+
+
+class KingdomMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "kingdom";
+	}
+
+	virtual bool hasFeature(MetaEngineFeature f) const override;
+	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	virtual int getMaximumSaveSlot() const override;
+	virtual SaveStateList listSaves(const char *target) const override;
+	virtual void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool KingdomMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+	    (f == kSupportsLoadingDuringStartup) ||
+	    (f == kSupportsDeleteSave) ||
+	    (f == kSavesSupportMetaInfo) ||
+	    (f == kSavesSupportThumbnail) ||
+	    (f == kSavesSupportCreationDate);
+}
+
+bool KingdomMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc)
+		*engine = new Kingdom::KingdomGame(syst, desc);
+
+	return desc != nullptr;
+}
+
+int KingdomMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVES;
+}
+
+SaveStateList KingdomMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.0##", target);
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	Kingdom::KingdomSavegameHeader header;
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		const char *ext = strrchr(file->c_str(), '.');
+		int slot = ext ? atoi(ext + 1) : -1;
+
+		if (slot >= 0 && slot < MAX_SAVES) {
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+			if (in) {
+				if (Kingdom::KingdomGame::readSavegameHeader(in, header)) {
+					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
+
+					header._thumbnail->free();
+					delete header._thumbnail;
+				}
+
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void KingdomMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor KingdomMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
+
+	if (f) {
+		Kingdom::KingdomSavegameHeader header;
+		Kingdom::KingdomGame::readSavegameHeader(f, header);
+		delete f;
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header._saveName);
+		desc.setThumbnail(header._thumbnail);
+		desc.setSaveDate(header._year, header._month, header._day);
+		desc.setSaveTime(header._hour, header._minute);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(KINGDOM)
+	REGISTER_PLUGIN_DYNAMIC(KINGDOM, PLUGIN_TYPE_ENGINE, KingdomMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(KINGDOM, PLUGIN_TYPE_ENGINE, KingdomMetaEngineConnect);
+#endif
diff --git a/engines/kingdom/module.mk b/engines/kingdom/module.mk
index 873f5b2120..82c7dd45b6 100644
--- a/engines/kingdom/module.mk
+++ b/engines/kingdom/module.mk
@@ -3,13 +3,13 @@ MODULE := engines/kingdom
 MODULE_OBJS = \
 	kingdom.o \
 	constants.o \
+	console.o \
 	logic1.o \
 	logic2.o \
 	logic3.o \
 	logic4.o \
 	logic.o \
-	console.o \
-	detection.o
+	metaengine.o
 
 # This module can be built as a plugin
 ifeq ($(ENABLE_KINGDOM), DYNAMIC_PLUGIN)
@@ -18,3 +18,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 1d6f4025400eaa777a24a5855f35b2571885058a
    https://github.com/scummvm/scummvm/commit/1d6f4025400eaa777a24a5855f35b2571885058a
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
KYRA: Move common game/detection related enums to new header

- Make KyraMetaEngineConnect our friend class

Changed paths:
  A engines/kyra/detection_enums.h
    engines/kyra/kyra_v1.h


diff --git a/engines/kyra/detection_enums.h b/engines/kyra/detection_enums.h
new file mode 100644
index 0000000000..6212099183
--- /dev/null
+++ b/engines/kyra/detection_enums.h
@@ -0,0 +1,56 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Kyra {
+
+enum {
+	GI_KYRA1 = 0,
+	GI_KYRA2 = 1,
+	GI_KYRA3 = 2,
+	GI_LOL = 4,
+	GI_EOB1 = 5,
+	GI_EOB2 = 6
+};
+
+struct GameFlags {
+	Common::Language lang;
+
+	// language overwrites of fan translations (only needed for multilingual games)
+	Common::Language fanLang;
+	Common::Language replacedLang;
+
+	Common::Platform platform;
+
+	bool isDemo               : 1;
+	bool useAltShapeHeader    : 1;    // alternative shape header (uses 2 bytes more, those are unused though)
+	bool isTalkie             : 1;
+	bool isOldFloppy          : 1;
+	bool useHiRes             : 1;
+	bool use16ColorMode       : 1;
+	bool useHiColorMode       : 1;
+	bool useDigSound          : 1;
+	bool useInstallerPackage  : 1;
+
+	byte gameID;
+};
+
+} // End of namespace Kyra
diff --git a/engines/kyra/kyra_v1.h b/engines/kyra/kyra_v1.h
index 878f150afb..65d02ebf25 100644
--- a/engines/kyra/kyra_v1.h
+++ b/engines/kyra/kyra_v1.h
@@ -36,6 +36,7 @@
 
 #include "kyra/script/script.h"
 #include "kyra/engine/item.h"
+#include "kyra/detection_enums.h"
 
 namespace Common {
 class OutSaveFile;
@@ -47,7 +48,7 @@ namespace Graphics {
 struct Surface;
 }
 
-class KyraMetaEngine;
+class KyraMetaEngineConnect;
 
 /**
  * This is the namespace of the Kyra engine.
@@ -107,41 +108,10 @@ class KyraMetaEngine;
  */
 namespace Kyra {
 
-struct GameFlags {
-	Common::Language lang;
-
-	// language overwrites of fan translations (only needed for multilingual games)
-	Common::Language fanLang;
-	Common::Language replacedLang;
-
-	Common::Platform platform;
-
-	bool isDemo               : 1;
-	bool useAltShapeHeader    : 1;    // alternative shape header (uses 2 bytes more, those are unused though)
-	bool isTalkie             : 1;
-	bool isOldFloppy          : 1;
-	bool useHiRes             : 1;
-	bool use16ColorMode       : 1;
-	bool useHiColorMode       : 1;
-	bool useDigSound          : 1;
-	bool useInstallerPackage  : 1;
-
-	byte gameID;
-};
-
 struct KeyCodeHash : public Common::UnaryFunction<Common::KeyCode, uint> {
 	uint operator()(Common::KeyCode val) const { return (uint)val; }
 };
 
-enum {
-	GI_KYRA1 = 0,
-	GI_KYRA2 = 1,
-	GI_KYRA3 = 2,
-	GI_LOL = 4,
-	GI_EOB1 = 5,
-	GI_EOB2 = 6
-};
-
 // TODO: this is just the start of makeing the debug output of the kyra engine a bit more useable
 // in the future we maybe merge some flags  and/or create new ones
 enum DebugLevels {
@@ -177,7 +147,7 @@ struct Button;
 
 class KyraEngine_v1 : public Engine {
 friend class Debugger;
-friend class ::KyraMetaEngine;
+friend class ::KyraMetaEngineConnect;
 friend class GUI;
 friend class GUI_v1;
 friend class GUI_EoB;


Commit: 846336cb31bc18b8462527dcf73b71f7437e7a15
    https://github.com/scummvm/scummvm/commit/846336cb31bc18b8462527dcf73b71f7437e7a15
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
KYRA: Split detection features & adapt to new plugins.

Changed paths:
  A engines/kyra/detection.h
  A engines/kyra/metaengine.cpp
    configure
    engines/kyra/detection.cpp
    engines/kyra/module.mk


diff --git a/configure b/configure
index bca8ae47ef..aaed3bb0f1 100755
--- a/configure
+++ b/configure
@@ -6163,7 +6163,8 @@ done
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
-								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM")
+								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
+								  "KYRA")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/kyra/detection.cpp b/engines/kyra/detection.cpp
index 1630f620d2..295ddd7309 100644
--- a/engines/kyra/detection.cpp
+++ b/engines/kyra/detection.cpp
@@ -20,28 +20,12 @@
  *
  */
 
-#include "kyra/engine/kyra_lok.h"
-#include "kyra/engine/lol.h"
-#include "kyra/engine/kyra_hof.h"
-#include "kyra/engine/kyra_mr.h"
-#include "kyra/engine/eob.h"
-#include "kyra/engine/darkmoon.h"
-
-#include "common/config-manager.h"
-#include "common/system.h"
-#include "common/savefile.h"
 #include "common/translation.h"
-
 #include "engines/advancedDetector.h"
-
 #include "base/plugins.h"
 
-struct KYRAGameDescription {
-	ADGameDescription desc;
-
-	Kyra::GameFlags flags;
-};
-
+#include "kyra/detection_enums.h"
+#include "kyra/detection.h"
 #include "kyra/detection_tables.h"
 
 namespace {
@@ -187,204 +171,6 @@ public:
 #endif
 		       ;
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	Common::KeymapArray initKeymaps(const char *target) const override;
-	virtual int getAutosaveSlot() const override { return 999; }
 };
 
-bool KyraMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-	    (f == kSupportsLoadingDuringStartup) ||
-	    (f == kSupportsDeleteSave) ||
-	    (f == kSavesSupportMetaInfo) ||
-	    (f == kSavesSupportThumbnail) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Kyra::KyraEngine_v1::hasFeature(EngineFeature f) const {
-	return
-	    (f == kSupportsReturnToLauncher) ||
-	    (f == kSupportsLoadingDuringRuntime) ||
-	    (f == kSupportsSavingDuringRuntime) ||
-	    (f == kSupportsSubtitleOptions);
-}
-
-bool KyraMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const KYRAGameDescription *gd = (const KYRAGameDescription *)desc;
-	bool res = true;
-
-	Kyra::GameFlags flags = gd->flags;
-
-	flags.lang = gd->desc.language;
-	flags.platform = gd->desc.platform;
-
-	Common::Platform platform = Common::parsePlatform(ConfMan.get("platform"));
-	if (platform != Common::kPlatformUnknown)
-		flags.platform = platform;
-
-	if (flags.lang == Common::UNK_LANG) {
-		Common::Language lang = Common::parseLanguage(ConfMan.get("language"));
-		if (lang != Common::UNK_LANG)
-			flags.lang = lang;
-		else
-			flags.lang = Common::EN_ANY;
-	}
-
-#ifndef USE_RGB_COLOR
-	flags.useHiColorMode = false;
-#endif
-
-	switch (flags.gameID) {
-	case Kyra::GI_KYRA1:
-		*engine = new Kyra::KyraEngine_LoK(syst, flags);
-		break;
-	case Kyra::GI_KYRA2:
-		*engine = new Kyra::KyraEngine_HoF(syst, flags);
-		break;
-	case Kyra::GI_KYRA3:
-		*engine = new Kyra::KyraEngine_MR(syst, flags);
-		break;
-#ifdef ENABLE_LOL
-	case Kyra::GI_LOL:
-		*engine = new Kyra::LoLEngine(syst, flags);
-		break;
-#endif // ENABLE_LOL
-#ifdef ENABLE_EOB
-	case Kyra::GI_EOB1:
-		*engine = new Kyra::EoBEngine(syst, flags);
-		break;
-	case Kyra::GI_EOB2:
-		 if (Common::parseRenderMode(ConfMan.get("render_mode")) == Common::kRenderEGA)
-			 flags.useHiRes = true;
-		 if (platform == Common::kPlatformFMTowns && !flags.useHiColorMode)
-			 error("EOB II FM-TOWNS requires support of 16bit color modes which has not been activated in your ScummVM build (The 'USE_RGB_COLOR' define has not been set).");
-		*engine = new Kyra::DarkMoonEngine(syst, flags);
-		break;
-#endif // ENABLE_EOB
-	default:
-		res = false;
-		warning("Kyra engine: unknown gameID");
-	}
-
-	return res;
-}
-
-SaveStateList KyraMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Kyra::KyraEngine_v1::SaveHeader header;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	Common::StringArray filenames;
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				if (Kyra::KyraEngine_v1::readSaveHeader(in, header) == Kyra::KyraEngine_v1::kRSHENoError) {
-					// WORKAROUND: Old savegames are using 'German' as description for kyra3 restart game save (slot 0),
-					// since that looks odd we replace it by "New Game".
-					if (slotNum == 0 && header.gameID == Kyra::GI_KYRA3)
-						header.description = "New Game";
-
-					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
-				}
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int KyraMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-void KyraMetaEngine::removeSaveState(const char *target, int slot) const {
-	// In Kyra games slot 0 can't be deleted, it's for restarting the game(s).
-	// An exception makes Lands of Lore here, it does not have any way to restart the
-	// game except via its main menu.
-	if (slot == 0 && !ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("lol") && !ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob") && !ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob2"))
-		return;
-
-	Common::String filename = Kyra::KyraEngine_v1::getSavegameFilename(target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor KyraMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Kyra::KyraEngine_v1::getSavegameFilename(target, slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename);
-	const bool nonKyraGame = ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("lol") || ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob") || ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob2");
-
-	if (in) {
-		Kyra::KyraEngine_v1::SaveHeader header;
-		Kyra::KyraEngine_v1::ReadSaveHeaderError error;
-
-		error = Kyra::KyraEngine_v1::readSaveHeader(in, header, false);
-		delete in;
-
-		if (error == Kyra::KyraEngine_v1::kRSHENoError) {
-			SaveStateDescriptor desc(slot, header.description);
-
-			// Slot 0 is used for the 'restart game' save in all three Kyrandia games, thus
-			// we prevent it from being deleted.
-			desc.setDeletableFlag(slot != 0 || nonKyraGame);
-
-			// We don't allow quick saves (slot 990 till 998) to be overwritten.
-			// The same goes for the 'Autosave', which is slot 999. Slot 0 will also
-			// be protected in Kyra 1-3, since it's the 'restart game' save.
-			desc.setWriteProtectedFlag((slot == 0 && !nonKyraGame) || slot >= 990);
-			desc.setThumbnail(header.thumbnail);
-
-			return desc;
-		}
-	}
-
-	SaveStateDescriptor desc(slot, Common::String());
-
-	// We don't allow quick saves (slot 990 till 998) to be overwritten.
-	// The same goes for the 'Autosave', which is slot 999. Slot 0 will also
-	// be protected in Kyra 1-3, since it's the 'restart game' save.
-	desc.setWriteProtectedFlag((slot == 0 && !nonKyraGame) || slot >= 990);
-
-	return desc;
-}
-
-Common::KeymapArray KyraMetaEngine::initKeymaps(const char *target) const {
-	Common::String gameId = ConfMan.get("gameid", target);
-
-#ifdef ENABLE_LOL
-	if (gameId.contains("lol")) {
-		return Kyra::LoLEngine::initKeymaps();
-	}
-#endif
-
-#ifdef ENABLE_EOB
-	if (gameId.contains("eob")) {
-		return Kyra::EoBCoreEngine::initKeymaps(gameId);
-	}
-#endif
-
-	return AdvancedMetaEngine::initKeymaps(target);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(KYRA)
-	REGISTER_PLUGIN_DYNAMIC(KYRA, PLUGIN_TYPE_ENGINE, KyraMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(KYRA, PLUGIN_TYPE_ENGINE, KyraMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(KYRA_DETECTION, PLUGIN_TYPE_METAENGINE, KyraMetaEngine);
diff --git a/engines/kyra/detection.h b/engines/kyra/detection.h
new file mode 100644
index 0000000000..fcc6e077f6
--- /dev/null
+++ b/engines/kyra/detection.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace {
+
+struct KYRAGameDescription {
+	ADGameDescription desc;
+
+	Kyra::GameFlags flags;
+};
+
+} // End of anonymous namespace
diff --git a/engines/kyra/metaengine.cpp b/engines/kyra/metaengine.cpp
new file mode 100644
index 0000000000..3d6c680693
--- /dev/null
+++ b/engines/kyra/metaengine.cpp
@@ -0,0 +1,248 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "kyra/engine/kyra_lok.h"
+#include "kyra/engine/lol.h"
+#include "kyra/engine/kyra_hof.h"
+#include "kyra/engine/kyra_mr.h"
+#include "kyra/engine/eob.h"
+#include "kyra/engine/darkmoon.h"
+
+#include "common/config-manager.h"
+#include "common/system.h"
+#include "common/savefile.h"
+#include "common/translation.h"
+
+#include "engines/advancedDetector.h"
+
+#include "base/plugins.h"
+
+#include "kyra/detection.h"
+
+class KyraMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "kyra";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	virtual int getAutosaveSlot() const override { return 999; }
+
+	Common::KeymapArray initKeymaps(const char *target) const override;
+};
+
+bool KyraMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+	    (f == kSupportsLoadingDuringStartup) ||
+	    (f == kSupportsDeleteSave) ||
+	    (f == kSavesSupportMetaInfo) ||
+	    (f == kSavesSupportThumbnail) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Kyra::KyraEngine_v1::hasFeature(EngineFeature f) const {
+	return
+	    (f == kSupportsReturnToLauncher) ||
+	    (f == kSupportsLoadingDuringRuntime) ||
+	    (f == kSupportsSavingDuringRuntime) ||
+	    (f == kSupportsSubtitleOptions);
+}
+
+bool KyraMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const KYRAGameDescription *gd = (const KYRAGameDescription *)desc;
+	bool res = true;
+
+	Kyra::GameFlags flags = gd->flags;
+
+	flags.lang = gd->desc.language;
+	flags.platform = gd->desc.platform;
+
+	Common::Platform platform = Common::parsePlatform(ConfMan.get("platform"));
+	if (platform != Common::kPlatformUnknown)
+		flags.platform = platform;
+
+	if (flags.lang == Common::UNK_LANG) {
+		Common::Language lang = Common::parseLanguage(ConfMan.get("language"));
+		if (lang != Common::UNK_LANG)
+			flags.lang = lang;
+		else
+			flags.lang = Common::EN_ANY;
+	}
+
+#ifndef USE_RGB_COLOR
+	flags.useHiColorMode = false;
+#endif
+
+	switch (flags.gameID) {
+	case Kyra::GI_KYRA1:
+		*engine = new Kyra::KyraEngine_LoK(syst, flags);
+		break;
+	case Kyra::GI_KYRA2:
+		*engine = new Kyra::KyraEngine_HoF(syst, flags);
+		break;
+	case Kyra::GI_KYRA3:
+		*engine = new Kyra::KyraEngine_MR(syst, flags);
+		break;
+#ifdef ENABLE_LOL
+	case Kyra::GI_LOL:
+		*engine = new Kyra::LoLEngine(syst, flags);
+		break;
+#endif // ENABLE_LOL
+#ifdef ENABLE_EOB
+	case Kyra::GI_EOB1:
+		*engine = new Kyra::EoBEngine(syst, flags);
+		break;
+	case Kyra::GI_EOB2:
+		 if (Common::parseRenderMode(ConfMan.get("render_mode")) == Common::kRenderEGA)
+			 flags.useHiRes = true;
+		 if (platform == Common::kPlatformFMTowns && !flags.useHiColorMode)
+			 error("EOB II FM-TOWNS requires support of 16bit color modes which has not been activated in your ScummVM build (The 'USE_RGB_COLOR' define has not been set).");
+		*engine = new Kyra::DarkMoonEngine(syst, flags);
+		break;
+#endif // ENABLE_EOB
+	default:
+		res = false;
+		warning("Kyra engine: unknown gameID");
+	}
+
+	return res;
+}
+
+SaveStateList KyraMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Kyra::KyraEngine_v1::SaveHeader header;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	Common::StringArray filenames;
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				if (Kyra::KyraEngine_v1::readSaveHeader(in, header) == Kyra::KyraEngine_v1::kRSHENoError) {
+					// WORKAROUND: Old savegames are using 'German' as description for kyra3 restart game save (slot 0),
+					// since that looks odd we replace it by "New Game".
+					if (slotNum == 0 && header.gameID == Kyra::GI_KYRA3)
+						header.description = "New Game";
+
+					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
+				}
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int KyraMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+void KyraMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	// In Kyra games slot 0 can't be deleted, it's for restarting the game(s).
+	// An exception makes Lands of Lore here, it does not have any way to restart the
+	// game except via its main menu.
+	if (slot == 0 && !ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("lol") && !ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob") && !ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob2"))
+		return;
+
+	Common::String filename = Kyra::KyraEngine_v1::getSavegameFilename(target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor KyraMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Kyra::KyraEngine_v1::getSavegameFilename(target, slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename);
+	const bool nonKyraGame = ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("lol") || ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob") || ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob2");
+
+	if (in) {
+		Kyra::KyraEngine_v1::SaveHeader header;
+		Kyra::KyraEngine_v1::ReadSaveHeaderError error;
+
+		error = Kyra::KyraEngine_v1::readSaveHeader(in, header, false);
+		delete in;
+
+		if (error == Kyra::KyraEngine_v1::kRSHENoError) {
+			SaveStateDescriptor desc(slot, header.description);
+
+			// Slot 0 is used for the 'restart game' save in all three Kyrandia games, thus
+			// we prevent it from being deleted.
+			desc.setDeletableFlag(slot != 0 || nonKyraGame);
+
+			// We don't allow quick saves (slot 990 till 998) to be overwritten.
+			// The same goes for the 'Autosave', which is slot 999. Slot 0 will also
+			// be protected in Kyra 1-3, since it's the 'restart game' save.
+			desc.setWriteProtectedFlag((slot == 0 && !nonKyraGame) || slot >= 990);
+			desc.setThumbnail(header.thumbnail);
+
+			return desc;
+		}
+	}
+
+	SaveStateDescriptor desc(slot, Common::String());
+
+	// We don't allow quick saves (slot 990 till 998) to be overwritten.
+	// The same goes for the 'Autosave', which is slot 999. Slot 0 will also
+	// be protected in Kyra 1-3, since it's the 'restart game' save.
+	desc.setWriteProtectedFlag((slot == 0 && !nonKyraGame) || slot >= 990);
+
+	return desc;
+}
+
+Common::KeymapArray KyraMetaEngineConnect::initKeymaps(const char *target) const {
+	Common::String gameId = ConfMan.get("gameid", target);
+
+#ifdef ENABLE_LOL
+	if (gameId.contains("lol")) {
+		return Kyra::LoLEngine::initKeymaps();
+	}
+#endif
+
+#ifdef ENABLE_EOB
+	if (gameId.contains("eob")) {
+		return Kyra::EoBCoreEngine::initKeymaps(gameId);
+	}
+#endif
+
+	return AdvancedMetaEngineConnect::initKeymaps(target);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(KYRA)
+	REGISTER_PLUGIN_DYNAMIC(KYRA, PLUGIN_TYPE_ENGINE, KyraMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(KYRA, PLUGIN_TYPE_ENGINE, KyraMetaEngineConnect);
+#endif
diff --git a/engines/kyra/module.mk b/engines/kyra/module.mk
index b5557aaf5c..04e1c3f7b1 100644
--- a/engines/kyra/module.mk
+++ b/engines/kyra/module.mk
@@ -1,7 +1,6 @@
 MODULE := engines/kyra
 
 MODULE_OBJS := \
-	detection.o \
 	engine/items_lok.o \
 	engine/items_v2.o \
 	engine/items_hof.o \
@@ -45,6 +44,7 @@ MODULE_OBJS := \
 	gui/saveload_lok.o \
 	gui/saveload_hof.o \
 	gui/saveload_mr.o \
+	metaengine.o \
 	resource/resource.o \
 	resource/resource_intern.o \
 	resource/staticres.o \
@@ -153,6 +153,9 @@ endif
 # Include common rules
 include $(srcdir)/rules.mk
 
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
 ifeq ($(BACKEND), maemo)
 #ugly workaround, screen.cpp crashes gcc version 3.4.4 (CodeSourcery ARM 2005q3-2) with anything but -O3
 $(MODULE)/graphics/screen.o: $(MODULE)/graphics/screen.cpp


Commit: 0fbfa709a236abbd3281efce2b959877a43ebc26
    https://github.com/scummvm/scummvm/commit/0fbfa709a236abbd3281efce2b959877a43ebc26
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
LAB: Split detection features & adapt to new plugins.

Changed paths:
  A engines/lab/detection_enums.h
  A engines/lab/metaengine.cpp
    configure
    engines/lab/detection.cpp
    engines/lab/lab.h
    engines/lab/module.mk


diff --git a/configure b/configure
index aaed3bb0f1..0f771a4e5d 100755
--- a/configure
+++ b/configure
@@ -6164,7 +6164,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
-								  "KYRA")
+								  "KYRA" "LAB")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/lab/detection.cpp b/engines/lab/detection.cpp
index d4cdc76967..8a63ca3604 100644
--- a/engines/lab/detection.cpp
+++ b/engines/lab/detection.cpp
@@ -29,8 +29,7 @@
  */
 
 #include "engines/advancedDetector.h"
-
-#include "lab/lab.h"
+#include "lab/detection_enums.h"
 
 static const PlainGameDescriptor lab_setting[] = {
 	{ "lab", "Labyrinth of Time" },
@@ -100,17 +99,7 @@ static const char *const directoryGlobs[] = {
 		0
 };
 
-namespace Lab {
-
-Common::Platform LabEngine::getPlatform() const {
-	return _gameDescription->platform;
-}
-
-uint32 LabEngine::getFeatures() const {
-	return _gameDescription->flags | _extraGameFeatures;
-}
 
-} // End of namespace Lab
 
 class LabMetaEngine : public AdvancedMetaEngine {
 public:
@@ -131,104 +120,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Labyrinth of Time (C) 2004 The Wyrmkeep Entertainment Co. and Terra Nova Development";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
-		// Instantiate Engine even if the game data is not found.
-		*engine = new Lab::LabEngine(syst, desc);
-		return true;
-	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool LabMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Lab::LabEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-SaveStateList LabMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Lab::SaveGameHeader header;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	Common::StringArray filenames;
-	filenames = saveFileMan->listSavefiles(pattern.c_str());
-
-	SaveStateList saveList;
-
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if ((slotNum >= 0) && (slotNum <= 999)) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
-			if (in) {
-				if (Lab::readSaveGameHeader(in, header))
-					saveList.push_back(SaveStateDescriptor(slotNum, header._descr.getDescription()));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int LabMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-void LabMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	saveFileMan->removeSavefile(Common::String::format("%s.%03u", target, slot));
-}
-
-SaveStateDescriptor LabMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03u", target, slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
-
-	if (in) {
-		Lab::SaveGameHeader header;
-
-		bool successfulRead = Lab::readSaveGameHeader(in, header, false);
-		delete in;
-
-		if (successfulRead) {
-			SaveStateDescriptor desc(slot, header._descr.getDescription());
-			// Do not allow save slot 0 (used for auto-saving) to be deleted or
-			// overwritten.
-			//desc.setDeletableFlag(slot != 0);
-			//desc.setWriteProtectedFlag(slot == 0);
-
-			return header._descr;
-		}
-	}
-
-	return SaveStateDescriptor();
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(LAB)
-	REGISTER_PLUGIN_DYNAMIC(LAB, PLUGIN_TYPE_ENGINE, LabMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(LAB, PLUGIN_TYPE_ENGINE, LabMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(LAB_DETECTION, PLUGIN_TYPE_METAENGINE, LabMetaEngine);
diff --git a/engines/lab/detection_enums.h b/engines/lab/detection_enums.h
new file mode 100644
index 0000000000..f9c0b8830e
--- /dev/null
+++ b/engines/lab/detection_enums.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+namespace Lab {
+
+enum GameFeatures {
+	GF_LOWRES = 1 << 0,
+	GF_WINDOWS_TRIAL = 1 << 1
+};
+
+} // End of namespace Lab
diff --git a/engines/lab/lab.h b/engines/lab/lab.h
index 0151c7f6ae..17667cc70f 100644
--- a/engines/lab/lab.h
+++ b/engines/lab/lab.h
@@ -41,6 +41,7 @@
 #include "lab/console.h"
 #include "lab/image.h"
 #include "lab/labsets.h"
+#include "lab/detection_enums.h"
 
 struct ADGameDescription;
 
@@ -74,11 +75,6 @@ struct SaveGameHeader {
 	uint16 _direction;
 };
 
-enum GameFeatures {
-	GF_LOWRES = 1 << 0,
-	GF_WINDOWS_TRIAL = 1 << 1
-};
-
 typedef Common::List<Button *> ButtonList;
 
 struct CrumbData {
diff --git a/engines/lab/metaengine.cpp b/engines/lab/metaengine.cpp
new file mode 100644
index 0000000000..b1b81356fc
--- /dev/null
+++ b/engines/lab/metaengine.cpp
@@ -0,0 +1,151 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+/*
+ * This code is based on Labyrinth of Time code with assistance of
+ *
+ * Copyright (c) 1993 Terra Nova Development
+ * Copyright (c) 2004 The Wyrmkeep Entertainment Co.
+ *
+ */
+
+#include "lab/lab.h"
+#include "engines/advancedDetector.h"
+
+namespace Lab {
+
+Common::Platform LabEngine::getPlatform() const {
+	return _gameDescription->platform;
+}
+
+uint32 LabEngine::getFeatures() const {
+	return _gameDescription->flags | _extraGameFeatures;
+}
+
+} // End of namespace Lab
+
+class LabMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "lab";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
+		// Instantiate Engine even if the game data is not found.
+		*engine = new Lab::LabEngine(syst, desc);
+		return true;
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool LabMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Lab::LabEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+SaveStateList LabMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Lab::SaveGameHeader header;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	Common::StringArray filenames;
+	filenames = saveFileMan->listSavefiles(pattern.c_str());
+
+	SaveStateList saveList;
+
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if ((slotNum >= 0) && (slotNum <= 999)) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
+			if (in) {
+				if (Lab::readSaveGameHeader(in, header))
+					saveList.push_back(SaveStateDescriptor(slotNum, header._descr.getDescription()));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int LabMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+void LabMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	saveFileMan->removeSavefile(Common::String::format("%s.%03u", target, slot));
+}
+
+SaveStateDescriptor LabMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03u", target, slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
+
+	if (in) {
+		Lab::SaveGameHeader header;
+
+		bool successfulRead = Lab::readSaveGameHeader(in, header, false);
+		delete in;
+
+		if (successfulRead) {
+			SaveStateDescriptor desc(slot, header._descr.getDescription());
+			// Do not allow save slot 0 (used for auto-saving) to be deleted or
+			// overwritten.
+			//desc.setDeletableFlag(slot != 0);
+			//desc.setWriteProtectedFlag(slot == 0);
+
+			return header._descr;
+		}
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(LAB)
+	REGISTER_PLUGIN_DYNAMIC(LAB, PLUGIN_TYPE_ENGINE, LabMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(LAB, PLUGIN_TYPE_ENGINE, LabMetaEngineConnect);
+#endif
diff --git a/engines/lab/module.mk b/engines/lab/module.mk
index 7bb86c8c1e..67fd2fd2db 100644
--- a/engines/lab/module.mk
+++ b/engines/lab/module.mk
@@ -3,7 +3,6 @@ MODULE := engines/lab
 MODULE_OBJS := \
 	anim.o \
 	console.o \
-	detection.o \
 	dispman.o \
 	engine.o \
 	eventman.o \
@@ -13,6 +12,7 @@ MODULE_OBJS := \
 	lab.o \
 	labsets.o \
 	map.o \
+	metaengine.o \
 	music.o \
 	processroom.o \
 	resource.o \
@@ -28,3 +28,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 06cb6c50e6970bc503ae24497b748cfac3938faa
    https://github.com/scummvm/scummvm/commit/06cb6c50e6970bc503ae24497b748cfac3938faa
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
LASTEXPRESS: Split detection features & adapt to new plugins.

Changed paths:
  A engines/lastexpress/metaengine.cpp
    configure
    engines/lastexpress/detection.cpp
    engines/lastexpress/module.mk


diff --git a/configure b/configure
index 0f771a4e5d..06df933f77 100755
--- a/configure
+++ b/configure
@@ -6164,7 +6164,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
-								  "KYRA" "LAB")
+								  "KYRA" "LAB" "LASTEXPRESS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/lastexpress/detection.cpp b/engines/lastexpress/detection.cpp
index 99431ca007..0dcc5ccc57 100644
--- a/engines/lastexpress/detection.cpp
+++ b/engines/lastexpress/detection.cpp
@@ -20,7 +20,6 @@
  *
  */
 
-#include "lastexpress/lastexpress.h"
 #include "engines/advancedDetector.h"
 
 namespace LastExpress {
@@ -241,26 +240,8 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "The Last Express (C) 1997 Smoking Car Productions";
 	}
-
-protected:
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
 };
 
-bool LastExpressMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
-	if (gd) {
-		*engine = new LastExpressEngine(syst, (const ADGameDescription *)gd);
-	}
-	return gd != 0;
-}
-
-bool LastExpressEngine::isDemo() const {
-	return (bool)(_gameDescription->flags & ADGF_DEMO);
-}
-
 } // End of namespace LastExpress
 
-#if PLUGIN_ENABLED_DYNAMIC(LASTEXPRESS)
-	REGISTER_PLUGIN_DYNAMIC(LASTEXPRESS, PLUGIN_TYPE_ENGINE, LastExpress::LastExpressMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(LASTEXPRESS, PLUGIN_TYPE_ENGINE, LastExpress::LastExpressMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(LASTEXPRESS_DETECTION, PLUGIN_TYPE_METAENGINE, LastExpress::LastExpressMetaEngine);
diff --git a/engines/lastexpress/metaengine.cpp b/engines/lastexpress/metaengine.cpp
new file mode 100644
index 0000000000..b9ebb244fb
--- /dev/null
+++ b/engines/lastexpress/metaengine.cpp
@@ -0,0 +1,55 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "lastexpress/lastexpress.h"
+#include "engines/advancedDetector.h"
+
+namespace LastExpress {
+
+class LastExpressMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "lastexpress";
+	}
+
+protected:
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
+};
+
+bool LastExpressMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+	if (gd) {
+		*engine = new LastExpressEngine(syst, (const ADGameDescription *)gd);
+	}
+	return gd != 0;
+}
+
+bool LastExpressEngine::isDemo() const {
+	return (bool)(_gameDescription->flags & ADGF_DEMO);
+}
+
+} // End of namespace LastExpress
+
+#if PLUGIN_ENABLED_DYNAMIC(LASTEXPRESS)
+	REGISTER_PLUGIN_DYNAMIC(LASTEXPRESS, PLUGIN_TYPE_ENGINE, LastExpress::LastExpressMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(LASTEXPRESS, PLUGIN_TYPE_ENGINE, LastExpress::LastExpressMetaEngineConnect);
+#endif
diff --git a/engines/lastexpress/module.mk b/engines/lastexpress/module.mk
index afce0b0749..d25a57c581 100644
--- a/engines/lastexpress/module.mk
+++ b/engines/lastexpress/module.mk
@@ -69,9 +69,9 @@ MODULE_OBJS := \
 	sound/queue.o \
 	sound/sound.o \
 	debug.o \
-	detection.o \
 	graphics.o \
 	lastexpress.o \
+	metaengine.o \
 	resource.o
 
 # This module can be built as a plugin
@@ -81,3 +81,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 5593b47e88596ca23d9e3067e3cdd7a040ce551a
    https://github.com/scummvm/scummvm/commit/5593b47e88596ca23d9e3067e3cdd7a040ce551a
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
LILLIPUT: Split detection features & adapt to new plugins.

Changed paths:
  A engines/lilliput/detection.h
  A engines/lilliput/detection_enums.h
  A engines/lilliput/metaengine.cpp
    configure
    engines/lilliput/detection.cpp
    engines/lilliput/lilliput.h
    engines/lilliput/module.mk


diff --git a/configure b/configure
index 06df933f77..d9292e7efc 100755
--- a/configure
+++ b/configure
@@ -6164,7 +6164,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
-								  "KYRA" "LAB" "LASTEXPRESS")
+								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/lilliput/detection.cpp b/engines/lilliput/detection.cpp
index b1206007e5..74d582efb7 100644
--- a/engines/lilliput/detection.cpp
+++ b/engines/lilliput/detection.cpp
@@ -20,31 +20,15 @@
  *
  */
 
+#include "base/plugins.h"
 #include "engines/advancedDetector.h"
-#include "common/system.h"
-#include "common/savefile.h"
 #include "common/textconsole.h"
-#include "graphics/thumbnail.h"
-#include "graphics/surface.h"
 
-#include "lilliput/lilliput.h"
+#include "lilliput/detection_enums.h"
+#include "lilliput/detection.h"
 
 namespace Lilliput {
 
-struct LilliputGameDescription {
-	ADGameDescription desc;
-	GameType gameType;
-};
-
-uint32 LilliputEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-const char *LilliputEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-
 static const PlainGameDescriptor lilliputGames[] = {
 	// Games
 	{"robin", "Adventures of Robin Hood"},
@@ -137,160 +121,8 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Lilliput (C) S.L.Grand, Brainware, 1991-1992";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool LilliputMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
-	if (gd) {
-		*engine = new LilliputEngine(syst, (const LilliputGameDescription *)gd);
-		((LilliputEngine *)*engine)->initGame((const LilliputGameDescription *)gd);
-	}
-	return gd != 0;
-}
-
-bool LilliputMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate);
-}
-
-int LilliputMetaEngine::getMaximumSaveSlot() const {
-	return 99;
-}
-
-SaveStateList LilliputMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += "-##.SAV";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	char slot[3];
-	int slotNum = 0;
-	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
-		slot[0] = filename->c_str()[filename->size() - 6];
-		slot[1] = filename->c_str()[filename->size() - 5];
-		slot[2] = '\0';
-		// Obtain the last 2 digits of the filename (without extension), since they correspond to the save slot
-		slotNum = atoi(slot);
-		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
-			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
-			if (file) {
-				int saveVersion = file->readByte();
-
-				if (saveVersion != kSavegameVersion) {
-					warning("Savegame of incompatible version");
-					delete file;
-					continue;
-				}
-
-				// read name
-				uint16 nameSize = file->readUint16BE();
-				if (nameSize >= 255) {
-					delete file;
-					continue;
-				}
-				char name[256];
-				file->read(name, nameSize);
-				name[nameSize] = 0;
-
-				saveList.push_back(SaveStateDescriptor(slotNum, name));
-				delete file;
-			}
-		}
-	}
-
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor LilliputMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
-	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (file) {
-		int saveVersion = file->readByte();
-
-		if (saveVersion != kSavegameVersion) {
-			warning("Savegame of incompatible version");
-			delete file;
-			return SaveStateDescriptor();
-		}
-
-		uint32 saveNameLength = file->readUint16BE();
-		Common::String saveName;
-		for (uint32 i = 0; i < saveNameLength; ++i) {
-			char curChr = file->readByte();
-			saveName += curChr;
-		}
-
-		SaveStateDescriptor desc(slot, saveName);
-
-		Graphics::Surface *thumbnail;
-		if (!Graphics::loadThumbnail(*file, thumbnail)) {
-			delete file;
-			return SaveStateDescriptor();
-		}
-		desc.setThumbnail(thumbnail);
-
-		desc.setDeletableFlag(true);
-		desc.setWriteProtectedFlag(false);
-
-		uint32 saveDate = file->readUint32BE();
-		uint16 saveTime = file->readUint16BE();
-
-		int day = (saveDate >> 24) & 0xFF;
-		int month = (saveDate >> 16) & 0xFF;
-		int year = saveDate & 0xFFFF;
-
-		desc.setSaveDate(year, month, day);
-
-		int hour = (saveTime >> 8) & 0xFF;
-		int minutes = saveTime & 0xFF;
-
-		desc.setSaveTime(hour, minutes);
-
-		// Slot 0 is used for the 'restart game' save in all Robin games, thus
-		// we prevent it from being deleted.
-		desc.setDeletableFlag(slot != 0);
-		desc.setWriteProtectedFlag(slot == 0);
-
-		delete file;
-		return desc;
-	}
-	return SaveStateDescriptor();
-}
-
-void LilliputMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
 } // End of namespace Lilliput
 
-#if PLUGIN_ENABLED_DYNAMIC(LILLIPUT)
-REGISTER_PLUGIN_DYNAMIC(LILLIPUT, PLUGIN_TYPE_ENGINE, Lilliput::LilliputMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(LILLIPUT, PLUGIN_TYPE_ENGINE, Lilliput::LilliputMetaEngine);
-#endif
-
-namespace Lilliput {
-
-void LilliputEngine::initGame(const LilliputGameDescription *gd) {
-	_gameType = gd->gameType;
-	_platform = gd->desc.platform;
-}
-
-} // End of namespace Lilliput
+REGISTER_PLUGIN_STATIC(LILLIPUT_DETECTION, PLUGIN_TYPE_METAENGINE, Lilliput::LilliputMetaEngine);
diff --git a/engines/lilliput/detection.h b/engines/lilliput/detection.h
new file mode 100644
index 0000000000..74b2e956b3
--- /dev/null
+++ b/engines/lilliput/detection.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Lilliput {
+
+struct LilliputGameDescription {
+	ADGameDescription desc;
+	GameType gameType;
+};
+
+} // End of namespace Lilliput
+
diff --git a/engines/lilliput/detection_enums.h b/engines/lilliput/detection_enums.h
new file mode 100644
index 0000000000..c040e09ddd
--- /dev/null
+++ b/engines/lilliput/detection_enums.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Lilliput {
+
+enum GameType {
+	kGameTypeNone  = 0,
+	kGameTypeRobin,
+	kGameTypeRome
+};
+
+} // End of namespace Lilliput
diff --git a/engines/lilliput/lilliput.h b/engines/lilliput/lilliput.h
index 3921b5fda1..b4e90a0afb 100644
--- a/engines/lilliput/lilliput.h
+++ b/engines/lilliput/lilliput.h
@@ -27,6 +27,7 @@
 #include "lilliput/script.h"
 #include "lilliput/sound.h"
 #include "lilliput/stream.h"
+#include "lilliput/detection_enums.h"
 
 #include "common/file.h"
 #include "common/rect.h"
@@ -54,12 +55,6 @@ namespace Lilliput {
 
 static const int kSavegameVersion = 1;
 
-enum GameType {
-	kGameTypeNone  = 0,
-	kGameTypeRobin,
-	kGameTypeRome
-};
-
 enum LilliputDebugChannels {
 	kDebugEngine    = 1 << 0,
 	kDebugScript    = 1 << 1,
diff --git a/engines/lilliput/metaengine.cpp b/engines/lilliput/metaengine.cpp
new file mode 100644
index 0000000000..e6df2bacfb
--- /dev/null
+++ b/engines/lilliput/metaengine.cpp
@@ -0,0 +1,209 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+#include "common/savefile.h"
+#include "common/textconsole.h"
+#include "graphics/thumbnail.h"
+#include "graphics/surface.h"
+
+#include "lilliput/lilliput.h"
+#include "lilliput/detection.h"
+
+namespace Lilliput {
+
+uint32 LilliputEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+const char *LilliputEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+} // End of namespace Lilliput
+
+namespace Lilliput {
+
+class LilliputMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "lilliput";
+	}
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool LilliputMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+	if (gd) {
+		*engine = new LilliputEngine(syst, (const LilliputGameDescription *)gd);
+		((LilliputEngine *)*engine)->initGame((const LilliputGameDescription *)gd);
+	}
+	return gd != 0;
+}
+
+bool LilliputMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate);
+}
+
+int LilliputMetaEngineConnect::getMaximumSaveSlot() const {
+	return 99;
+}
+
+SaveStateList LilliputMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += "-##.SAV";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	char slot[3];
+	int slotNum = 0;
+	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
+		slot[0] = filename->c_str()[filename->size() - 6];
+		slot[1] = filename->c_str()[filename->size() - 5];
+		slot[2] = '\0';
+		// Obtain the last 2 digits of the filename (without extension), since they correspond to the save slot
+		slotNum = atoi(slot);
+		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
+			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
+			if (file) {
+				int saveVersion = file->readByte();
+
+				if (saveVersion != kSavegameVersion) {
+					warning("Savegame of incompatible version");
+					delete file;
+					continue;
+				}
+
+				// read name
+				uint16 nameSize = file->readUint16BE();
+				if (nameSize >= 255) {
+					delete file;
+					continue;
+				}
+				char name[256];
+				file->read(name, nameSize);
+				name[nameSize] = 0;
+
+				saveList.push_back(SaveStateDescriptor(slotNum, name));
+				delete file;
+			}
+		}
+	}
+
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor LilliputMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
+	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (file) {
+		int saveVersion = file->readByte();
+
+		if (saveVersion != kSavegameVersion) {
+			warning("Savegame of incompatible version");
+			delete file;
+			return SaveStateDescriptor();
+		}
+
+		uint32 saveNameLength = file->readUint16BE();
+		Common::String saveName;
+		for (uint32 i = 0; i < saveNameLength; ++i) {
+			char curChr = file->readByte();
+			saveName += curChr;
+		}
+
+		SaveStateDescriptor desc(slot, saveName);
+
+		Graphics::Surface *thumbnail;
+		if (!Graphics::loadThumbnail(*file, thumbnail)) {
+			delete file;
+			return SaveStateDescriptor();
+		}
+		desc.setThumbnail(thumbnail);
+
+		desc.setDeletableFlag(true);
+		desc.setWriteProtectedFlag(false);
+
+		uint32 saveDate = file->readUint32BE();
+		uint16 saveTime = file->readUint16BE();
+
+		int day = (saveDate >> 24) & 0xFF;
+		int month = (saveDate >> 16) & 0xFF;
+		int year = saveDate & 0xFFFF;
+
+		desc.setSaveDate(year, month, day);
+
+		int hour = (saveTime >> 8) & 0xFF;
+		int minutes = saveTime & 0xFF;
+
+		desc.setSaveTime(hour, minutes);
+
+		// Slot 0 is used for the 'restart game' save in all Robin games, thus
+		// we prevent it from being deleted.
+		desc.setDeletableFlag(slot != 0);
+		desc.setWriteProtectedFlag(slot == 0);
+
+		delete file;
+		return desc;
+	}
+	return SaveStateDescriptor();
+}
+
+void LilliputMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+} // End of namespace Lilliput
+
+#if PLUGIN_ENABLED_DYNAMIC(LILLIPUT)
+	REGISTER_PLUGIN_DYNAMIC(LILLIPUT, PLUGIN_TYPE_ENGINE, Lilliput::LilliputMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(LILLIPUT, PLUGIN_TYPE_ENGINE, Lilliput::LilliputMetaEngineConnect);
+#endif
+
+namespace Lilliput {
+
+void LilliputEngine::initGame(const LilliputGameDescription *gd) {
+	_gameType = gd->gameType;
+	_platform = gd->desc.platform;
+}
+
+} // End of namespace Lilliput
diff --git a/engines/lilliput/module.mk b/engines/lilliput/module.mk
index 8a095e8045..4002907135 100644
--- a/engines/lilliput/module.mk
+++ b/engines/lilliput/module.mk
@@ -2,8 +2,8 @@ MODULE := engines/lilliput
 
 MODULE_OBJS = \
 	console.o \
-	detection.o \
 	lilliput.o \
+	metaengine.o \
 	script.o \
 	sound.o \
 	stream.o
@@ -18,3 +18,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 985faf8d8cffbf6dcb9e271e16b2e1597ebe9275
    https://github.com/scummvm/scummvm/commit/985faf8d8cffbf6dcb9e271e16b2e1597ebe9275
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MACVENTURE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/macventure/metaengine.cpp
    configure
    engines/macventure/detection.cpp
    engines/macventure/module.mk


diff --git a/configure b/configure
index d9292e7efc..7f69b05cec 100755
--- a/configure
+++ b/configure
@@ -6164,7 +6164,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
-								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT")
+								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/macventure/detection.cpp b/engines/macventure/detection.cpp
index 6a3556ac34..062f269569 100644
--- a/engines/macventure/detection.cpp
+++ b/engines/macventure/detection.cpp
@@ -23,9 +23,6 @@
 #include "base/plugins.h"
 
 #include "engines/advancedDetector.h"
-#include "common/system.h"
-
-#include "macventure/macventure.h"
 
 namespace MacVenture {
 
@@ -40,9 +37,6 @@ static const ADGameDescription gameDescriptions[] = {
 	AD_TABLE_END_MARKER
 };
 
-const char *MacVentureEngine::getGameFileName() const {
-	return _gameDescription->filesDescriptions[0].fileName;
-}
 } // End of namespace MacVenture
 
 static const PlainGameDescriptor macventureGames[] = {
@@ -74,112 +68,8 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "(C) ICOM Simulations";
 	}
-
-protected:
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool MacVentureMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime);
-}
-
-bool MacVentureEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-SaveStateList MacVentureMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-		SaveStateDescriptor desc;
-		// Do not allow save slot 0 (used for auto-saving) to be deleted or
-		// overwritten.
-		desc.setDeletableFlag(slotNum != 0);
-		desc.setWriteProtectedFlag(slotNum == 0);
-
-		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				desc = loadMetaData(in, slotNum);
-				if (desc.getSaveSlot() != slotNum) {
-					// invalid
-					delete in;
-					continue;
-				}
-				saveList.push_back(desc);
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int MacVentureMetaEngine::getMaximumSaveSlot() const { return 999; }
-
-bool MacVentureMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *game) const {
-	if (game) {
-		*engine = new MacVenture::MacVentureEngine(syst, game);
-	}
-	return game != 0;
-}
-
-void MacVentureMetaEngine::removeSaveState(const char *target, int slot) const {
-	g_system->getSavefileManager()->removeSavefile(Common::String::format("%s.%03d", target, slot));
-}
-
-
-SaveStateDescriptor MacVentureMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	SaveStateDescriptor desc;
-	Common::String saveFileName;
-	Common::String pattern = target;
-	pattern += ".###";
-	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-		if (slotNum == slot) {
-			saveFileName = *file;
-		}
-	}
-
-	Common::InSaveFile *in = saveFileMan->openForLoading(saveFileName);
-	if (in) {
-		desc = loadMetaData(in, slot, false);
-		delete in;
-		return desc;
-	}
-	return SaveStateDescriptor(-1, "");
-}
-
 } // End of namespace MacVenture
 
-#if PLUGIN_ENABLED_DYNAMIC(MACVENTURE)
- REGISTER_PLUGIN_DYNAMIC(MACVENTURE, PLUGIN_TYPE_ENGINE, MacVenture::MacVentureMetaEngine);
-#else
- REGISTER_PLUGIN_STATIC(MACVENTURE, PLUGIN_TYPE_ENGINE, MacVenture::MacVentureMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(MACVENTURE_DETECTION, PLUGIN_TYPE_METAENGINE, MacVenture::MacVentureMetaEngine);
diff --git a/engines/macventure/metaengine.cpp b/engines/macventure/metaengine.cpp
new file mode 100644
index 0000000000..af5a0bde12
--- /dev/null
+++ b/engines/macventure/metaengine.cpp
@@ -0,0 +1,157 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+
+#include "macventure/macventure.h"
+
+namespace MacVenture {
+
+const char *MacVentureEngine::getGameFileName() const {
+	return _gameDescription->filesDescriptions[0].fileName;
+}
+
+} // End of namespace MacVenture
+
+
+namespace MacVenture {
+
+SaveStateDescriptor loadMetaData(Common::SeekableReadStream *s, int slot, bool skipThumbnail = true);
+
+class MacVentureMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "macventure";
+	}
+
+protected:
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+
+};
+
+bool MacVentureMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime);
+}
+
+bool MacVentureEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+SaveStateList MacVentureMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+		SaveStateDescriptor desc;
+		// Do not allow save slot 0 (used for auto-saving) to be deleted or
+		// overwritten.
+		desc.setDeletableFlag(slotNum != 0);
+		desc.setWriteProtectedFlag(slotNum == 0);
+
+		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				desc = loadMetaData(in, slotNum);
+				if (desc.getSaveSlot() != slotNum) {
+					// invalid
+					delete in;
+					continue;
+				}
+				saveList.push_back(desc);
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int MacVentureMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+
+bool MacVentureMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *game) const {
+	if (game) {
+		*engine = new MacVenture::MacVentureEngine(syst, game);
+	}
+	return game != 0;
+}
+
+void MacVentureMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	g_system->getSavefileManager()->removeSavefile(Common::String::format("%s.%03d", target, slot));
+}
+
+
+SaveStateDescriptor MacVentureMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	SaveStateDescriptor desc;
+	Common::String saveFileName;
+	Common::String pattern = target;
+	pattern += ".###";
+	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+		if (slotNum == slot) {
+			saveFileName = *file;
+		}
+	}
+
+	Common::InSaveFile *in = saveFileMan->openForLoading(saveFileName);
+	if (in) {
+		desc = loadMetaData(in, slot, false);
+		delete in;
+		return desc;
+	}
+	return SaveStateDescriptor(-1, "");
+}
+
+} // End of namespace MacVenture
+
+#if PLUGIN_ENABLED_DYNAMIC(MACVENTURE)
+	REGISTER_PLUGIN_DYNAMIC(MACVENTURE, PLUGIN_TYPE_ENGINE, MacVenture::MacVentureMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(MACVENTURE, PLUGIN_TYPE_ENGINE, MacVenture::MacVentureMetaEngineConnect);
+#endif
diff --git a/engines/macventure/module.mk b/engines/macventure/module.mk
index 227eb41e28..0c0cf8b093 100644
--- a/engines/macventure/module.mk
+++ b/engines/macventure/module.mk
@@ -5,11 +5,11 @@ MODULE_OBJS := \
 	controls.o \
 	cursor.o \
 	datafiles.o \
-	detection.o \
 	dialog.o \
 	gui.o \
 	image.o \
 	macventure.o \
+	metaengine.o \
 	prebuilt_dialogs.o \
 	saveload.o \
 	script.o \
@@ -29,3 +29,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 53131399f9b10a9c9622f96faba60b5757398f26
    https://github.com/scummvm/scummvm/commit/53131399f9b10a9c9622f96faba60b5757398f26
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MADE: Move common game/detection related code into new header files

- Move enums from made.h -> detection_enums.h
- Move MadeGameDescription struct inside detector tables -> detection.h

Changed paths:
  A engines/made/detection.h
  A engines/made/detection_enums.h
    engines/made/detection_tables.h
    engines/made/made.h


diff --git a/engines/made/detection.h b/engines/made/detection.h
new file mode 100644
index 0000000000..d13abfbb44
--- /dev/null
+++ b/engines/made/detection.h
@@ -0,0 +1,36 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+namespace Made {
+
+struct MadeGameDescription {
+	ADGameDescription desc;
+
+	int gameID;
+	int gameType;
+	uint32 features;
+	uint16 version;
+};
+
+} // End of namespace Made
+
diff --git a/engines/made/detection_enums.h b/engines/made/detection_enums.h
new file mode 100644
index 0000000000..bb26d2c5b1
--- /dev/null
+++ b/engines/made/detection_enums.h
@@ -0,0 +1,39 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Made {
+
+enum MadeGameID {
+	GID_RTZ		= 0,
+	GID_MANHOLE	= 1,
+	GID_LGOP2	= 2,
+	GID_RODNEY	= 3
+};
+
+enum MadeGameFeatures {
+	GF_DEMO				= 1 << 0,
+	GF_CD				= 1 << 1,
+	GF_CD_COMPRESSED	= 1 << 2,
+	GF_FLOPPY			= 1 << 3
+};
+
+} // End of namespace Made
diff --git a/engines/made/detection_tables.h b/engines/made/detection_tables.h
index bb590cf0c2..ce52d7dad8 100644
--- a/engines/made/detection_tables.h
+++ b/engines/made/detection_tables.h
@@ -27,15 +27,6 @@
 
 namespace Made {
 
-struct MadeGameDescription {
-	ADGameDescription desc;
-
-	int gameID;
-	int gameType;
-	uint32 features;
-	uint16 version;
-};
-
 static const MadeGameDescription gameDescriptions[] = {
 	{
 		// NOTE: Return to Zork entries with *.dat are used to detect the game via rtzcd.dat,
diff --git a/engines/made/made.h b/engines/made/made.h
index aaf1813b93..3f7007f24e 100644
--- a/engines/made/made.h
+++ b/engines/made/made.h
@@ -24,6 +24,7 @@
 #define MADE_MADE_H
 
 #include "made/sound.h"
+#include "made/detection_enums.h"
 
 #include "engines/engine.h"
 
@@ -42,20 +43,6 @@
  */
 namespace Made {
 
-enum MadeGameID {
-	GID_RTZ		= 0,
-	GID_MANHOLE	= 1,
-	GID_LGOP2	= 2,
-	GID_RODNEY	= 3
-};
-
-enum MadeGameFeatures {
-	GF_DEMO				= 1 << 0,
-	GF_CD				= 1 << 1,
-	GF_CD_COMPRESSED	= 1 << 2,
-	GF_FLOPPY			= 1 << 3
-};
-
 const uint32 kTimerResolution = 40;
 
 struct MadeGameDescription;


Commit: 70ba16f857b09d1f9fafd20615fdb7212455c36b
    https://github.com/scummvm/scummvm/commit/70ba16f857b09d1f9fafd20615fdb7212455c36b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MADE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/made/metaengine.cpp
    configure
    engines/made/detection.cpp
    engines/made/module.mk


diff --git a/configure b/configure
index 7f69b05cec..58dd058a6e 100755
--- a/configure
+++ b/configure
@@ -6164,7 +6164,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
-								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE")
+								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/made/detection.cpp b/engines/made/detection.cpp
index f4147b388c..02dbc5763a 100644
--- a/engines/made/detection.cpp
+++ b/engines/made/detection.cpp
@@ -20,30 +20,11 @@
  *
  */
 
-#include "made/made.h"
-#include "made/detection_tables.h"
-
+#include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-namespace Made {
-
-uint32 MadeEngine::getGameID() const {
-	return _gameDescription->gameID;
-}
-
-uint32 MadeEngine::getFeatures() const {
-	return _gameDescription->features;
-}
-
-Common::Platform MadeEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-uint16 MadeEngine::getVersion() const {
-	return _gameDescription->version;
-}
-
-}
+#include "made/detection_enums.h"
+#include "made/detection.h"
 
 static const PlainGameDescriptor madeGames[] = {
 	{"manhole", "The Manhole"},
@@ -53,6 +34,8 @@ static const PlainGameDescriptor madeGames[] = {
 	{0, 0}
 };
 
+#include "made/detection_tables.h"
+
 class MadeMetaEngine : public AdvancedMetaEngine {
 public:
 	MadeMetaEngine() : AdvancedMetaEngine(Made::gameDescriptions, sizeof(Made::MadeGameDescription), madeGames) {
@@ -70,31 +53,9 @@ public:
 		return "MADE Engine (C) Activision";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
-
 };
 
-bool MadeMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		false;
-}
-
-bool Made::MadeEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher);
-}
-
-bool MadeMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Made::MadeGameDescription *gd = (const Made::MadeGameDescription *)desc;
-	if (gd) {
-		*engine = new Made::MadeEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
 ADDetectedGame MadeMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	// Set the default values for the fallback descriptor's ADGameDescription part.
 	Made::g_fallbackDesc.desc.language = Common::UNK_LANG;
@@ -110,8 +71,4 @@ ADDetectedGame MadeMetaEngine::fallbackDetect(const FileMap &allFiles, const Com
 	return ADDetectedGame();
 }
 
-#if PLUGIN_ENABLED_DYNAMIC(MADE)
-	REGISTER_PLUGIN_DYNAMIC(MADE, PLUGIN_TYPE_ENGINE, MadeMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(MADE, PLUGIN_TYPE_ENGINE, MadeMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(MADE_DETECTION, PLUGIN_TYPE_METAENGINE, MadeMetaEngine);
diff --git a/engines/made/metaengine.cpp b/engines/made/metaengine.cpp
new file mode 100644
index 0000000000..cacc7b929e
--- /dev/null
+++ b/engines/made/metaengine.cpp
@@ -0,0 +1,80 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/advancedDetector.h"
+#include "made/made.h"
+#include "made/detection.h"
+
+
+namespace Made {
+
+uint32 MadeEngine::getGameID() const {
+	return _gameDescription->gameID;
+}
+
+uint32 MadeEngine::getFeatures() const {
+	return _gameDescription->features;
+}
+
+Common::Platform MadeEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+uint16 MadeEngine::getVersion() const {
+	return _gameDescription->version;
+}
+
+} // End of namespace Made
+
+class MadeMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "made";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool MadeMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		false;
+}
+
+bool Made::MadeEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher);
+}
+
+bool MadeMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Made::MadeGameDescription *gd = (const Made::MadeGameDescription *)desc;
+	if (gd) {
+		*engine = new Made::MadeEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(MADE)
+	REGISTER_PLUGIN_DYNAMIC(MADE, PLUGIN_TYPE_ENGINE, MadeMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(MADE, PLUGIN_TYPE_ENGINE, MadeMetaEngineConnect);
+#endif
diff --git a/engines/made/module.mk b/engines/made/module.mk
index d8c0c9eeb5..2717b4d3c4 100644
--- a/engines/made/module.mk
+++ b/engines/made/module.mk
@@ -3,9 +3,9 @@ MODULE := engines/made
 MODULE_OBJS := \
 	console.o \
 	database.o \
-	detection.o \
 	graphics.o \
 	made.o \
+	metaengine.o \
 	music.o \
 	pmvplayer.o \
 	redreader.o \
@@ -24,3 +24,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: d338d4c7d434216ab25e80418c4b91921546b7c5
    https://github.com/scummvm/scummvm/commit/d338d4c7d434216ab25e80418c4b91921546b7c5
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MADS: Split detection features & adapt to new plugins.

Changed paths:
  A engines/mads/detection.h
  A engines/mads/detection_enums.h
  A engines/mads/metaengine.cpp
    configure
    engines/mads/detection.cpp
    engines/mads/mads.h
    engines/mads/module.mk


diff --git a/configure b/configure
index 58dd058a6e..b999cb87c3 100755
--- a/configure
+++ b/configure
@@ -6164,7 +6164,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
-								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE")
+								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/mads/detection.cpp b/engines/mads/detection.cpp
index d5d7415c10..f8c31ab64a 100644
--- a/engines/mads/detection.cpp
+++ b/engines/mads/detection.cpp
@@ -21,51 +21,14 @@
  *
  */
 
-#include "mads/mads.h"
-
 #include "base/plugins.h"
-#include "common/savefile.h"
 #include "common/str-array.h"
-#include "common/memstream.h"
 #include "engines/advancedDetector.h"
 #include "common/system.h"
 #include "common/translation.h"
-#include "graphics/surface.h"
-#include "mads/events.h"
-#include "mads/game.h"
-
-#define MAX_SAVES 99
-
-namespace MADS {
-
-struct MADSGameDescription {
-	ADGameDescription desc;
-
-	int gameID;
-	uint32 features;
-};
-
-uint32 MADSEngine::getGameID() const {
-	return _gameDescription->gameID;
-}
-
-uint32 MADSEngine::getGameFeatures() const {
-	return _gameDescription->features;
-}
-
-uint32 MADSEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
 
-Common::Language MADSEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-Common::Platform MADSEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-} // End of namespace MADS
+#include "mads/detection_enums.h"
+#include "mads/detection.h"
 
 static const PlainGameDescriptor MADSGames[] = {
 	{"dragonsphere", "Dragonsphere"},
@@ -169,107 +132,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "MADS (C) Microprose";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool MADSMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSimpleSavesNames);
-}
-
-bool MADS::MADSEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool MADSMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const MADS::MADSGameDescription *gd = (const MADS::MADSGameDescription *)desc;
-	if (gd) {
-		*engine = new MADS::MADSEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList MADSMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.0##", target);
-	MADS::MADSSavegameHeader header;
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		const char *ext = strrchr(file->c_str(), '.');
-		int slot = ext ? atoi(ext + 1) : -1;
-
-		if (slot >= 0 && slot < MAX_SAVES) {
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-			if (in) {
-				if (MADS::Game::readSavegameHeader(in, header))
-					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int MADSMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVES;
-}
-
-void MADSMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor MADSMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
-
-	if (f) {
-		MADS::MADSSavegameHeader header;
-		if (!MADS::Game::readSavegameHeader(f, header, false)) {
-			delete f;
-			return SaveStateDescriptor();
-		}
-		delete f;
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header._saveName);
-		desc.setThumbnail(header._thumbnail);
-		desc.setSaveDate(header._year, header._month, header._day);
-		desc.setSaveTime(header._hour, header._minute);
-		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-
-#if PLUGIN_ENABLED_DYNAMIC(MADS)
-	REGISTER_PLUGIN_DYNAMIC(MADS, PLUGIN_TYPE_ENGINE, MADSMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(MADS, PLUGIN_TYPE_ENGINE, MADSMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(MADS_DETECTION, PLUGIN_TYPE_METAENGINE, MADSMetaEngine);
diff --git a/engines/mads/detection.h b/engines/mads/detection.h
new file mode 100644
index 0000000000..5e36dfb6f0
--- /dev/null
+++ b/engines/mads/detection.h
@@ -0,0 +1,34 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ *
+ */
+
+
+namespace MADS {
+
+struct MADSGameDescription {
+	ADGameDescription desc;
+
+	int gameID;
+	uint32 features;
+};
+
+} // End of namespace MADS
diff --git a/engines/mads/detection_enums.h b/engines/mads/detection_enums.h
new file mode 100644
index 0000000000..a0fd396cba
--- /dev/null
+++ b/engines/mads/detection_enums.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace MADS {
+
+enum {
+	GType_RexNebular = 0,
+	GType_Dragonsphere = 1,
+	GType_Phantom = 2
+};
+
+} // End of namespace MADS
diff --git a/engines/mads/mads.h b/engines/mads/mads.h
index 4b98af1836..9cda26e63a 100644
--- a/engines/mads/mads.h
+++ b/engines/mads/mads.h
@@ -40,6 +40,7 @@
 #include "mads/msurface.h"
 #include "mads/resources.h"
 #include "mads/sound.h"
+#include "mads/detection_enums.h"
 
 /**
  * This is the namespace of the MADS engine.
@@ -61,12 +62,6 @@ enum MADSDebugChannels {
 	kDebugGraphics	= 1 << 2
 };
 
-enum {
-	GType_RexNebular = 0,
-	GType_Dragonsphere = 1,
-	GType_Phantom = 2
-};
-
 enum ScreenFade {
 	SCREEN_FADE_SMOOTH = 0,
 	SCREEN_FADE_MEDIUM = 1,
diff --git a/engines/mads/metaengine.cpp b/engines/mads/metaengine.cpp
new file mode 100644
index 0000000000..9ba6633666
--- /dev/null
+++ b/engines/mads/metaengine.cpp
@@ -0,0 +1,174 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ *
+ */
+
+#include "mads/mads.h"
+
+#include "base/plugins.h"
+#include "engines/advancedDetector.h"
+
+#include "common/savefile.h"
+#include "common/str-array.h"
+#include "common/memstream.h"
+#include "common/system.h"
+#include "common/translation.h"
+#include "graphics/surface.h"
+
+#include "mads/events.h"
+#include "mads/game.h"
+#include "mads/detection.h"
+
+#define MAX_SAVES 99
+
+namespace MADS {
+
+uint32 MADSEngine::getGameID() const {
+	return _gameDescription->gameID;
+}
+
+uint32 MADSEngine::getGameFeatures() const {
+	return _gameDescription->features;
+}
+
+uint32 MADSEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language MADSEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+Common::Platform MADSEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+} // End of namespace MADS
+
+class MADSMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "mads";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool MADSMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSimpleSavesNames);
+}
+
+bool MADS::MADSEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool MADSMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const MADS::MADSGameDescription *gd = (const MADS::MADSGameDescription *)desc;
+	if (gd) {
+		*engine = new MADS::MADSEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList MADSMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.0##", target);
+	MADS::MADSSavegameHeader header;
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		const char *ext = strrchr(file->c_str(), '.');
+		int slot = ext ? atoi(ext + 1) : -1;
+
+		if (slot >= 0 && slot < MAX_SAVES) {
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+			if (in) {
+				if (MADS::Game::readSavegameHeader(in, header))
+					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int MADSMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVES;
+}
+
+void MADSMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor MADSMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
+
+	if (f) {
+		MADS::MADSSavegameHeader header;
+		if (!MADS::Game::readSavegameHeader(f, header, false)) {
+			delete f;
+			return SaveStateDescriptor();
+		}
+		delete f;
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header._saveName);
+		desc.setThumbnail(header._thumbnail);
+		desc.setSaveDate(header._year, header._month, header._day);
+		desc.setSaveTime(header._hour, header._minute);
+		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(MADS)
+	REGISTER_PLUGIN_DYNAMIC(MADS, PLUGIN_TYPE_ENGINE, MADSMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(MADS, PLUGIN_TYPE_ENGINE, MADSMetaEngineConnect);
+#endif
diff --git a/engines/mads/module.mk b/engines/mads/module.mk
index 8f154394bf..2093fcb71f 100644
--- a/engines/mads/module.mk
+++ b/engines/mads/module.mk
@@ -35,7 +35,6 @@ MODULE_OBJS := \
 	compression.o \
 	conversations.o \
 	debugger.o \
-	detection.o \
 	dialogs.o \
 	events.o \
 	font.o \
@@ -48,6 +47,7 @@ MODULE_OBJS := \
 	menu_views.o \
 	messages.o \
 	msurface.o \
+	metaengine.o \
 	palette.o \
 	player.o \
 	rails.o \
@@ -68,3 +68,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 394aa54b7b7d328119a930e7c209dd0692b657d5
    https://github.com/scummvm/scummvm/commit/394aa54b7b7d328119a930e7c209dd0692b657d5
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MORTEVIELLE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/mortevielle/detection.h
  A engines/mortevielle/detection_enums.h
  A engines/mortevielle/metaengine.cpp
    configure
    engines/mortevielle/detection.cpp
    engines/mortevielle/module.mk
    engines/mortevielle/mortevielle.h


diff --git a/configure b/configure
index b999cb87c3..4de7cc10f1 100755
--- a/configure
+++ b/configure
@@ -6164,7 +6164,8 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
-								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS")
+								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
+								  "MORTEVIELLE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/mortevielle/detection.cpp b/engines/mortevielle/detection.cpp
index a2d32c1fc5..a0d85c7ae0 100644
--- a/engines/mortevielle/detection.cpp
+++ b/engines/mortevielle/detection.cpp
@@ -23,25 +23,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "mortevielle/mortevielle.h"
-#include "mortevielle/saveload.h"
-
-namespace Mortevielle {
-struct MortevielleGameDescription {
-	ADGameDescription desc;
-	Common::Language originalLanguage;
-	uint8 dataFeature;
-};
-
-uint32 MortevielleEngine::getGameFlags() const { return _gameDescription->desc.flags; }
-
-Common::Language MortevielleEngine::getLanguage() const { return _gameDescription->desc.language; }
-
-Common::Language MortevielleEngine::getOriginalLanguage() const { return _gameDescription->originalLanguage; }
-
-bool MortevielleEngine::useOriginalData() const { return _gameDescription->dataFeature == kUseOriginalData; }
-
-}
+#include "mortevielle/detection.h"
+#include "mortevielle/detection_enums.h"
 
 static const PlainGameDescriptor MortevielleGame[] = {
 	{"mortevielle", "Mortville Manor"},
@@ -71,50 +54,7 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Mortville Manor (C) 1987-89 Lankhor";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool MortevielleMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Mortevielle::MortevielleEngine(syst, (const Mortevielle::MortevielleGameDescription *)desc);
-	}
-	return desc != 0;
-}
-
-bool MortevielleMetaEngine::hasFeature(MetaEngineFeature f) const {
-	switch (f) {
-	case kSupportsListSaves:
-	case kSupportsDeleteSave:
-	case kSupportsLoadingDuringStartup:
-	case kSavesSupportMetaInfo:
-	case kSavesSupportThumbnail:
-	case kSavesSupportCreationDate:
-	case kSimpleSavesNames:
-		return true;
-	default:
-		return false;
-	}
-}
-
-int MortevielleMetaEngine::getMaximumSaveSlot() const { return 99; }
-
-SaveStateList MortevielleMetaEngine::listSaves(const char *target) const {
-	return Mortevielle::SavegameManager::listSaves(target);
-}
-
-SaveStateDescriptor MortevielleMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Mortevielle::MortevielleEngine::generateSaveFilename(target, slot);
-	return Mortevielle::SavegameManager::querySaveMetaInfos(filename);
-}
-
 
-#if PLUGIN_ENABLED_DYNAMIC(MORTEVIELLE)
-	REGISTER_PLUGIN_DYNAMIC(MORTEVIELLE, PLUGIN_TYPE_ENGINE, MortevielleMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(MORTEVIELLE, PLUGIN_TYPE_ENGINE, MortevielleMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(MORTEVIELLE_DETECTION, PLUGIN_TYPE_METAENGINE, MortevielleMetaEngine);
diff --git a/engines/mortevielle/detection.h b/engines/mortevielle/detection.h
new file mode 100644
index 0000000000..0855afe14d
--- /dev/null
+++ b/engines/mortevielle/detection.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Mortevielle {
+
+struct MortevielleGameDescription {
+	ADGameDescription desc;
+	Common::Language originalLanguage;
+	uint8 dataFeature;
+};
+
+} // End of namespace Mortevielle
diff --git a/engines/mortevielle/detection_enums.h b/engines/mortevielle/detection_enums.h
new file mode 100644
index 0000000000..a1c5bd8ba2
--- /dev/null
+++ b/engines/mortevielle/detection_enums.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Mortevielle {
+
+enum {
+	kUseOriginalData = 0,
+	kUseEngineDataFile = 1
+};
+
+} // End of namespace Mortevielle
diff --git a/engines/mortevielle/metaengine.cpp b/engines/mortevielle/metaengine.cpp
new file mode 100644
index 0000000000..6bc1e23ef2
--- /dev/null
+++ b/engines/mortevielle/metaengine.cpp
@@ -0,0 +1,93 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+#include "engines/advancedDetector.h"
+
+#include "mortevielle/mortevielle.h"
+#include "mortevielle/saveload.h"
+#include "mortevielle/detection.h"
+
+namespace Mortevielle {
+
+uint32 MortevielleEngine::getGameFlags() const { return _gameDescription->desc.flags; }
+
+Common::Language MortevielleEngine::getLanguage() const { return _gameDescription->desc.language; }
+
+Common::Language MortevielleEngine::getOriginalLanguage() const { return _gameDescription->originalLanguage; }
+
+bool MortevielleEngine::useOriginalData() const { return _gameDescription->dataFeature == kUseOriginalData; }
+
+} // End of namespace Mortevielle
+
+class MortevielleMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "mortevielle";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool MortevielleMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Mortevielle::MortevielleEngine(syst, (const Mortevielle::MortevielleGameDescription *)desc);
+	}
+	return desc != 0;
+}
+
+bool MortevielleMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	switch (f) {
+	case kSupportsListSaves:
+	case kSupportsDeleteSave:
+	case kSupportsLoadingDuringStartup:
+	case kSavesSupportMetaInfo:
+	case kSavesSupportThumbnail:
+	case kSavesSupportCreationDate:
+	case kSimpleSavesNames:
+		return true;
+	default:
+		return false;
+	}
+}
+
+int MortevielleMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+
+SaveStateList MortevielleMetaEngineConnect::listSaves(const char *target) const {
+	return Mortevielle::SavegameManager::listSaves(target);
+}
+
+SaveStateDescriptor MortevielleMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Mortevielle::MortevielleEngine::generateSaveFilename(target, slot);
+	return Mortevielle::SavegameManager::querySaveMetaInfos(filename);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(MORTEVIELLE)
+	REGISTER_PLUGIN_DYNAMIC(MORTEVIELLE, PLUGIN_TYPE_ENGINE, MortevielleMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(MORTEVIELLE, PLUGIN_TYPE_ENGINE, MortevielleMetaEngineConnect);
+#endif
\ No newline at end of file
diff --git a/engines/mortevielle/module.mk b/engines/mortevielle/module.mk
index 7188e36958..0c525fefe3 100644
--- a/engines/mortevielle/module.mk
+++ b/engines/mortevielle/module.mk
@@ -3,10 +3,10 @@ MODULE := engines/mortevielle
 MODULE_OBJS := \
 	actions.o \
 	debugger.o \
-	detection.o \
 	dialogs.o \
 	graphics.o \
 	menu.o \
+	metaengine.o \
 	mortevielle.o \
 	mouse.o \
 	outtext.o \
@@ -21,3 +21,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mortevielle/mortevielle.h b/engines/mortevielle/mortevielle.h
index 039a55324f..93872c8f43 100644
--- a/engines/mortevielle/mortevielle.h
+++ b/engines/mortevielle/mortevielle.h
@@ -44,6 +44,7 @@
 #include "mortevielle/saveload.h"
 #include "mortevielle/sound.h"
 #include "mortevielle/outtext.h"
+#include "mortevielle/detection_enums.h"
 
 namespace Mortevielle {
 
@@ -61,11 +62,6 @@ enum {
 	MORTDAT_LANG_GERMAN = 2
 };
 
-enum {
-	kUseOriginalData = 0,
-	kUseEngineDataFile = 1
-};
-
 // Static string list
 enum {
 	S_YES_NO = 0, S_GO_TO = 1, S_SOMEONE_ENTERS = 2, S_COOL = 3, S_LOURDE = 4,


Commit: 056f26402a80ffb80fd6d81421d049eccb2ddba6
    https://github.com/scummvm/scummvm/commit/056f26402a80ffb80fd6d81421d049eccb2ddba6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MUTATIONOFJB: Split detection features & adapt to new plugins.

Changed paths:
  A engines/mutationofjb/metaengine.cpp
    configure
    engines/mutationofjb/detection.cpp
    engines/mutationofjb/module.mk


diff --git a/configure b/configure
index 4de7cc10f1..6dae80f061 100755
--- a/configure
+++ b/configure
@@ -6165,7 +6165,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
-								  "MORTEVIELLE")
+								  "MORTEVIELLE" "MUTATIONOFJB")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/mutationofjb/detection.cpp b/engines/mutationofjb/detection.cpp
index cbe50ccc96..a88db46fdf 100644
--- a/engines/mutationofjb/detection.cpp
+++ b/engines/mutationofjb/detection.cpp
@@ -20,13 +20,7 @@
  *
  */
 
-#include "mutationofjb/mutationofjb.h"
-
-#include "common/config-manager.h"
-#include "common/system.h"
-#include "common/savefile.h"
-#include "common/serializer.h"
-
+#include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
 static const PlainGameDescriptor mutationofjbGames[] = {
@@ -103,56 +97,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Mutation of J.B. (C) 1996 RIKI Computer Games";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
-		if (desc) {
-			*engine = new MutationOfJB::MutationOfJBEngine(syst, desc);
-		}
-		return desc != nullptr;
-	}
-
-	bool hasFeature(MetaEngineFeature f) const override {
-		if (f == kSupportsListSaves || f == kSimpleSavesNames || f == kSupportsLoadingDuringStartup) {
-			return true;
-		}
-
-		return false;
-	}
-
-	int getMaximumSaveSlot() const override {
-		return 999;
-	}
-
-	SaveStateList listSaves(const char *target) const override {
-		Common::SaveFileManager *const saveFileMan = g_system->getSavefileManager();
-		Common::StringArray filenames;
-		Common::String pattern = target;
-		pattern += ".###";
-
-		filenames = saveFileMan->listSavefiles(pattern);
-
-		SaveStateList saveList;
-		int slotNo = 0;
-		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-			// Obtain the last 3 digits of the filename, since they correspond to the save slot
-			slotNo = atoi(file->c_str() + file->size() - 3);
-
-			Common::InSaveFile *const in = saveFileMan->openForLoading(*file);
-			if (in) {
-				Common::Serializer sz(in, nullptr);
-
-				MutationOfJB::SaveHeader saveHdr;
-				if (saveHdr.sync(sz)) {
-					saveList.push_back(SaveStateDescriptor(slotNo, saveHdr._description));
-				}
-			}
-		}
-		return saveList;
-	}
 };
 
-#if PLUGIN_ENABLED_DYNAMIC(MUTATIONOFJB)
-	REGISTER_PLUGIN_DYNAMIC(MUTATIONOFJB, PLUGIN_TYPE_ENGINE, MutationOfJBMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(MUTATIONOFJB, PLUGIN_TYPE_ENGINE, MutationOfJBMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(MUTATIONOFJB_DETECTION, PLUGIN_TYPE_METAENGINE, MutationOfJBMetaEngine);
diff --git a/engines/mutationofjb/metaengine.cpp b/engines/mutationofjb/metaengine.cpp
new file mode 100644
index 0000000000..453bf28929
--- /dev/null
+++ b/engines/mutationofjb/metaengine.cpp
@@ -0,0 +1,89 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "mutationofjb/mutationofjb.h"
+
+#include "common/config-manager.h"
+#include "common/system.h"
+#include "common/savefile.h"
+#include "common/serializer.h"
+
+#include "engines/advancedDetector.h"
+
+class MutationOfJBMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "mutationofjb";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
+		if (desc) {
+			*engine = new MutationOfJB::MutationOfJBEngine(syst, desc);
+		}
+		return desc != nullptr;
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override {
+		if (f == kSupportsListSaves || f == kSimpleSavesNames || f == kSupportsLoadingDuringStartup) {
+			return true;
+		}
+
+		return false;
+	}
+
+	int getMaximumSaveSlot() const override {
+		return 999;
+	}
+
+	SaveStateList listSaves(const char *target) const override {
+		Common::SaveFileManager *const saveFileMan = g_system->getSavefileManager();
+		Common::StringArray filenames;
+		Common::String pattern = target;
+		pattern += ".###";
+
+		filenames = saveFileMan->listSavefiles(pattern);
+
+		SaveStateList saveList;
+		int slotNo = 0;
+		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+			// Obtain the last 3 digits of the filename, since they correspond to the save slot
+			slotNo = atoi(file->c_str() + file->size() - 3);
+
+			Common::InSaveFile *const in = saveFileMan->openForLoading(*file);
+			if (in) {
+				Common::Serializer sz(in, nullptr);
+
+				MutationOfJB::SaveHeader saveHdr;
+				if (saveHdr.sync(sz)) {
+					saveList.push_back(SaveStateDescriptor(slotNo, saveHdr._description));
+				}
+			}
+		}
+		return saveList;
+	}
+};
+
+#if PLUGIN_ENABLED_DYNAMIC(MUTATIONOFJB)
+	REGISTER_PLUGIN_DYNAMIC(MUTATIONOFJB, PLUGIN_TYPE_ENGINE, MutationOfJBMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(MUTATIONOFJB, PLUGIN_TYPE_ENGINE, MutationOfJBMetaEngineConnect);
+#endif
diff --git a/engines/mutationofjb/module.mk b/engines/mutationofjb/module.mk
index 9e3b1d75d7..f45acd8db1 100644
--- a/engines/mutationofjb/module.mk
+++ b/engines/mutationofjb/module.mk
@@ -45,7 +45,6 @@ MODULE_OBJS := \
 	assets.o \
 	conversationlinelist.o \
 	debug.o \
-	detection.o \
 	encryptedfile.o \
 	font.o \
 	game.o \
@@ -55,6 +54,7 @@ MODULE_OBJS := \
 	hardcodedstrings.o \
 	inventory.o \
 	inventoryitemdefinitionlist.o \
+	metaengine.o \
 	mutationofjb.o \
 	room.o \
 	script.o \
@@ -68,3 +68,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: fbac5798fb595fab07434b443dbb1c862128353c
    https://github.com/scummvm/scummvm/commit/fbac5798fb595fab07434b443dbb1c862128353c
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
NEVERHOOD: Split detection features & adapt to new plugins.

Changed paths:
  A engines/neverhood/detection.h
  A engines/neverhood/metaengine.cpp
    configure
    engines/neverhood/detection.cpp
    engines/neverhood/module.mk


diff --git a/configure b/configure
index 6dae80f061..85ea8c0327 100755
--- a/configure
+++ b/configure
@@ -6165,7 +6165,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
-								  "MORTEVIELLE" "MUTATIONOFJB")
+								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/neverhood/detection.cpp b/engines/neverhood/detection.cpp
index 5ed615efad..036b3397a2 100644
--- a/engines/neverhood/detection.cpp
+++ b/engines/neverhood/detection.cpp
@@ -26,39 +26,7 @@
 #include "common/file.h"
 #include "common/translation.h"
 
-#include "neverhood/neverhood.h"
-
-enum NeverhoodGameFeatures {
-	GF_BIG_DEMO = (1 << 0)
-};
-
-namespace Neverhood {
-
-const char *NeverhoodEngine::getGameId() const {
-	return _gameDescription->gameId;
-}
-
-Common::Platform NeverhoodEngine::getPlatform() const {
-	return _gameDescription->platform;
-}
-
-Common::Language NeverhoodEngine::getLanguage() const {
-	return _gameDescription->language;
-}
-
-bool NeverhoodEngine::isDemo() const {
-	return _gameDescription->flags & ADGF_DEMO;
-}
-
-bool NeverhoodEngine::isBigDemo() const {
-	return _gameDescription->flags & GF_BIG_DEMO;
-}
-
-bool NeverhoodEngine::applyResourceFixes() const {
-	return getLanguage() == Common::RU_RUS;
-}
-
-}
+#include "neverhood/detection.h"
 
 static const PlainGameDescriptor neverhoodGames[] = {
 	{"neverhood", "The Neverhood Chronicles"},
@@ -180,42 +148,9 @@ public:
 		return "The Neverhood Chronicles (C) The Neverhood, Inc.";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-
 };
 
-bool NeverhoodMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Neverhood::NeverhoodEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool NeverhoodMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Neverhood::NeverhoodEngine(syst, desc);
-	}
-	return desc != 0;
-}
-
 const ExtraGuiOptions NeverhoodMetaEngine::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	options.push_back(neverhoodExtraGuiOption1);
@@ -224,79 +159,4 @@ const ExtraGuiOptions NeverhoodMetaEngine::getExtraGuiOptions(const Common::Stri
 	return options;
 }
 
-SaveStateList NeverhoodMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Neverhood::NeverhoodEngine::SaveHeader header;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	Common::StringArray filenames;
-	filenames = saveFileMan->listSavefiles(pattern.c_str());
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); file++) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
-			if (in) {
-				if (Neverhood::NeverhoodEngine::readSaveHeader(in, header) == Neverhood::NeverhoodEngine::kRSHENoError) {
-					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
-				}
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int NeverhoodMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-void NeverhoodMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::String filename = Neverhood::NeverhoodEngine::getSavegameFilename(target, slot);
-	saveFileMan->removeSavefile(filename.c_str());
-}
-
-SaveStateDescriptor NeverhoodMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Neverhood::NeverhoodEngine::getSavegameFilename(target, slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
-
-	if (in) {
-		Neverhood::NeverhoodEngine::SaveHeader header;
-		Neverhood::NeverhoodEngine::kReadSaveHeaderError error;
-
-		error = Neverhood::NeverhoodEngine::readSaveHeader(in, header, false);
-		delete in;
-
-		if (error == Neverhood::NeverhoodEngine::kRSHENoError) {
-			SaveStateDescriptor desc(slot, header.description);
-
-			desc.setDeletableFlag(false);
-			desc.setWriteProtectedFlag(false);
-			desc.setThumbnail(header.thumbnail);
-			int day = (header.saveDate >> 24) & 0xFF;
-			int month = (header.saveDate >> 16) & 0xFF;
-			int year = header.saveDate & 0xFFFF;
-			desc.setSaveDate(year, month, day);
-			int hour = (header.saveTime >> 16) & 0xFF;
-			int minutes = (header.saveTime >> 8) & 0xFF;
-			desc.setSaveTime(hour, minutes);
-			desc.setPlayTime(header.playTime * 1000);
-			return desc;
-		}
-	}
-
-	return SaveStateDescriptor();
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(NEVERHOOD)
-	REGISTER_PLUGIN_DYNAMIC(NEVERHOOD, PLUGIN_TYPE_ENGINE, NeverhoodMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(NEVERHOOD, PLUGIN_TYPE_ENGINE, NeverhoodMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(NEVERHOOD_DETECTION, PLUGIN_TYPE_METAENGINE, NeverhoodMetaEngine);
diff --git a/engines/neverhood/detection.h b/engines/neverhood/detection.h
new file mode 100644
index 0000000000..369050894f
--- /dev/null
+++ b/engines/neverhood/detection.h
@@ -0,0 +1,34 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Neverhood {
+
+struct NeverhoodGameDescription {
+	ADGameDescription desc;
+
+	int gameID;
+	int gameType;
+	uint32 features;
+	uint16 version;
+};
+
+} // End of namespace Neverhood
diff --git a/engines/neverhood/metaengine.cpp b/engines/neverhood/metaengine.cpp
new file mode 100644
index 0000000000..239a1955d6
--- /dev/null
+++ b/engines/neverhood/metaengine.cpp
@@ -0,0 +1,180 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+#include "common/file.h"
+#include "common/translation.h"
+
+#include "neverhood/neverhood.h"
+#include "neverhood/detection.h"
+
+enum NeverhoodGameFeatures {
+	GF_BIG_DEMO = (1 << 0)
+};
+
+namespace Neverhood {
+
+const char *NeverhoodEngine::getGameId() const {
+	return _gameDescription->gameId;
+}
+
+Common::Platform NeverhoodEngine::getPlatform() const {
+	return _gameDescription->platform;
+}
+
+Common::Language NeverhoodEngine::getLanguage() const {
+	return _gameDescription->language;
+}
+
+bool NeverhoodEngine::isDemo() const {
+	return _gameDescription->flags & ADGF_DEMO;
+}
+
+bool NeverhoodEngine::isBigDemo() const {
+	return _gameDescription->flags & GF_BIG_DEMO;
+}
+
+bool NeverhoodEngine::applyResourceFixes() const {
+	return getLanguage() == Common::RU_RUS;
+}
+
+} // End of namespace Neverhood
+
+class NeverhoodMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "neverhood";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool NeverhoodMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Neverhood::NeverhoodEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool NeverhoodMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Neverhood::NeverhoodEngine(syst, desc);
+	}
+	return desc != 0;
+}
+
+SaveStateList NeverhoodMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Neverhood::NeverhoodEngine::SaveHeader header;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	Common::StringArray filenames;
+	filenames = saveFileMan->listSavefiles(pattern.c_str());
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); file++) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
+			if (in) {
+				if (Neverhood::NeverhoodEngine::readSaveHeader(in, header) == Neverhood::NeverhoodEngine::kRSHENoError) {
+					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
+				}
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int NeverhoodMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+void NeverhoodMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::String filename = Neverhood::NeverhoodEngine::getSavegameFilename(target, slot);
+	saveFileMan->removeSavefile(filename.c_str());
+}
+
+SaveStateDescriptor NeverhoodMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Neverhood::NeverhoodEngine::getSavegameFilename(target, slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
+
+	if (in) {
+		Neverhood::NeverhoodEngine::SaveHeader header;
+		Neverhood::NeverhoodEngine::kReadSaveHeaderError error;
+
+		error = Neverhood::NeverhoodEngine::readSaveHeader(in, header, false);
+		delete in;
+
+		if (error == Neverhood::NeverhoodEngine::kRSHENoError) {
+			SaveStateDescriptor desc(slot, header.description);
+
+			desc.setDeletableFlag(false);
+			desc.setWriteProtectedFlag(false);
+			desc.setThumbnail(header.thumbnail);
+			int day = (header.saveDate >> 24) & 0xFF;
+			int month = (header.saveDate >> 16) & 0xFF;
+			int year = header.saveDate & 0xFFFF;
+			desc.setSaveDate(year, month, day);
+			int hour = (header.saveTime >> 16) & 0xFF;
+			int minutes = (header.saveTime >> 8) & 0xFF;
+			desc.setSaveTime(hour, minutes);
+			desc.setPlayTime(header.playTime * 1000);
+			return desc;
+		}
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(NEVERHOOD)
+	REGISTER_PLUGIN_DYNAMIC(NEVERHOOD, PLUGIN_TYPE_ENGINE, NeverhoodMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(NEVERHOOD, PLUGIN_TYPE_ENGINE, NeverhoodMetaEngineConnect);
+#endif
diff --git a/engines/neverhood/module.mk b/engines/neverhood/module.mk
index 9c1220134c..2ffef0c3bb 100644
--- a/engines/neverhood/module.mk
+++ b/engines/neverhood/module.mk
@@ -4,7 +4,6 @@ MODULE_OBJS = \
 	background.o \
 	blbarchive.o \
 	console.o \
-	detection.o \
 	diskplayerscene.o \
 	entity.o \
 	gamemodule.o \
@@ -12,6 +11,7 @@ MODULE_OBJS = \
 	graphics.o \
 	klaymen.o \
 	menumodule.o \
+	metaengine.o \
 	microtiles.o \
 	module.o \
 	modules/module1000.o \
@@ -75,3 +75,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: d3f164698a3bd281297b3d36493ab1a58f08b98a
    https://github.com/scummvm/scummvm/commit/d3f164698a3bd281297b3d36493ab1a58f08b98a
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PARALLACTION: Split detection features & adapt to new plugins.

Changed paths:
  A engines/parallaction/detection.h
  A engines/parallaction/metaengine.cpp
    configure
    engines/parallaction/detection.cpp
    engines/parallaction/module.mk


diff --git a/configure b/configure
index 85ea8c0327..6345d220ff 100755
--- a/configure
+++ b/configure
@@ -6165,7 +6165,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
-								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD")
+								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/parallaction/detection.cpp b/engines/parallaction/detection.cpp
index 0c515d2331..9351c247ba 100644
--- a/engines/parallaction/detection.cpp
+++ b/engines/parallaction/detection.cpp
@@ -28,21 +28,7 @@
 #include "common/textconsole.h"
 
 #include "parallaction/parallaction.h"
-
-namespace Parallaction {
-
-struct PARALLACTIONGameDescription {
-	ADGameDescription desc;
-
-	int gameType;
-	uint32 features;
-};
-
-int Parallaction::getGameType() const { return _gameDescription->gameType; }
-uint32 Parallaction::getFeatures() const { return _gameDescription->features; }
-Common::Language Parallaction::getLanguage() const { return _gameDescription->desc.language; }
-Common::Platform Parallaction::getPlatform() const { return _gameDescription->desc.platform; }
-}
+#include "parallaction/detection.h"
 
 static const PlainGameDescriptor parallactionGames[] = {
 	{"nippon", "Nippon Safes Inc."},
@@ -233,81 +219,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Nippon Safes Inc. (C) Dynabyte";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool ParallactionMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsDeleteSave);
-}
-
-bool Parallaction::Parallaction::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher);
-}
-
-bool ParallactionMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Parallaction::PARALLACTIONGameDescription *gd = (const Parallaction::PARALLACTIONGameDescription *)desc;
-	bool res = true;
-
-	switch (gd->gameType) {
-	case Parallaction::GType_Nippon:
-		*engine = new Parallaction::Parallaction_ns(syst, gd);
-		break;
-	case Parallaction::GType_BRA:
-		*engine = new Parallaction::Parallaction_br(syst, gd);
-		break;
-	default:
-		res = false;
-		error("Parallaction engine: unknown gameType");
-	}
-
-	return res;
-}
-
-SaveStateList ParallactionMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-
-	Common::String pattern(ConfMan.getDomain(target)->getVal("gameid") + ".0##");
-	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-
-		if (slotNum >= 0 && slotNum <= 99) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				Common::String saveDesc = in->readLine();
-				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int ParallactionMetaEngine::getMaximumSaveSlot() const { return 99; }
-
-void ParallactionMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = ConfMan.getDomain(target)->getVal("gameid");
-	filename += Common::String::format(".0%02d", slot);
-
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(PARALLACTION)
-	REGISTER_PLUGIN_DYNAMIC(PARALLACTION, PLUGIN_TYPE_ENGINE, ParallactionMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(PARALLACTION, PLUGIN_TYPE_ENGINE, ParallactionMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(PARALLACTION_DETECTION, PLUGIN_TYPE_METAENGINE, ParallactionMetaEngine);
diff --git a/engines/parallaction/detection.h b/engines/parallaction/detection.h
new file mode 100644
index 0000000000..d6b7c29f71
--- /dev/null
+++ b/engines/parallaction/detection.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Parallaction {
+
+struct PARALLACTIONGameDescription {
+	ADGameDescription desc;
+
+	int gameType;
+	uint32 features;
+};
+
+} // End of namespace Parallaction
diff --git a/engines/parallaction/metaengine.cpp b/engines/parallaction/metaengine.cpp
new file mode 100644
index 0000000000..42ec7d6520
--- /dev/null
+++ b/engines/parallaction/metaengine.cpp
@@ -0,0 +1,125 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "common/config-manager.h"
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+#include "common/textconsole.h"
+
+#include "parallaction/parallaction.h"
+#include "parallaction/detection.h"
+
+namespace Parallaction {
+
+int Parallaction::getGameType() const { return _gameDescription->gameType; }
+uint32 Parallaction::getFeatures() const { return _gameDescription->features; }
+Common::Language Parallaction::getLanguage() const { return _gameDescription->desc.language; }
+Common::Platform Parallaction::getPlatform() const { return _gameDescription->desc.platform; }
+
+} // End of namespace Parallaction
+
+class ParallactionMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "parallaction";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool ParallactionMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsDeleteSave);
+}
+
+bool Parallaction::Parallaction::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher);
+}
+
+bool ParallactionMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Parallaction::PARALLACTIONGameDescription *gd = (const Parallaction::PARALLACTIONGameDescription *)desc;
+	bool res = true;
+
+	switch (gd->gameType) {
+	case Parallaction::GType_Nippon:
+		*engine = new Parallaction::Parallaction_ns(syst, gd);
+		break;
+	case Parallaction::GType_BRA:
+		*engine = new Parallaction::Parallaction_br(syst, gd);
+		break;
+	default:
+		res = false;
+		error("Parallaction engine: unknown gameType");
+	}
+
+	return res;
+}
+
+SaveStateList ParallactionMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+
+	Common::String pattern(ConfMan.getDomain(target)->getVal("gameid") + ".0##");
+	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+
+		if (slotNum >= 0 && slotNum <= 99) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				Common::String saveDesc = in->readLine();
+				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int ParallactionMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+
+void ParallactionMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = ConfMan.getDomain(target)->getVal("gameid");
+	filename += Common::String::format(".0%02d", slot);
+
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(PARALLACTION)
+	REGISTER_PLUGIN_DYNAMIC(PARALLACTION, PLUGIN_TYPE_ENGINE, ParallactionMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(PARALLACTION, PLUGIN_TYPE_ENGINE, ParallactionMetaEngineConnect);
+#endif
diff --git a/engines/parallaction/module.mk b/engines/parallaction/module.mk
index f8a4e0b9a3..3ad5b48b05 100644
--- a/engines/parallaction/module.mk
+++ b/engines/parallaction/module.mk
@@ -6,7 +6,6 @@ MODULE_OBJS := \
 	callables_br.o \
 	callables_ns.o \
 	debug.o \
-	detection.o \
 	dialogue.o \
 	disk_br.o \
 	disk_ns.o \
@@ -21,6 +20,7 @@ MODULE_OBJS := \
 	gui_ns.o \
 	input.o \
 	inventory.o \
+	metaengine.o \
 	objects.o \
 	parallaction.o \
 	parallaction_br.o \
@@ -41,3 +41,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 8f751aa359e66e5865ee8688a35122ce8391021e
    https://github.com/scummvm/scummvm/commit/8f751aa359e66e5865ee8688a35122ce8391021e
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PEGASUS: Split detection features & adapt to new plugins.

Changed paths:
  A engines/pegasus/detection.h
  A engines/pegasus/metaengine.cpp
    configure
    engines/pegasus/detection.cpp
    engines/pegasus/module.mk


diff --git a/configure b/configure
index 6345d220ff..9814a1d0b4 100755
--- a/configure
+++ b/configure
@@ -6165,7 +6165,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
-								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION")
+								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/pegasus/detection.cpp b/engines/pegasus/detection.cpp
index 186ad47637..090f7935d2 100644
--- a/engines/pegasus/detection.cpp
+++ b/engines/pegasus/detection.cpp
@@ -25,48 +25,8 @@
 #include "engines/advancedDetector.h"
 #include "common/config-manager.h"
 #include "common/file.h"
-#include "common/savefile.h"
 
-#include "pegasus/pegasus.h"
-
-namespace Pegasus {
-
-struct PegasusGameDescription {
-	ADGameDescription desc;
-};
-
-enum {
-	GF_DVD = (1 << 1)
-};
-
-bool PegasusEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher)
-		|| (f == kSupportsLoadingDuringRuntime)
-		|| (f == kSupportsSavingDuringRuntime);
-}
-
-bool PegasusEngine::isDemo() const {
-	return (_gameDescription->desc.flags & ADGF_DEMO) != 0;
-}
-
-bool PegasusEngine::isDVD() const {
-	return (_gameDescription->desc.flags & GF_DVD) != 0;
-}
-
-bool PegasusEngine::isDVDDemo() const {
-	return isDemo() && isDVD();
-}
-
-bool PegasusEngine::isOldDemo() const {
-	return isDemo() && !isDVD();
-}
-
-bool PegasusEngine::isWindows() const {
-	return _gameDescription->desc.platform == Common::kPlatformWindows;
-}
-
-} // End of namespace Pegasus
+#include "pegasus/detection.h"
 
 static const PlainGameDescriptor pegasusGames[] = {
 	{"pegasus", "The Journeyman Project: Pegasus Prime"},
@@ -147,62 +107,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "The Journeyman Project: Pegasus Prime (C) Presto Studios";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override { return 999; }
-	void removeSaveState(const char *target, int slot) const override;
-	Common::KeymapArray initKeymaps(const char *target) const override;
 };
 
-bool PegasusMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves)
-		|| (f == kSupportsLoadingDuringStartup)
-		|| (f == kSupportsDeleteSave);
-}
-
-SaveStateList PegasusMetaEngine::listSaves(const char *target) const {
-	// The original had no pattern, so the user must rename theirs
-	// Note that we ignore the target because saves are compatible between
-	// all versions
-	Common::StringArray fileNames = Pegasus::PegasusEngine::listSaveFiles();
-
-	SaveStateList saveList;
-	for (uint32 i = 0; i < fileNames.size(); i++) {
-		// Isolate the description from the file name
-		Common::String desc = fileNames[i].c_str() + 8;
-		for (int j = 0; j < 4; j++)
-			desc.deleteLastChar();
-
-		saveList.push_back(SaveStateDescriptor(i, desc));
-	}
-
-	return saveList;
-}
-
-void PegasusMetaEngine::removeSaveState(const char *target, int slot) const {
-	// See listSaves() for info on the pattern
-	Common::StringArray fileNames = Pegasus::PegasusEngine::listSaveFiles();
-	g_system->getSavefileManager()->removeSavefile(fileNames[slot].c_str());
-}
-
-Common::KeymapArray PegasusMetaEngine::initKeymaps(const char *target) const {
-	return Pegasus::PegasusEngine::initKeymaps();
-}
-
-bool PegasusMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Pegasus::PegasusGameDescription *gd = (const Pegasus::PegasusGameDescription *)desc;
-
-	if (gd)
-		*engine = new Pegasus::PegasusEngine(syst, gd);
-
-	return (gd != 0);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(PEGASUS)
-	REGISTER_PLUGIN_DYNAMIC(PEGASUS, PLUGIN_TYPE_ENGINE, PegasusMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(PEGASUS, PLUGIN_TYPE_ENGINE, PegasusMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(PEGASUS_DETECTION, PLUGIN_TYPE_METAENGINE, PegasusMetaEngine);
diff --git a/engines/pegasus/detection.h b/engines/pegasus/detection.h
new file mode 100644
index 0000000000..f5571fafbb
--- /dev/null
+++ b/engines/pegasus/detection.h
@@ -0,0 +1,33 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Pegasus {
+
+struct PegasusGameDescription {
+	ADGameDescription desc;
+};
+
+enum {
+	GF_DVD = (1 << 1)
+};
+
+} // End of namespace Pegasus
diff --git a/engines/pegasus/metaengine.cpp b/engines/pegasus/metaengine.cpp
new file mode 100644
index 0000000000..d6616ec67c
--- /dev/null
+++ b/engines/pegasus/metaengine.cpp
@@ -0,0 +1,128 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+#include "common/config-manager.h"
+#include "common/file.h"
+#include "common/savefile.h"
+
+#include "pegasus/pegasus.h"
+#include "pegasus/detection.h"
+
+namespace Pegasus {
+
+bool PegasusEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher)
+		|| (f == kSupportsLoadingDuringRuntime)
+		|| (f == kSupportsSavingDuringRuntime);
+}
+
+bool PegasusEngine::isDemo() const {
+	return (_gameDescription->desc.flags & ADGF_DEMO) != 0;
+}
+
+bool PegasusEngine::isDVD() const {
+	return (_gameDescription->desc.flags & GF_DVD) != 0;
+}
+
+bool PegasusEngine::isDVDDemo() const {
+	return isDemo() && isDVD();
+}
+
+bool PegasusEngine::isOldDemo() const {
+	return isDemo() && !isDVD();
+}
+
+bool PegasusEngine::isWindows() const {
+	return _gameDescription->desc.platform == Common::kPlatformWindows;
+}
+
+} // End of namespace Pegasus
+
+class PegasusMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "pegasus";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override { return 999; }
+	void removeSaveState(const char *target, int slot) const override;
+	Common::KeymapArray initKeymaps(const char *target) const override;
+};
+
+bool PegasusMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves)
+		|| (f == kSupportsLoadingDuringStartup)
+		|| (f == kSupportsDeleteSave);
+}
+
+SaveStateList PegasusMetaEngineConnect::listSaves(const char *target) const {
+	// The original had no pattern, so the user must rename theirs
+	// Note that we ignore the target because saves are compatible between
+	// all versions
+	Common::StringArray fileNames = Pegasus::PegasusEngine::listSaveFiles();
+
+	SaveStateList saveList;
+	for (uint32 i = 0; i < fileNames.size(); i++) {
+		// Isolate the description from the file name
+		Common::String desc = fileNames[i].c_str() + 8;
+		for (int j = 0; j < 4; j++)
+			desc.deleteLastChar();
+
+		saveList.push_back(SaveStateDescriptor(i, desc));
+	}
+
+	return saveList;
+}
+
+void PegasusMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	// See listSaves() for info on the pattern
+	Common::StringArray fileNames = Pegasus::PegasusEngine::listSaveFiles();
+	g_system->getSavefileManager()->removeSavefile(fileNames[slot].c_str());
+}
+
+Common::KeymapArray PegasusMetaEngineConnect::initKeymaps(const char *target) const {
+	return Pegasus::PegasusEngine::initKeymaps();
+}
+
+bool PegasusMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Pegasus::PegasusGameDescription *gd = (const Pegasus::PegasusGameDescription *)desc;
+
+	if (gd)
+		*engine = new Pegasus::PegasusEngine(syst, gd);
+
+	return (gd != 0);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(PEGASUS)
+	REGISTER_PLUGIN_DYNAMIC(PEGASUS, PLUGIN_TYPE_ENGINE, PegasusMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(PEGASUS, PLUGIN_TYPE_ENGINE, PegasusMetaEngineConnect);
+#endif
\ No newline at end of file
diff --git a/engines/pegasus/module.mk b/engines/pegasus/module.mk
index 6d69d6ea58..1fe1963f32 100644
--- a/engines/pegasus/module.mk
+++ b/engines/pegasus/module.mk
@@ -4,7 +4,6 @@ MODULE_OBJS = \
 	compass.o \
 	console.o \
 	cursor.o \
-	detection.o \
 	elements.o \
 	energymonitor.o \
 	fader.o \
@@ -15,6 +14,7 @@ MODULE_OBJS = \
 	interaction.o \
 	interface.o \
 	menu.o \
+	metaengine.o \
 	movie.o \
 	notification.o \
 	pegasus.o \
@@ -99,3 +99,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 556aa7ef7c4b27ce233ea4c8cb13a71e0d46ec57
    https://github.com/scummvm/scummvm/commit/556aa7ef7c4b27ce233ea4c8cb13a71e0d46ec57
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PETKA: Split detection features & adapt to new plugins.

Changed paths:
  A engines/petka/metaengine.cpp
    configure
    engines/petka/detection.cpp
    engines/petka/module.mk


diff --git a/configure b/configure
index 9814a1d0b4..c24474810c 100755
--- a/configure
+++ b/configure
@@ -6165,7 +6165,8 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
-								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS")
+								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
+								  "PETKA")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/petka/detection.cpp b/engines/petka/detection.cpp
index fc25b5dcaf..b1825a7934 100644
--- a/engines/petka/detection.cpp
+++ b/engines/petka/detection.cpp
@@ -20,13 +20,10 @@
  *
  */
 
-#include "common/system.h"
-#include "common/savefile.h"
+#include "base/plugins.h"
 
 #include "engines/advancedDetector.h"
 
-#include "petka/petka.h"
-
 static const PlainGameDescriptor petkaGames[] = {
 	{"petka_demo", "Red Comrades Demo"},
 	{"petka1", "Red Comrades 1: Save the Galaxy"},
@@ -54,77 +51,6 @@ public:
 	virtual const char *getOriginalCopyright() const override {
 		return "Red Comrades (C) S.K.I.F";
 	}
-
-	virtual bool hasFeature(MetaEngineFeature f) const override;
-	virtual int getMaximumSaveSlot() const override { return 18; }
-	virtual SaveStateList listSaves(const char *target) const override;
-	virtual void removeSaveState(const char *target, int slot) const override;
-	virtual SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool PetkaMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime);
-}
-
-SaveStateList PetkaMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::String pattern = Common::String::format("%s.s##", target);
-	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
-			Common::ScopedPtr<Common::InSaveFile> in(saveFileMan->openForLoading(*file));
-			if (in) {
-				SaveStateDescriptor desc;
-				desc.setSaveSlot(slotNum);
-				if (Petka::readSaveHeader(*in.get(), desc))
-					saveList.push_back(desc);
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void PetkaMetaEngine::removeSaveState(const char *target, int slot) const {
-	g_system->getSavefileManager()->removeSavefile(Petka::generateSaveName(slot, target));
-}
-
-SaveStateDescriptor PetkaMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(Petka::generateSaveName(slot, target)));
-
-	if (f) {
-		SaveStateDescriptor desc;
-		if (!Petka::readSaveHeader(*f.get(), desc, false))
-			return SaveStateDescriptor();
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-bool PetkaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc)
-		*engine = new Petka::PetkaEngine(syst, desc);
-
-	return desc != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(PETKA)
-	REGISTER_PLUGIN_DYNAMIC(PETKA, PLUGIN_TYPE_ENGINE, PetkaMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(PETKA, PLUGIN_TYPE_ENGINE, PetkaMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(PETKA_DETECTION, PLUGIN_TYPE_METAENGINE, PetkaMetaEngine);
diff --git a/engines/petka/metaengine.cpp b/engines/petka/metaengine.cpp
new file mode 100644
index 0000000000..c4adc64296
--- /dev/null
+++ b/engines/petka/metaengine.cpp
@@ -0,0 +1,108 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/system.h"
+#include "common/savefile.h"
+
+#include "engines/advancedDetector.h"
+
+#include "petka/petka.h"
+
+class PetkaMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "petka";
+	}
+
+    virtual bool hasFeature(MetaEngineFeature f) const override;
+	virtual int getMaximumSaveSlot() const override { return 18; }
+	virtual SaveStateList listSaves(const char *target) const override;
+	virtual void removeSaveState(const char *target, int slot) const override;
+	virtual SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool PetkaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime);
+}
+
+SaveStateList PetkaMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::String pattern = Common::String::format("%s.s##", target);
+	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
+			Common::ScopedPtr<Common::InSaveFile> in(saveFileMan->openForLoading(*file));
+			if (in) {
+				SaveStateDescriptor desc;
+				desc.setSaveSlot(slotNum);
+				if (Petka::readSaveHeader(*in.get(), desc))
+					saveList.push_back(desc);
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void PetkaMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	g_system->getSavefileManager()->removeSavefile(Petka::generateSaveName(slot, target));
+}
+
+SaveStateDescriptor PetkaMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(Petka::generateSaveName(slot, target)));
+
+	if (f) {
+		SaveStateDescriptor desc;
+		if (!Petka::readSaveHeader(*f.get(), desc, false))
+			return SaveStateDescriptor();
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+bool PetkaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc)
+		*engine = new Petka::PetkaEngine(syst, desc);
+
+	return desc != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(PETKA)
+	REGISTER_PLUGIN_DYNAMIC(PETKA, PLUGIN_TYPE_ENGINE, PetkaMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(PETKA, PLUGIN_TYPE_ENGINE, PetkaMetaEngineConnect);
+#endif
diff --git a/engines/petka/module.mk b/engines/petka/module.mk
index 29723ffa8d..7bcbb03ef3 100644
--- a/engines/petka/module.mk
+++ b/engines/petka/module.mk
@@ -2,9 +2,9 @@ MODULE := engines/petka
 
 MODULE_OBJS = \
     big_dialogue.o \
-    detection.o \
     file_mgr.o \
     flc.o \
+    metaengine.o \
     petka.o \
     saveload.o \
     q_manager.o \
@@ -35,3 +35,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 0816e46ba6ccbceace20b3d94bde868b9b593827
    https://github.com/scummvm/scummvm/commit/0816e46ba6ccbceace20b3d94bde868b9b593827
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PINK: Split detection features & adapt to new plugins.

Changed paths:
  A engines/pink/metaengine.cpp
    configure
    engines/pink/detection.cpp
    engines/pink/module.mk


diff --git a/configure b/configure
index c24474810c..eed8cb6110 100755
--- a/configure
+++ b/configure
@@ -6166,7 +6166,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
-								  "PETKA")
+								  "PETKA" "PINK")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/pink/detection.cpp b/engines/pink/detection.cpp
index 3e6a963762..c6ffafa324 100644
--- a/engines/pink/detection.cpp
+++ b/engines/pink/detection.cpp
@@ -24,16 +24,6 @@
 
 #include "engines/advancedDetector.h"
 
-#include "pink/pink.h"
-
-namespace Pink {
-
-Common::Language PinkEngine::getLanguage() const {
-	return _desc->language;
-}
-
-} // End of Namespace Pink
-
 static const PlainGameDescriptor pinkGames[] = {
 	{"peril", "The Pink Panther: Passport to Peril"},
 	{"pokus", "The Pink Panther: Hokus Pokus Pink"},
@@ -67,79 +57,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Pink Panther (C) Wanderlust Interactive";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	int getMaximumSaveSlot() const override { return 99; }
-	SaveStateList listSaves(const char *target) const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool PinkMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSimpleSavesNames);
-}
-
-SaveStateList PinkMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::String pattern = Common::String::format("%s.s##", target);
-	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
-			Common::ScopedPtr<Common::InSaveFile> in(saveFileMan->openForLoading(*file));
-			if (in) {
-				SaveStateDescriptor desc;
-				desc.setSaveSlot(slotNum);
-				if (Pink::readSaveHeader(*in.get(), desc))
-					saveList.push_back(desc);
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void PinkMetaEngine::removeSaveState(const char *target, int slot) const {
-	g_system->getSavefileManager()->removeSavefile(Pink::generateSaveName(slot, target));
-}
-
-SaveStateDescriptor PinkMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(Pink::generateSaveName(slot, target)));
-
-	if (f) {
-		SaveStateDescriptor desc;
-		if (!Pink::readSaveHeader(*f.get(), desc, false))
-			return SaveStateDescriptor();
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-bool PinkMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc)
-		*engine = new Pink::PinkEngine(syst, desc);
-
-	return desc != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(PINK)
-REGISTER_PLUGIN_DYNAMIC(PINK, PLUGIN_TYPE_ENGINE, PinkMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(PINK, PLUGIN_TYPE_ENGINE, PinkMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(PINK_DETECTION, PLUGIN_TYPE_METAENGINE, PinkMetaEngine);
diff --git a/engines/pink/metaengine.cpp b/engines/pink/metaengine.cpp
new file mode 100644
index 0000000000..3891e7049d
--- /dev/null
+++ b/engines/pink/metaengine.cpp
@@ -0,0 +1,120 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/system.h"
+
+#include "engines/advancedDetector.h"
+
+#include "pink/pink.h"
+
+namespace Pink {
+
+Common::Language PinkEngine::getLanguage() const {
+	return _desc->language;
+}
+
+} // End of Namespace Pink
+
+class PinkMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "pink";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+	int getMaximumSaveSlot() const override { return 99; }
+	SaveStateList listSaves(const char *target) const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool PinkMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSimpleSavesNames);
+}
+
+SaveStateList PinkMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::String pattern = Common::String::format("%s.s##", target);
+	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
+			Common::ScopedPtr<Common::InSaveFile> in(saveFileMan->openForLoading(*file));
+			if (in) {
+				SaveStateDescriptor desc;
+				desc.setSaveSlot(slotNum);
+				if (Pink::readSaveHeader(*in.get(), desc))
+					saveList.push_back(desc);
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void PinkMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	g_system->getSavefileManager()->removeSavefile(Pink::generateSaveName(slot, target));
+}
+
+SaveStateDescriptor PinkMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(Pink::generateSaveName(slot, target)));
+
+	if (f) {
+		SaveStateDescriptor desc;
+		if (!Pink::readSaveHeader(*f.get(), desc, false))
+			return SaveStateDescriptor();
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+bool PinkMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc)
+		*engine = new Pink::PinkEngine(syst, desc);
+
+	return desc != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(PINK)
+	REGISTER_PLUGIN_DYNAMIC(PINK, PLUGIN_TYPE_ENGINE, PinkMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(PINK, PLUGIN_TYPE_ENGINE, PinkMetaEngineConnect);
+#endif
+
diff --git a/engines/pink/module.mk b/engines/pink/module.mk
index f6941d30e9..bc85597e2c 100644
--- a/engines/pink/module.mk
+++ b/engines/pink/module.mk
@@ -6,10 +6,10 @@ MODULE_OBJS = \
 	cel_decoder.o \
 	console.o \
 	cursor_mgr.o \
-	detection.o \
 	director.o \
 	file.o \
 	gui.o \
+	metaengine.o \
 	pda_mgr.o \
 	pink.o \
 	resource_mgr.o \
@@ -57,3 +57,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 4458a2e2439c270947796f6a6525e2dd0e0db5db
    https://github.com/scummvm/scummvm/commit/4458a2e2439c270947796f6a6525e2dd0e0db5db
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PRINCE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/prince/detection.h
  A engines/prince/detection_enums.h
  A engines/prince/metaengine.cpp
    configure
    engines/prince/detection.cpp
    engines/prince/module.mk
    engines/prince/prince.h


diff --git a/configure b/configure
index eed8cb6110..b17ab22fff 100755
--- a/configure
+++ b/configure
@@ -6166,7 +6166,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
-								  "PETKA" "PINK")
+								  "PETKA" "PINK" "PRINCE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/prince/detection.cpp b/engines/prince/detection.cpp
index 57732fcb48..f0f9b5984c 100644
--- a/engines/prince/detection.cpp
+++ b/engines/prince/detection.cpp
@@ -20,33 +20,10 @@
  *
  */
 
-#include "prince/prince.h"
 #include "engines/advancedDetector.h"
 
-namespace Prince {
-
-struct PrinceGameDescription {
-	ADGameDescription desc;
-	PrinceGameType gameType;
-};
-
-int PrinceEngine::getGameType() const {
-	return _gameDescription->gameType;
-}
-
-const char *PrinceEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-uint32 PrinceEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language PrinceEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-} // End of namespace Prince
+#include "prince/detection_enums.h"
+#include "prince/detection.h"
 
 static const PlainGameDescriptor princeGames[] = {
 	{"prince", "The Prince and the Coward"},
@@ -163,126 +140,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "The Prince and the Coward (C) 1996-97 Metropolis";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	int getMaximumSaveSlot() const override { return 99; }
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool PrinceMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Prince::PrinceEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime) ||
-		(f == kSupportsReturnToLauncher);
-}
-
-SaveStateList PrinceMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); filename++) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(filename->c_str() + filename->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 99) {
-
-			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
-			if (file) {
-				Prince::SavegameHeader header;
-
-				// Check to see if it's a ScummVM savegame or not
-				char buffer[kSavegameStrSize + 1];
-				file->read(buffer, kSavegameStrSize + 1);
-
-				if (!strncmp(buffer, kSavegameStr, kSavegameStrSize + 1)) {
-					// Valid savegame
-					if (Prince::PrinceEngine::readSavegameHeader(file, header)) {
-						saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
-					}
-				} else {
-					// Must be an original format savegame
-					saveList.push_back(SaveStateDescriptor(slotNum, "Unknown"));
-				}
-
-				delete file;
-			}
-		}
-	}
-
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor PrinceMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (f) {
-		Prince::SavegameHeader header;
-
-		// Check to see if it's a ScummVM savegame or not
-		char buffer[kSavegameStrSize + 1];
-		f->read(buffer, kSavegameStrSize + 1);
-
-		bool hasHeader = !strncmp(buffer, kSavegameStr, kSavegameStrSize + 1) &&
-			Prince::PrinceEngine::readSavegameHeader(f, header, false);
-		delete f;
-
-		if (!hasHeader) {
-			// Original savegame perhaps?
-			SaveStateDescriptor desc(slot, "Unknown");
-			return desc;
-		} else {
-			// Create the return descriptor
-			SaveStateDescriptor desc(slot, header.saveName);
-			desc.setThumbnail(header.thumbnail);
-			desc.setSaveDate(header.saveYear, header.saveMonth, header.saveDay);
-			desc.setSaveTime(header.saveHour, header.saveMinutes);
-			desc.setPlayTime(header.playTime * 1000);
-
-			return desc;
-		}
-	}
-
-	return SaveStateDescriptor();
-}
-
-void PrinceMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-bool PrinceMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	using namespace Prince;
-	const PrinceGameDescription *gd = (const PrinceGameDescription *)desc;
-	if (gd) {
-		*engine = new PrinceEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(PRINCE)
-REGISTER_PLUGIN_DYNAMIC(PRINCE, PLUGIN_TYPE_ENGINE, PrinceMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(PRINCE, PLUGIN_TYPE_ENGINE, PrinceMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(PRINCE_DETECTION, PLUGIN_TYPE_METAENGINE, PrinceMetaEngine);
diff --git a/engines/prince/detection.h b/engines/prince/detection.h
new file mode 100644
index 0000000000..33d076d5aa
--- /dev/null
+++ b/engines/prince/detection.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Prince {
+
+struct PrinceGameDescription {
+	ADGameDescription desc;
+	PrinceGameType gameType;
+};
+
+} // End of namespace Prince
diff --git a/engines/prince/detection_enums.h b/engines/prince/detection_enums.h
new file mode 100644
index 0000000000..5596371901
--- /dev/null
+++ b/engines/prince/detection_enums.h
@@ -0,0 +1,37 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Prince {
+
+enum PrinceGameType {
+	kPrinceDataUNK,
+	kPrinceDataDE,
+	kPrinceDataPL
+};
+
+enum {
+	GF_TRANSLATED = 1 << 0,
+	GF_EXTRACTED  = 1 << 1,
+	GF_NOVOICES   = 1 << 2
+};
+
+} // End of namespace Prince
diff --git a/engines/prince/metaengine.cpp b/engines/prince/metaengine.cpp
new file mode 100644
index 0000000000..23ea7e7667
--- /dev/null
+++ b/engines/prince/metaengine.cpp
@@ -0,0 +1,175 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/advancedDetector.h"
+#include "prince/prince.h"
+#include "prince/detection.h"
+
+namespace Prince {
+
+int PrinceEngine::getGameType() const {
+	return _gameDescription->gameType;
+}
+
+const char *PrinceEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+uint32 PrinceEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language PrinceEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+} // End of namespace Prince
+
+class PrinceMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "prince";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	int getMaximumSaveSlot() const override { return 99; }
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool PrinceMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Prince::PrinceEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime) ||
+		(f == kSupportsReturnToLauncher);
+}
+
+SaveStateList PrinceMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); filename++) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(filename->c_str() + filename->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 99) {
+
+			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
+			if (file) {
+				Prince::SavegameHeader header;
+
+				// Check to see if it's a ScummVM savegame or not
+				char buffer[kSavegameStrSize + 1];
+				file->read(buffer, kSavegameStrSize + 1);
+
+				if (!strncmp(buffer, kSavegameStr, kSavegameStrSize + 1)) {
+					// Valid savegame
+					if (Prince::PrinceEngine::readSavegameHeader(file, header)) {
+						saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
+					}
+				} else {
+					// Must be an original format savegame
+					saveList.push_back(SaveStateDescriptor(slotNum, "Unknown"));
+				}
+
+				delete file;
+			}
+		}
+	}
+
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor PrinceMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (f) {
+		Prince::SavegameHeader header;
+
+		// Check to see if it's a ScummVM savegame or not
+		char buffer[kSavegameStrSize + 1];
+		f->read(buffer, kSavegameStrSize + 1);
+
+		bool hasHeader = !strncmp(buffer, kSavegameStr, kSavegameStrSize + 1) &&
+			Prince::PrinceEngine::readSavegameHeader(f, header, false);
+		delete f;
+
+		if (!hasHeader) {
+			// Original savegame perhaps?
+			SaveStateDescriptor desc(slot, "Unknown");
+			return desc;
+		} else {
+			// Create the return descriptor
+			SaveStateDescriptor desc(slot, header.saveName);
+			desc.setThumbnail(header.thumbnail);
+			desc.setSaveDate(header.saveYear, header.saveMonth, header.saveDay);
+			desc.setSaveTime(header.saveHour, header.saveMinutes);
+			desc.setPlayTime(header.playTime * 1000);
+
+			return desc;
+		}
+	}
+
+	return SaveStateDescriptor();
+}
+
+void PrinceMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+bool PrinceMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	using namespace Prince;
+	const PrinceGameDescription *gd = (const PrinceGameDescription *)desc;
+	if (gd) {
+		*engine = new PrinceEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(PRINCE)
+	REGISTER_PLUGIN_DYNAMIC(PRINCE, PLUGIN_TYPE_ENGINE, PrinceMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(PRINCE, PLUGIN_TYPE_ENGINE, PrinceMetaEngineConnect);
+#endif
diff --git a/engines/prince/module.mk b/engines/prince/module.mk
index 0a24c0c243..0bca0ab5b0 100644
--- a/engines/prince/module.mk
+++ b/engines/prince/module.mk
@@ -6,13 +6,13 @@ MODULE_OBJS = \
 	cursor.o \
 	debugger.o \
 	decompress.o \
-	detection.o \
 	draw.o \
 	flags.o \
 	font.o \
 	graphics.o \
 	hero.o \
 	inventory.o \
+	metaengine.o \
 	mhwanh.o \
 	music.o \
 	mob.o \
@@ -34,3 +34,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/prince/prince.h b/engines/prince/prince.h
index 173efdc0fe..bbcb97edaa 100644
--- a/engines/prince/prince.h
+++ b/engines/prince/prince.h
@@ -48,15 +48,10 @@
 #include "prince/mob.h"
 #include "prince/object.h"
 #include "prince/pscr.h"
+#include "prince/detection_enums.h"
 
 namespace Prince {
 
-enum PrinceGameType {
-	kPrinceDataUNK,
-	kPrinceDataDE,
-	kPrinceDataPL
-};
-
 struct SavegameHeader;
 
 class PrinceEngine;
@@ -76,12 +71,6 @@ class Animation;
 class Room;
 class Pscr;
 
-enum {
-	GF_TRANSLATED = 1 << 0,
-	GF_EXTRACTED  = 1 << 1,
-	GF_NOVOICES   = 1 << 2
-};
-
 struct SavegameHeader {
 	uint8 version;
 	Common::String saveName;


Commit: e29f02597c63723a36351c87165e3502feeee31f
    https://github.com/scummvm/scummvm/commit/e29f02597c63723a36351c87165e3502feeee31f
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SHERLOCK: Split detection features & adapt to new plugins.

Changed paths:
  A engines/sherlock/detection.h
  A engines/sherlock/detection_enums.h
  A engines/sherlock/metaengine.cpp
    configure
    engines/sherlock/detection.cpp
    engines/sherlock/module.mk
    engines/sherlock/sherlock.h


diff --git a/configure b/configure
index b17ab22fff..e3d1908373 100755
--- a/configure
+++ b/configure
@@ -6166,7 +6166,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
-								  "PETKA" "PINK" "PRINCE")
+								  "PETKA" "PINK" "PRINCE" "SHERLOCK")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/sherlock/detection.cpp b/engines/sherlock/detection.cpp
index 5992f41375..2454b54899 100644
--- a/engines/sherlock/detection.cpp
+++ b/engines/sherlock/detection.cpp
@@ -20,35 +20,11 @@
  *
  */
 
-#include "sherlock/sherlock.h"
-#include "sherlock/saveload.h"
-#include "sherlock/scalpel/scalpel.h"
-#include "sherlock/tattoo/tattoo.h"
-#include "common/system.h"
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-namespace Sherlock {
-
-struct SherlockGameDescription {
-	ADGameDescription desc;
-
-	GameType gameID;
-};
-
-GameType SherlockEngine::getGameID() const {
-	return _gameDescription->gameID;
-}
-
-Common::Platform SherlockEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-Common::Language SherlockEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-} // End of namespace Sherlock
+#include "sherlock/detection_enums.h"
+#include "sherlock/detection.h"
 
 static const PlainGameDescriptor sherlockGames[] = {
 	{ "scalpel", "The Case of the Serrated Scalpel" },
@@ -162,120 +138,7 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Sherlock (C) 1992-1996 Mythos Software, (C) 1992-1996 Electronic Arts";
 	}
-
-	/**
-	 * Creates an instance of the game engine
-	 */
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-
-	/**
-	 * Returns a list of features the game's MetaEngine support
-	 */
-	bool hasFeature(MetaEngineFeature f) const override;
-
-	/**
-	 * Return a list of savegames
-	 */
-	SaveStateList listSaves(const char *target) const override;
-
-	/**
-	 * Returns the maximum number of allowed save slots
-	 */
-	int getMaximumSaveSlot() const override;
-
-	/**
-	 * Deletes a savegame in the specified slot
-	 */
-	void removeSaveState(const char *target, int slot) const override;
-
-	/**
-	 * Given a specified savegame slot, returns extended information for the save
-	 */
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool SherlockMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Sherlock::SherlockGameDescription *gd = (const Sherlock::SherlockGameDescription *)desc;
-	if (gd) {
-		switch (gd->gameID) {
-		case Sherlock::GType_SerratedScalpel:
-			*engine = new Sherlock::Scalpel::ScalpelEngine(syst, gd);
-			break;
-		case Sherlock::GType_RoseTattoo:
-			*engine = new Sherlock::Tattoo::TattooEngine(syst, gd);
-			break;
-		default:
-			error("Unknown game");
-			break;
-		}
-	}
-	return gd != 0;
-}
-
-bool SherlockMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Sherlock::SherlockEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool Sherlock::SherlockEngine::isDemo() const {
-	return _gameDescription->desc.flags & ADGF_DEMO;
-}
-
-SaveStateList SherlockMetaEngine::listSaves(const char *target) const {
-	return Sherlock::SaveManager::getSavegameList(target);
-}
 
-int SherlockMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVEGAME_SLOTS;
-}
-
-void SherlockMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Sherlock::SaveManager(nullptr, target).generateSaveName(slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor SherlockMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Sherlock::SaveManager(nullptr, target).generateSaveName(slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
-
-	if (f) {
-		Sherlock::SherlockSavegameHeader header;
-		if (!Sherlock::SaveManager::readSavegameHeader(f, header, false)) {
-			delete f;
-			return SaveStateDescriptor();
-		}
-		delete f;
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header._saveName);
-		desc.setThumbnail(header._thumbnail);
-		desc.setSaveDate(header._year, header._month, header._day);
-		desc.setSaveTime(header._hour, header._minute);
-		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-
-#if PLUGIN_ENABLED_DYNAMIC(SHERLOCK)
-	REGISTER_PLUGIN_DYNAMIC(SHERLOCK, PLUGIN_TYPE_ENGINE, SherlockMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(SHERLOCK, PLUGIN_TYPE_ENGINE, SherlockMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(SHERLOCK_DETECTION, PLUGIN_TYPE_METAENGINE, SherlockMetaEngine);
diff --git a/engines/sherlock/detection.h b/engines/sherlock/detection.h
new file mode 100644
index 0000000000..d9ccc800c6
--- /dev/null
+++ b/engines/sherlock/detection.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Sherlock {
+
+struct SherlockGameDescription {
+	ADGameDescription desc;
+
+	GameType gameID;
+};
+
+} // End of namespace Sherlock
diff --git a/engines/sherlock/detection_enums.h b/engines/sherlock/detection_enums.h
new file mode 100644
index 0000000000..bd33256d5e
--- /dev/null
+++ b/engines/sherlock/detection_enums.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Sherlock {
+
+enum GameType {
+	GType_SerratedScalpel = 0,
+	GType_RoseTattoo = 1
+};
+
+} // End of namespace Sherlock
diff --git a/engines/sherlock/metaengine.cpp b/engines/sherlock/metaengine.cpp
new file mode 100644
index 0000000000..e5fa0f1ea6
--- /dev/null
+++ b/engines/sherlock/metaengine.cpp
@@ -0,0 +1,171 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "sherlock/sherlock.h"
+#include "sherlock/saveload.h"
+#include "sherlock/scalpel/scalpel.h"
+#include "sherlock/tattoo/tattoo.h"
+
+#include "common/system.h"
+#include "common/translation.h"
+#include "engines/advancedDetector.h"
+
+#include "sherlock/detection.h"
+
+namespace Sherlock {
+
+GameType SherlockEngine::getGameID() const {
+	return _gameDescription->gameID;
+}
+
+Common::Platform SherlockEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+Common::Language SherlockEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+} // End of namespace Sherlock
+
+
+class SherlockMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "sherlock";
+	}
+
+    /**
+	 * Creates an instance of the game engine
+	 */
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	/**
+	 * Returns a list of features the game's MetaEngine support
+	 */
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	/**
+	 * Return a list of savegames
+	 */
+	SaveStateList listSaves(const char *target) const override;
+
+	/**
+	 * Returns the maximum number of allowed save slots
+	 */
+	int getMaximumSaveSlot() const override;
+
+	/**
+	 * Deletes a savegame in the specified slot
+	 */
+	void removeSaveState(const char *target, int slot) const override;
+
+	/**
+	 * Given a specified savegame slot, returns extended information for the save
+	 */
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool SherlockMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Sherlock::SherlockGameDescription *gd = (const Sherlock::SherlockGameDescription *)desc;
+	if (gd) {
+		switch (gd->gameID) {
+		case Sherlock::GType_SerratedScalpel:
+			*engine = new Sherlock::Scalpel::ScalpelEngine(syst, gd);
+			break;
+		case Sherlock::GType_RoseTattoo:
+			*engine = new Sherlock::Tattoo::TattooEngine(syst, gd);
+			break;
+		default:
+			error("Unknown game");
+			break;
+		}
+	}
+	return gd != 0;
+}
+
+bool SherlockMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Sherlock::SherlockEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool Sherlock::SherlockEngine::isDemo() const {
+	return _gameDescription->desc.flags & ADGF_DEMO;
+}
+
+SaveStateList SherlockMetaEngineConnect::listSaves(const char *target) const {
+	return Sherlock::SaveManager::getSavegameList(target);
+}
+
+int SherlockMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVEGAME_SLOTS;
+}
+
+void SherlockMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Sherlock::SaveManager(nullptr, target).generateSaveName(slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor SherlockMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Sherlock::SaveManager(nullptr, target).generateSaveName(slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
+
+	if (f) {
+		Sherlock::SherlockSavegameHeader header;
+		if (!Sherlock::SaveManager::readSavegameHeader(f, header, false)) {
+			delete f;
+			return SaveStateDescriptor();
+		}
+		delete f;
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header._saveName);
+		desc.setThumbnail(header._thumbnail);
+		desc.setSaveDate(header._year, header._month, header._day);
+		desc.setSaveTime(header._hour, header._minute);
+		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(SHERLOCK)
+	REGISTER_PLUGIN_DYNAMIC(SHERLOCK, PLUGIN_TYPE_ENGINE, SherlockMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(SHERLOCK, PLUGIN_TYPE_ENGINE, SherlockMetaEngineConnect);
+#endif
diff --git a/engines/sherlock/module.mk b/engines/sherlock/module.mk
index 0d17d0b249..265053a080 100644
--- a/engines/sherlock/module.mk
+++ b/engines/sherlock/module.mk
@@ -49,7 +49,6 @@ MODULE_OBJS = \
 	tattoo/widget_verbs.o \
 	animation.o \
 	debugger.o \
-	detection.o \
 	events.o \
 	fixed_text.o \
 	fonts.o \
@@ -57,6 +56,7 @@ MODULE_OBJS = \
 	inventory.o \
 	journal.o \
 	map.o \
+	metaengine.o \
 	music.o \
 	objects.o \
 	people.o \
@@ -77,3 +77,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sherlock/sherlock.h b/engines/sherlock/sherlock.h
index cbd82c8d27..06a28af8bb 100644
--- a/engines/sherlock/sherlock.h
+++ b/engines/sherlock/sherlock.h
@@ -31,7 +31,9 @@
 #include "common/random.h"
 #include "common/savefile.h"
 #include "common/util.h"
+
 #include "engines/engine.h"
+
 #include "sherlock/animation.h"
 #include "sherlock/debugger.h"
 #include "sherlock/events.h"
@@ -48,6 +50,7 @@
 #include "sherlock/sound.h"
 #include "sherlock/talk.h"
 #include "sherlock/user_interface.h"
+#include "sherlock/detection_enums.h"
 
 namespace Sherlock {
 
@@ -58,11 +61,6 @@ enum {
 	kDebugLevelMusic       = 4 << 0
 };
 
-enum GameType {
-	GType_SerratedScalpel = 0,
-	GType_RoseTattoo = 1
-};
-
 #define SHERLOCK_SCREEN_WIDTH _vm->_screen->width()
 #define SHERLOCK_SCREEN_HEIGHT _vm->_screen->height()
 #define SHERLOCK_SCENE_WIDTH _vm->_screen->_backBuffer1.width()


Commit: af47301ccaa80f3610307cc925e1f9571192bbd9
    https://github.com/scummvm/scummvm/commit/af47301ccaa80f3610307cc925e1f9571192bbd9
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SLUDGE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/sludge/detection.h
  A engines/sludge/metaengine.cpp
    configure
    engines/sludge/detection.cpp
    engines/sludge/module.mk


diff --git a/configure b/configure
index e3d1908373..7d74813287 100755
--- a/configure
+++ b/configure
@@ -6166,7 +6166,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
-								  "PETKA" "PINK" "PRINCE" "SHERLOCK")
+								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/sludge/detection.cpp b/engines/sludge/detection.cpp
index 0061f50d97..8ab37da31c 100644
--- a/engines/sludge/detection.cpp
+++ b/engines/sludge/detection.cpp
@@ -21,27 +21,11 @@
  */
 #include "common/debug.h"
 #include "common/stream.h"
+#include "common/file.h"
 
 #include "engines/advancedDetector.h"
 
-#include "sludge/sludge.h"
-
-namespace Sludge {
-
-struct SludgeGameDescription {
-	ADGameDescription desc;
-	uint languageID;
-};
-
-uint SludgeEngine::getLanguageID() const { return _gameDescription->languageID; }
-const char *SludgeEngine::getGameId() const { return _gameDescription->desc.gameId;}
-uint32 SludgeEngine::getFeatures() const { return _gameDescription->desc.flags; }
-Common::Language SludgeEngine::getLanguage() const { return _gameDescription->desc.language; }
-const char *SludgeEngine::getGameFile() const {
-	return _gameDescription->desc.filesDescriptions[0].fileName;
-}
-
-} // End of namespace Sludge
+#include "sludge/detection.h"
 
 static const PlainGameDescriptor sludgeGames[] = {
 	{ "sludge",			"Sludge Game" },
@@ -99,14 +83,6 @@ public:
 		return "Sludge (C) 2000-2014 Hungry Software and contributors";
 	}
 
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
-		const Sludge::SludgeGameDescription *gd = (const Sludge::SludgeGameDescription *)desc;
-			if (gd) {
-				*engine = new Sludge::SludgeEngine(syst, gd);
-			}
-			return gd != 0;
-	}
-
 	// for fall back detection
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
 };
@@ -170,8 +146,4 @@ ADDetectedGame SludgeMetaEngine::fallbackDetect(const FileMap &allFiles, const C
 	return ADDetectedGame();
 }
 
-#if PLUGIN_ENABLED_DYNAMIC(SLUDGE)
-	REGISTER_PLUGIN_DYNAMIC(SLUDGE, PLUGIN_TYPE_ENGINE, SludgeMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(SLUDGE, PLUGIN_TYPE_ENGINE, SludgeMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(SLUDGE_DETECTION, PLUGIN_TYPE_METAENGINE, SludgeMetaEngine);
diff --git a/engines/sludge/detection.h b/engines/sludge/detection.h
new file mode 100644
index 0000000000..be57defc5d
--- /dev/null
+++ b/engines/sludge/detection.h
@@ -0,0 +1,30 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Sludge {
+
+struct SludgeGameDescription {
+	ADGameDescription desc;
+	uint languageID;
+};
+
+} // End of namespace Sludge
diff --git a/engines/sludge/metaengine.cpp b/engines/sludge/metaengine.cpp
new file mode 100644
index 0000000000..96385daea5
--- /dev/null
+++ b/engines/sludge/metaengine.cpp
@@ -0,0 +1,62 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/debug.h"
+#include "common/stream.h"
+
+#include "engines/advancedDetector.h"
+
+#include "sludge/sludge.h"
+#include "sludge/detection.h"
+
+namespace Sludge {
+
+uint SludgeEngine::getLanguageID() const { return _gameDescription->languageID; }
+const char *SludgeEngine::getGameId() const { return _gameDescription->desc.gameId;}
+uint32 SludgeEngine::getFeatures() const { return _gameDescription->desc.flags; }
+Common::Language SludgeEngine::getLanguage() const { return _gameDescription->desc.language; }
+const char *SludgeEngine::getGameFile() const {
+	return _gameDescription->desc.filesDescriptions[0].fileName;
+}
+
+} // End of namespace Sludge
+
+class SludgeMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "sludge";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
+		const Sludge::SludgeGameDescription *gd = (const Sludge::SludgeGameDescription *)desc;
+			if (gd) {
+				*engine = new Sludge::SludgeEngine(syst, gd);
+			}
+			return gd != 0;
+	}
+};
+
+#if PLUGIN_ENABLED_DYNAMIC(SLUDGE)
+	REGISTER_PLUGIN_DYNAMIC(SLUDGE, PLUGIN_TYPE_ENGINE, SludgeMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(SLUDGE, PLUGIN_TYPE_ENGINE, SludgeMetaEngineConnect);
+#endif
diff --git a/engines/sludge/module.mk b/engines/sludge/module.mk
index d904e6c4c3..19435b559d 100644
--- a/engines/sludge/module.mk
+++ b/engines/sludge/module.mk
@@ -6,7 +6,6 @@ MODULE_OBJS := \
 	builtin.o \
 	console.o \
 	cursors.o \
-	detection.o \
 	event.o \
 	fileset.o \
 	floor.o \
@@ -19,6 +18,7 @@ MODULE_OBJS := \
 	language.o \
 	loadsave.o \
 	main_loop.o \
+	metaengine.o \
 	moreio.o \
 	movie.o \
 	newfatal.o \
@@ -49,4 +49,7 @@ PLUGIN := 1
 endif
  
 # Include common rules 
-include $(srcdir)/rules.mk
\ No newline at end of file
+include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 65f13a0b26a7c3abc66c83abec21fc5ce8dbbde0
    https://github.com/scummvm/scummvm/commit/65f13a0b26a7c3abc66c83abec21fc5ce8dbbde0
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
STARTREK: Split detection features & adapt to new plugins.

Changed paths:
  A engines/startrek/detection.h
  A engines/startrek/detection_enums.h
  A engines/startrek/metaengine.cpp
    configure
    engines/startrek/detection.cpp
    engines/startrek/module.mk
    engines/startrek/startrek.h


diff --git a/configure b/configure
index 7d74813287..eead51b9ba 100755
--- a/configure
+++ b/configure
@@ -6166,7 +6166,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
-								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE")
+								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/startrek/detection.cpp b/engines/startrek/detection.cpp
index 04b5a6903e..26480182a3 100644
--- a/engines/startrek/detection.cpp
+++ b/engines/startrek/detection.cpp
@@ -24,40 +24,11 @@
 
 #include "engines/advancedDetector.h"
 
-#include "graphics/thumbnail.h"
-
 #include "common/config-manager.h"
 #include "common/file.h"
-#include "common/savefile.h"
-
-#include "startrek/startrek.h"
-
-namespace StarTrek {
-
-struct StarTrekGameDescription {
-	ADGameDescription desc;
-
-	uint8 gameType;
-	uint32 features;
-};
-
-uint32 StarTrekEngine::getFeatures() const {
-	return _gameDescription->features;
-}
-
-Common::Platform StarTrekEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
 
-uint8 StarTrekEngine::getGameType() const {
-	return _gameDescription->gameType;
-}
-
-Common::Language StarTrekEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-} // End of Namespace StarTrek
+#include "startrek/detection.h"
+#include "startrek/detection_enums.h"
 
 static const PlainGameDescriptor starTrekGames[] = {
 	{"st25", "Star Trek: 25th Anniversary"},
@@ -333,150 +304,8 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Star Trek: 25th Anniversary, Star Trek: Judgment Rites (C) Interplay";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool StarTrekMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-	    (f == kSupportsLoadingDuringStartup) ||
-	    (f == kSupportsDeleteSave) ||
-	    (f == kSavesSupportMetaInfo) ||
-	    (f == kSavesSupportThumbnail) ||
-	    (f == kSavesSupportCreationDate) ||
-	    (f == kSavesSupportPlayTime) ||
-	    (f == kSimpleSavesNames);
-}
-
-bool StarTrekMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const StarTrek::StarTrekGameDescription *gd = (const StarTrek::StarTrekGameDescription *)desc;
-
-	*engine = new StarTrek::StarTrekEngine(syst, gd);
-
-	return (gd != 0);
-}
-
-SaveStateList StarTrekMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNr = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNr >= 0 && slotNr <= getMaximumSaveSlot()) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				StarTrek::SavegameMetadata meta;
-				StarTrek::saveOrLoadMetadata(in, nullptr, &meta);
-				delete in;
-
-				uint16 descriptionPos = 0;
-
-				// Security-check, if saveDescription has a terminating NUL
-				while (meta.description[descriptionPos]) {
-					descriptionPos++;
-					if (descriptionPos >= sizeof(meta.description))
-						break;
-				}
-				if (descriptionPos >= sizeof(meta.description)) {
-					strcpy(meta.description, "[broken saved game]");
-				}
-
-				saveList.push_back(SaveStateDescriptor(slotNr, meta.description));
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-
-int StarTrekMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-void StarTrekMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-SaveStateDescriptor StarTrekMetaEngine::querySaveMetaInfos(const char *target, int slotNr) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slotNr);
-
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (in) {
-		StarTrek::SavegameMetadata meta;
-		StarTrek::saveOrLoadMetadata(in, nullptr, &meta);
-		delete in;
-
-		uint16 descriptionPos = 0;
-
-		while (meta.description[descriptionPos]) {
-			descriptionPos++;
-			if (descriptionPos >= sizeof(meta.description))
-				break;
-		}
-		if (descriptionPos >= sizeof(meta.description)) {
-			// broken meta.description, ignore it
-			SaveStateDescriptor descriptor(slotNr, "[broken saved game]");
-			return descriptor;
-		}
-
-		SaveStateDescriptor descriptor(slotNr, meta.description);
-
-		// Do not allow save slot 0 (used for auto-saving) to be deleted or
-		// overwritten.
-		if (slotNr == 0) {
-			descriptor.setWriteProtectedFlag(true);
-			descriptor.setDeletableFlag(false);
-		} else {
-			descriptor.setWriteProtectedFlag(false);
-			descriptor.setDeletableFlag(true);
-		}
-
-		if (meta.thumbnail == nullptr) {
-			return SaveStateDescriptor();
-		}
-
-		descriptor.setThumbnail(meta.thumbnail);
-		descriptor.setPlayTime(meta.playTime);
-		descriptor.setSaveDate(meta.getYear(), meta.getMonth(), meta.getDay());
-		descriptor.setSaveTime(meta.getHour(), meta.getMinute());
-
-		return descriptor;
-
-	} else {
-		SaveStateDescriptor emptySave;
-		// Do not allow save slot 0 (used for auto-saving) to be overwritten.
-		if (slotNr == 0) {
-			emptySave.setWriteProtectedFlag(true);
-		} else {
-			emptySave.setWriteProtectedFlag(false);
-		}
-		return emptySave;
-	}
-}
-
 
 
-#if PLUGIN_ENABLED_DYNAMIC(STARTREK)
-REGISTER_PLUGIN_DYNAMIC(STARTREK, PLUGIN_TYPE_ENGINE, StarTrekMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(STARTREK, PLUGIN_TYPE_ENGINE, StarTrekMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(STARTREK_DETECTION, PLUGIN_TYPE_METAENGINE, StarTrekMetaEngine);
diff --git a/engines/startrek/detection.h b/engines/startrek/detection.h
new file mode 100644
index 0000000000..d7db1a09b7
--- /dev/null
+++ b/engines/startrek/detection.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace StarTrek {
+
+struct StarTrekGameDescription {
+	ADGameDescription desc;
+
+	uint8 gameType;
+	uint32 features;
+};
+
+} // End of Namespace StarTrek
\ No newline at end of file
diff --git a/engines/startrek/detection_enums.h b/engines/startrek/detection_enums.h
new file mode 100644
index 0000000000..f58701a694
--- /dev/null
+++ b/engines/startrek/detection_enums.h
@@ -0,0 +1,35 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace StarTrek {
+
+enum StarTrekGameType {
+	GType_ST25 = 1,
+	GType_STJR = 2
+};
+
+enum StarTrekGameFeatures {
+	GF_DEMO  = (1 << 0),
+	GF_CDROM = (1 << 1)
+};
+
+} // End of namespace StarTrek
diff --git a/engines/startrek/metaengine.cpp b/engines/startrek/metaengine.cpp
new file mode 100644
index 0000000000..f7c5007a62
--- /dev/null
+++ b/engines/startrek/metaengine.cpp
@@ -0,0 +1,206 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+
+#include "graphics/thumbnail.h"
+
+#include "common/config-manager.h"
+#include "common/file.h"
+#include "common/savefile.h"
+
+#include "startrek/startrek.h"
+
+#include "startrek/detection.h"
+
+namespace StarTrek {
+
+uint32 StarTrekEngine::getFeatures() const {
+	return _gameDescription->features;
+}
+
+Common::Platform StarTrekEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+uint8 StarTrekEngine::getGameType() const {
+	return _gameDescription->gameType;
+}
+
+Common::Language StarTrekEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+} // End of Namespace StarTrek
+
+class StarTrekMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "startrek";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool StarTrekMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+	    (f == kSupportsLoadingDuringStartup) ||
+	    (f == kSupportsDeleteSave) ||
+	    (f == kSavesSupportMetaInfo) ||
+	    (f == kSavesSupportThumbnail) ||
+	    (f == kSavesSupportCreationDate) ||
+	    (f == kSavesSupportPlayTime) ||
+	    (f == kSimpleSavesNames);
+}
+
+bool StarTrekMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const StarTrek::StarTrekGameDescription *gd = (const StarTrek::StarTrekGameDescription *)desc;
+
+	*engine = new StarTrek::StarTrekEngine(syst, gd);
+
+	return (gd != 0);
+}
+
+SaveStateList StarTrekMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNr = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNr >= 0 && slotNr <= getMaximumSaveSlot()) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				StarTrek::SavegameMetadata meta;
+				StarTrek::saveOrLoadMetadata(in, nullptr, &meta);
+				delete in;
+
+				uint16 descriptionPos = 0;
+
+				// Security-check, if saveDescription has a terminating NUL
+				while (meta.description[descriptionPos]) {
+					descriptionPos++;
+					if (descriptionPos >= sizeof(meta.description))
+						break;
+				}
+				if (descriptionPos >= sizeof(meta.description)) {
+					strcpy(meta.description, "[broken saved game]");
+				}
+
+				saveList.push_back(SaveStateDescriptor(slotNr, meta.description));
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+
+int StarTrekMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+void StarTrekMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+SaveStateDescriptor StarTrekMetaEngineConnect::querySaveMetaInfos(const char *target, int slotNr) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slotNr);
+
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (in) {
+		StarTrek::SavegameMetadata meta;
+		StarTrek::saveOrLoadMetadata(in, nullptr, &meta);
+		delete in;
+
+		uint16 descriptionPos = 0;
+
+		while (meta.description[descriptionPos]) {
+			descriptionPos++;
+			if (descriptionPos >= sizeof(meta.description))
+				break;
+		}
+		if (descriptionPos >= sizeof(meta.description)) {
+			// broken meta.description, ignore it
+			SaveStateDescriptor descriptor(slotNr, "[broken saved game]");
+			return descriptor;
+		}
+
+		SaveStateDescriptor descriptor(slotNr, meta.description);
+
+		// Do not allow save slot 0 (used for auto-saving) to be deleted or
+		// overwritten.
+		if (slotNr == 0) {
+			descriptor.setWriteProtectedFlag(true);
+			descriptor.setDeletableFlag(false);
+		} else {
+			descriptor.setWriteProtectedFlag(false);
+			descriptor.setDeletableFlag(true);
+		}
+
+		if (meta.thumbnail == nullptr) {
+			return SaveStateDescriptor();
+		}
+
+		descriptor.setThumbnail(meta.thumbnail);
+		descriptor.setPlayTime(meta.playTime);
+		descriptor.setSaveDate(meta.getYear(), meta.getMonth(), meta.getDay());
+		descriptor.setSaveTime(meta.getHour(), meta.getMinute());
+
+		return descriptor;
+
+	} else {
+		SaveStateDescriptor emptySave;
+		// Do not allow save slot 0 (used for auto-saving) to be overwritten.
+		if (slotNr == 0) {
+			emptySave.setWriteProtectedFlag(true);
+		} else {
+			emptySave.setWriteProtectedFlag(false);
+		}
+		return emptySave;
+	}
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(STARTREK)
+    REGISTER_PLUGIN_DYNAMIC(STARTREK, PLUGIN_TYPE_ENGINE, StarTrekMetaEngineConnect);
+#else
+    REGISTER_PLUGIN_STATIC(STARTREK, PLUGIN_TYPE_ENGINE, StarTrekMetaEngineConnect);
+#endif
diff --git a/engines/startrek/module.mk b/engines/startrek/module.mk
index 1de7872aa9..b169b15fef 100644
--- a/engines/startrek/module.mk
+++ b/engines/startrek/module.mk
@@ -6,7 +6,6 @@ MODULE_OBJS = \
 	bitmap.o \
 	common.o \
 	console.o \
-	detection.o \
 	events.o \
 	font.o \
 	graphics.o \
@@ -15,6 +14,7 @@ MODULE_OBJS = \
 	lzss.o \
 	menu.o \
 	resource.o \
+	metaengine.o \
 	room.o \
 	saveload.o \
 	sound.o \
@@ -88,3 +88,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/startrek/startrek.h b/engines/startrek/startrek.h
index 939e53adc3..804878da59 100644
--- a/engines/startrek/startrek.h
+++ b/engines/startrek/startrek.h
@@ -48,6 +48,7 @@
 #include "startrek/object.h"
 #include "startrek/sound.h"
 #include "startrek/space.h"
+#include "startrek/detection_enums.h"
 
 
 using Common::SharedPtr;
@@ -116,15 +117,7 @@ const int MAX_BUFFERED_WALK_ACTIONS = 32;
 const int MAX_BAN_FILES = 16;
 
 
-enum StarTrekGameType {
-	GType_ST25 = 1,
-	GType_STJR = 2
-};
 
-enum StarTrekGameFeatures {
-	GF_DEMO  = (1 << 0),
-	GF_CDROM = (1 << 1)
-};
 
 enum kDebugLevels {
 	kDebugSound =     1 << 0,


Commit: c7d7d18ad269ad01954ee8cdd608fb970f03e1c8
    https://github.com/scummvm/scummvm/commit/c7d7d18ad269ad01954ee8cdd608fb970f03e1c8
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SUPERNOVA: Split detection features & adapt to new plugins.

Changed paths:
  A engines/supernova/metaengine.cpp
    configure
    engines/supernova/detection.cpp
    engines/supernova/module.mk


diff --git a/configure b/configure
index eead51b9ba..d888f829f7 100755
--- a/configure
+++ b/configure
@@ -6166,7 +6166,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
-								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK")
+								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/supernova/detection.cpp b/engines/supernova/detection.cpp
index 618fccd1b9..ed0bf4bcf3 100644
--- a/engines/supernova/detection.cpp
+++ b/engines/supernova/detection.cpp
@@ -23,14 +23,9 @@
 #include "base/plugins.h"
 #include "common/file.h"
 #include "common/gui_options.h"
-#include "common/savefile.h"
 #include "common/translation.h"
-#include "common/system.h"
-#include "graphics/thumbnail.h"
 #include "engines/advancedDetector.h"
 
-#include "supernova/supernova.h"
-
 #define GAMEOPTION_IMPROVED GUIO_GAMEOPTIONS1
 
 static const ADExtraGuiOptionsMap optionsList[] = {
@@ -122,154 +117,7 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Mission Supernova (C) 1994 Thomas and Steffen Dingel";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	void removeSaveState(const char *target, int slot) const override;
-	int getMaximumSaveSlot() const override {
-		return 99;
-	}
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool SupernovaMetaEngine::hasFeature(MetaEngineFeature f) const {
-	switch (f) {
-	case kSupportsLoadingDuringStartup:
-		// fallthrough
-	case kSupportsListSaves:
-		// fallthrough
-	case kSupportsDeleteSave:
-		// fallthrough
-	case kSavesSupportMetaInfo:
-		// fallthrough
-	case kSavesSupportThumbnail:
-		// fallthrough
-	case kSavesSupportCreationDate:
-		// fallthrough
-	case kSavesSupportPlayTime:
-		return true;
-	default:
-		return false;
-	}
-}
-
-bool SupernovaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Supernova::SupernovaEngine(syst);
-	}
-
-	return desc != nullptr;
-}
-
-SaveStateList SupernovaMetaEngine::listSaves(const char *target) const {
-	Common::StringArray filenames;
-	Common::String pattern;
-	if (!strncmp(target, "msn1", 4))
-		pattern = Common::String::format("msn_save.###");
-	if (!strncmp(target, "msn2", 4))
-		pattern = Common::String::format("ms2_save.###");
-
-	filenames = g_system->getSavefileManager()->listSavefiles(pattern);
-
-	SaveStateList saveFileList;
-	for (Common::StringArray::const_iterator file = filenames.begin();
-		 file != filenames.end(); ++file) {
-		int saveSlot = atoi(file->c_str() + file->size() - 3);
-		if (saveSlot >= 0 && saveSlot <= getMaximumSaveSlot()) {
-			Common::InSaveFile *savefile = g_system->getSavefileManager()->openForLoading(*file);
-			if (savefile) {
-				uint saveHeader = savefile->readUint32LE();
-				if ((saveHeader == SAVEGAME_HEADER && !strncmp(target, "msn1", 4)) ||
-					(saveHeader == SAVEGAME_HEADER2 && !strncmp(target, "msn2", 4))) {
-					byte saveVersion = savefile->readByte();
-					if (saveVersion <= SAVEGAME_VERSION) {
-						int saveFileDescSize = savefile->readSint16LE();
-						char* saveFileDesc = new char[saveFileDescSize];
-						savefile->read(saveFileDesc, saveFileDescSize);
-						saveFileList.push_back(SaveStateDescriptor(saveSlot, saveFileDesc));
-						delete [] saveFileDesc;
-					}
-				}
-				delete savefile;
-			}
-		}
-	}
-
-	Common::sort(saveFileList.begin(), saveFileList.end(), SaveStateDescriptorSlotComparator());
-	return saveFileList;
-}
-
-void SupernovaMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename;
-	if (!strncmp(target, "msn1", 4))
-		filename = Common::String::format("msn_save.%03d", slot);
-	if (!strncmp(target, "msn2", 4))
-		filename = Common::String::format("ms2_save.%03d", slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor SupernovaMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName;
-	if (!strncmp(target, "msn1", 4))
-		fileName = Common::String::format("msn_save.%03d", slot);
-	if (!strncmp(target, "msn2", 4))
-		fileName = Common::String::format("ms2_save.%03d", slot);
-	Common::InSaveFile *savefile = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (savefile) {
-		uint saveHeader = savefile->readUint32LE();
-		if ((!strncmp(target, "msn1", 4) && saveHeader != SAVEGAME_HEADER) ||
-			(!strncmp(target, "msn2", 4) && saveHeader != SAVEGAME_HEADER2)) {
-			delete savefile;
-			return SaveStateDescriptor();
-		}
-		byte saveVersion = savefile->readByte();
-		if (saveVersion > SAVEGAME_VERSION){
-			delete savefile;
-			return SaveStateDescriptor();
-		}
-
-		int descriptionSize = savefile->readSint16LE();
-		char* description = new char[descriptionSize];
-		savefile->read(description, descriptionSize);
-		SaveStateDescriptor desc(slot, description);
-		delete [] description;
-
-		uint32 saveDate = savefile->readUint32LE();
-		int day = (saveDate >> 24) & 0xFF;
-		int month = (saveDate >> 16) & 0xFF;
-		int year = saveDate & 0xFFFF;
-		desc.setSaveDate(year, month, day);
-
-		uint16 saveTime = savefile->readUint16LE();
-		int hour = (saveTime >> 8) & 0xFF;
-		int minutes = saveTime & 0xFF;
-		desc.setSaveTime(hour, minutes);
-
-		uint32 playTime =savefile->readUint32LE();
-		desc.setPlayTime(playTime * 1000);
-
-		if (Graphics::checkThumbnailHeader(*savefile)) {
-			Graphics::Surface *thumbnail;
-			if (!Graphics::loadThumbnail(*savefile, thumbnail)) {
-				delete savefile;
-				return SaveStateDescriptor();
-			}
-			desc.setThumbnail(thumbnail);
-		}
-
-		delete savefile;
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
 
-#if PLUGIN_ENABLED_DYNAMIC(SUPERNOVA)
-REGISTER_PLUGIN_DYNAMIC(SUPERNOVA, PLUGIN_TYPE_ENGINE, SupernovaMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(SUPERNOVA, PLUGIN_TYPE_ENGINE, SupernovaMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(SUPERNOVA_DETECTION, PLUGIN_TYPE_METAENGINE, SupernovaMetaEngine);
diff --git a/engines/supernova/metaengine.cpp b/engines/supernova/metaengine.cpp
new file mode 100644
index 0000000000..36c756c8c6
--- /dev/null
+++ b/engines/supernova/metaengine.cpp
@@ -0,0 +1,183 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+#include "common/file.h"
+#include "common/gui_options.h"
+#include "common/savefile.h"
+#include "common/translation.h"
+#include "common/system.h"
+#include "graphics/thumbnail.h"
+#include "engines/advancedDetector.h"
+
+#include "supernova/supernova.h"
+
+class SupernovaMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "supernova";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	void removeSaveState(const char *target, int slot) const override;
+	int getMaximumSaveSlot() const override {
+		return 99;
+	}
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool SupernovaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	switch (f) {
+	case kSupportsLoadingDuringStartup:
+	case kSupportsListSaves:
+	case kSupportsDeleteSave:
+	case kSavesSupportMetaInfo:
+	case kSavesSupportThumbnail:
+	case kSavesSupportCreationDate:
+	case kSavesSupportPlayTime:
+		return true;
+	default:
+		return false;
+	}
+}
+
+bool SupernovaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Supernova::SupernovaEngine(syst);
+	}
+
+	return desc != nullptr;
+}
+
+SaveStateList SupernovaMetaEngineConnect::listSaves(const char *target) const {
+	Common::StringArray filenames;
+	Common::String pattern;
+	if (!strncmp(target, "msn1", 4))
+		pattern = Common::String::format("msn_save.###");
+	if (!strncmp(target, "msn2", 4))
+		pattern = Common::String::format("ms2_save.###");
+
+	filenames = g_system->getSavefileManager()->listSavefiles(pattern);
+
+	SaveStateList saveFileList;
+	for (Common::StringArray::const_iterator file = filenames.begin();
+		 file != filenames.end(); ++file) {
+		int saveSlot = atoi(file->c_str() + file->size() - 3);
+		if (saveSlot >= 0 && saveSlot <= getMaximumSaveSlot()) {
+			Common::InSaveFile *savefile = g_system->getSavefileManager()->openForLoading(*file);
+			if (savefile) {
+				uint saveHeader = savefile->readUint32LE();
+				if ((saveHeader == SAVEGAME_HEADER && !strncmp(target, "msn1", 4)) ||
+					(saveHeader == SAVEGAME_HEADER2 && !strncmp(target, "msn2", 4))) {
+					byte saveVersion = savefile->readByte();
+					if (saveVersion <= SAVEGAME_VERSION) {
+						int saveFileDescSize = savefile->readSint16LE();
+						char* saveFileDesc = new char[saveFileDescSize];
+						savefile->read(saveFileDesc, saveFileDescSize);
+						saveFileList.push_back(SaveStateDescriptor(saveSlot, saveFileDesc));
+						delete [] saveFileDesc;
+					}
+				}
+				delete savefile;
+			}
+		}
+	}
+
+	Common::sort(saveFileList.begin(), saveFileList.end(), SaveStateDescriptorSlotComparator());
+	return saveFileList;
+}
+
+void SupernovaMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename;
+	if (!strncmp(target, "msn1", 4))
+		filename = Common::String::format("msn_save.%03d", slot);
+	if (!strncmp(target, "msn2", 4))
+		filename = Common::String::format("ms2_save.%03d", slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor SupernovaMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName;
+	if (!strncmp(target, "msn1", 4))
+		fileName = Common::String::format("msn_save.%03d", slot);
+	if (!strncmp(target, "msn2", 4))
+		fileName = Common::String::format("ms2_save.%03d", slot);
+	Common::InSaveFile *savefile = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (savefile) {
+		uint saveHeader = savefile->readUint32LE();
+		if ((!strncmp(target, "msn1", 4) && saveHeader != SAVEGAME_HEADER) ||
+			(!strncmp(target, "msn2", 4) && saveHeader != SAVEGAME_HEADER2)) {
+			delete savefile;
+			return SaveStateDescriptor();
+		}
+		byte saveVersion = savefile->readByte();
+		if (saveVersion > SAVEGAME_VERSION){
+			delete savefile;
+			return SaveStateDescriptor();
+		}
+
+		int descriptionSize = savefile->readSint16LE();
+		char* description = new char[descriptionSize];
+		savefile->read(description, descriptionSize);
+		SaveStateDescriptor desc(slot, description);
+		delete [] description;
+
+		uint32 saveDate = savefile->readUint32LE();
+		int day = (saveDate >> 24) & 0xFF;
+		int month = (saveDate >> 16) & 0xFF;
+		int year = saveDate & 0xFFFF;
+		desc.setSaveDate(year, month, day);
+
+		uint16 saveTime = savefile->readUint16LE();
+		int hour = (saveTime >> 8) & 0xFF;
+		int minutes = saveTime & 0xFF;
+		desc.setSaveTime(hour, minutes);
+
+		uint32 playTime =savefile->readUint32LE();
+		desc.setPlayTime(playTime * 1000);
+
+		if (Graphics::checkThumbnailHeader(*savefile)) {
+			Graphics::Surface *thumbnail;
+			if (!Graphics::loadThumbnail(*savefile, thumbnail)) {
+				delete savefile;
+				return SaveStateDescriptor();
+			}
+			desc.setThumbnail(thumbnail);
+		}
+
+		delete savefile;
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(SUPERNOVA)
+    REGISTER_PLUGIN_DYNAMIC(SUPERNOVA, PLUGIN_TYPE_ENGINE, SupernovaMetaEngineConnect);
+#else
+    REGISTER_PLUGIN_STATIC(SUPERNOVA, PLUGIN_TYPE_ENGINE, SupernovaMetaEngineConnect);
+#endif
diff --git a/engines/supernova/module.mk b/engines/supernova/module.mk
index ae8a71abf8..22db249658 100644
--- a/engines/supernova/module.mk
+++ b/engines/supernova/module.mk
@@ -2,8 +2,8 @@ MODULE := engines/supernova
 
 MODULE_OBJS := \
 	console.o \
-	detection.o \
 	graphics.o \
+	metaengine.o \
 	resman.o \
 	room.o \
 	supernova1/rooms.o \
@@ -25,3 +25,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 2aca677fcc9c7bd1487fae8be51758dd325f4486
    https://github.com/scummvm/scummvm/commit/2aca677fcc9c7bd1487fae8be51758dd325f4486
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TEENAGENT: Split detection features & adapt to new plugins.

Changed paths:
  A engines/teenagent/metaengine.cpp
    configure
    engines/teenagent/detection.cpp
    engines/teenagent/module.mk


diff --git a/configure b/configure
index d888f829f7..b44c6b9561 100755
--- a/configure
+++ b/configure
@@ -6166,7 +6166,8 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
-								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA")
+								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
+								  "TEENAGENT")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/teenagent/detection.cpp b/engines/teenagent/detection.cpp
index 4a5de272dc..ad1b1629ea 100644
--- a/engines/teenagent/detection.cpp
+++ b/engines/teenagent/detection.cpp
@@ -20,16 +20,11 @@
  *
  */
 
-#include "common/system.h"
-#include "common/savefile.h"
 #include "common/algorithm.h"
 
 #include "base/plugins.h"
 
 #include "engines/advancedDetector.h"
-#include "teenagent/resources.h"
-#include "teenagent/teenagent.h"
-#include "graphics/thumbnail.h"
 
 static const PlainGameDescriptor teenAgentGames[] = {
 	{ "teenagent", "Teen Agent" },
@@ -81,9 +76,7 @@ static const ADGameDescription teenAgentGameDescriptions[] = {
 	AD_TABLE_END_MARKER,
 };
 
-enum {
-	MAX_SAVES = 20
-};
+
 
 class TeenAgentMetaEngine : public AdvancedMetaEngine {
 public:
@@ -101,98 +94,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "TEENAGENT (C) 1994 Metropolis";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override {
-		switch (f) {
-		case kSupportsListSaves:
-		case kSupportsDeleteSave:
-		case kSupportsLoadingDuringStartup:
-		case kSavesSupportMetaInfo:
-		case kSavesSupportThumbnail:
-			return true;
-		default:
-			return false;
-		}
-	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
-		if (desc) {
-			*engine = new TeenAgent::TeenAgentEngine(syst, desc);
-		}
-		return desc != 0;
-	}
-
-	static Common::String generateGameStateFileName(const char *target, int slot) {
-		return Common::String::format("%s.%02d", target, slot);
-	}
-
-	SaveStateList listSaves(const char *target) const override {
-		Common::String pattern = target;
-		pattern += ".##";
-
-		Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
-
-		SaveStateList saveList;
-		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-			int slot = atoi(file->c_str() + file->size() - 2);
-			if (slot >= 0 && slot < MAX_SAVES) {
-				Common::ScopedPtr<Common::InSaveFile> in(g_system->getSavefileManager()->openForLoading(*file));
-				if (!in)
-					continue;
-
-				char buf[25];
-				in->seek(0);
-				in->read(buf, 24);
-				buf[24] = 0;
-				saveList.push_back(SaveStateDescriptor(slot, buf));
-			}
-		}
-		// Sort saves based on slot number.
-		Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-		return saveList;
-	}
-
-	int getMaximumSaveSlot() const override {
-		return MAX_SAVES - 1;
-	}
-
-	void removeSaveState(const char *target, int slot) const override {
-		Common::String filename = generateGameStateFileName(target, slot);
-		g_system->getSavefileManager()->removeSavefile(filename);
-	}
-
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
-		Common::String filename = generateGameStateFileName(target, slot);
-		Common::ScopedPtr<Common::InSaveFile> in(g_system->getSavefileManager()->openForLoading(filename));
-		if (!in)
-			return SaveStateDescriptor();
-
-		char buf[25];
-		in->seek(0);
-		in->read(buf, 24);
-		buf[24] = 0;
-
-		Common::String desc = buf;
-
-		in->seek(TeenAgent::saveStateSize);
-		if (!Graphics::checkThumbnailHeader(*in))
-			return SaveStateDescriptor(slot, desc);
-
-		SaveStateDescriptor ssd(slot, desc);
-
-		//checking for the thumbnail
-		Graphics::Surface *thumbnail;
-		if (!Graphics::loadThumbnail(*in, thumbnail)) {
-			return SaveStateDescriptor();
-		}
-		ssd.setThumbnail(thumbnail);
-
-		return ssd;
-	}
 };
 
-#if PLUGIN_ENABLED_DYNAMIC(TEENAGENT)
-	REGISTER_PLUGIN_DYNAMIC(TEENAGENT, PLUGIN_TYPE_ENGINE, TeenAgentMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TEENAGENT, PLUGIN_TYPE_ENGINE, TeenAgentMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(TEENAGENT_DETECTION, PLUGIN_TYPE_METAENGINE, TeenAgentMetaEngine);
diff --git a/engines/teenagent/metaengine.cpp b/engines/teenagent/metaengine.cpp
new file mode 100644
index 0000000000..74f21474dc
--- /dev/null
+++ b/engines/teenagent/metaengine.cpp
@@ -0,0 +1,137 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/system.h"
+#include "common/savefile.h"
+#include "common/algorithm.h"
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+#include "teenagent/resources.h"
+#include "teenagent/teenagent.h"
+#include "graphics/thumbnail.h"
+
+enum {
+	MAX_SAVES = 20
+};
+
+class TeenAgentMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "teenagent";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override {
+		switch (f) {
+		case kSupportsListSaves:
+		case kSupportsDeleteSave:
+		case kSupportsLoadingDuringStartup:
+		case kSavesSupportMetaInfo:
+		case kSavesSupportThumbnail:
+			return true;
+		default:
+			return false;
+		}
+	}
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
+		if (desc) {
+			*engine = new TeenAgent::TeenAgentEngine(syst, desc);
+		}
+		return desc != 0;
+	}
+
+	static Common::String generateGameStateFileName(const char *target, int slot) {
+		return Common::String::format("%s.%02d", target, slot);
+	}
+
+	SaveStateList listSaves(const char *target) const override {
+		Common::String pattern = target;
+		pattern += ".##";
+
+		Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
+
+		SaveStateList saveList;
+		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+			int slot = atoi(file->c_str() + file->size() - 2);
+			if (slot >= 0 && slot < MAX_SAVES) {
+				Common::ScopedPtr<Common::InSaveFile> in(g_system->getSavefileManager()->openForLoading(*file));
+				if (!in)
+					continue;
+
+				char buf[25];
+				in->seek(0);
+				in->read(buf, 24);
+				buf[24] = 0;
+				saveList.push_back(SaveStateDescriptor(slot, buf));
+			}
+		}
+		// Sort saves based on slot number.
+		Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+		return saveList;
+	}
+
+	int getMaximumSaveSlot() const override {
+		return MAX_SAVES - 1;
+	}
+
+	void removeSaveState(const char *target, int slot) const override {
+		Common::String filename = generateGameStateFileName(target, slot);
+		g_system->getSavefileManager()->removeSavefile(filename);
+	}
+
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
+		Common::String filename = generateGameStateFileName(target, slot);
+		Common::ScopedPtr<Common::InSaveFile> in(g_system->getSavefileManager()->openForLoading(filename));
+		if (!in)
+			return SaveStateDescriptor();
+
+		char buf[25];
+		in->seek(0);
+		in->read(buf, 24);
+		buf[24] = 0;
+
+		Common::String desc = buf;
+
+		in->seek(TeenAgent::saveStateSize);
+		if (!Graphics::checkThumbnailHeader(*in))
+			return SaveStateDescriptor(slot, desc);
+
+		SaveStateDescriptor ssd(slot, desc);
+
+		//checking for the thumbnail
+		Graphics::Surface *thumbnail;
+		if (!Graphics::loadThumbnail(*in, thumbnail)) {
+			return SaveStateDescriptor();
+		}
+		ssd.setThumbnail(thumbnail);
+
+		return ssd;
+	}
+};
+
+#if PLUGIN_ENABLED_DYNAMIC(TEENAGENT)
+	REGISTER_PLUGIN_DYNAMIC(TEENAGENT, PLUGIN_TYPE_ENGINE, TeenAgentMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TEENAGENT, PLUGIN_TYPE_ENGINE, TeenAgentMetaEngineConnect);
+#endif
diff --git a/engines/teenagent/module.mk b/engines/teenagent/module.mk
index 01ba3c79cb..8deb130f57 100644
--- a/engines/teenagent/module.mk
+++ b/engines/teenagent/module.mk
@@ -5,10 +5,10 @@ MODULE_OBJS := \
 	animation.o \
 	callbacks.o \
 	console.o \
-	detection.o \
 	dialog.o \
 	font.o \
 	inventory.o \
+	metaengine.o \
 	music.o \
 	objects.o \
 	pack.o \
@@ -26,3 +26,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 31b35628f22c1816354bfb0b9d34785d918ce64d
    https://github.com/scummvm/scummvm/commit/31b35628f22c1816354bfb0b9d34785d918ce64d
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TESTBED: Split detection features & adapt to new plugins.

Changed paths:
  A engines/testbed/metaengine.cpp
    configure
    engines/testbed/detection.cpp
    engines/testbed/module.mk


diff --git a/configure b/configure
index b44c6b9561..aab9dd0298 100755
--- a/configure
+++ b/configure
@@ -6167,7 +6167,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
-								  "TEENAGENT")
+								  "TEENAGENT" "TESTBED")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/testbed/detection.cpp b/engines/testbed/detection.cpp
index 1179a6b9d7..dcc22dc13b 100644
--- a/engines/testbed/detection.cpp
+++ b/engines/testbed/detection.cpp
@@ -21,13 +21,9 @@
  */
 
 #include "engines/advancedDetector.h"
-#include "common/system.h"
 
 #include "base/plugins.h"
 
-#include "testbed/testbed.h"
-#include "testbed/testsuite.h"
-
 static const PlainGameDescriptor testbed_setting[] = {
 	{ "testbed", "Testbed: The Backend Testing Framework" },
 	{ 0, 0 }
@@ -63,38 +59,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Copyright (C) ScummVM";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription * /* desc */) const override {
-		// Instantiate Engine even if the game data is not found.
-		*engine = new Testbed::TestbedEngine(syst);
-		return true;
-	}
-
-	const Common::AchievementsInfo getAchievementsInfo(const Common::String &target) const override {
-		Common::AchievementsInfo result;
-		result.platform = Common::UNK_ACHIEVEMENTS;
-		result.appId = "testbed";
-		Common::AchievementDescription testSuiteFinalAchievement = {"EVERYTHINGWORKS", true, "Everything works!", "Completed all available testsuites"};
-		result.descriptions.push_back(testSuiteFinalAchievement);
-
-		Common::Array<Testbed::Testsuite *> testsuiteList;
-		Testbed::TestbedEngine::pushTestsuites(testsuiteList);
-		for (Common::Array<Testbed::Testsuite *>::const_iterator i = testsuiteList.begin(); i != testsuiteList.end(); ++i) {
-			Common::AchievementDescription it = {(*i)->getName(), false, (*i)->getDescription(), 0};
-			result.descriptions.push_back(it);
-			delete (*i);
-		}
-
-		return result;
-	}
-	
-	bool hasFeature(MetaEngineFeature f) const override {
-		return false;
-	}
 };
 
-#if PLUGIN_ENABLED_DYNAMIC(TESTBED)
-	REGISTER_PLUGIN_DYNAMIC(TESTBED, PLUGIN_TYPE_ENGINE, TestbedMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TESTBED, PLUGIN_TYPE_ENGINE, TestbedMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(TESTBED_DETECTION, PLUGIN_TYPE_METAENGINE, TestbedMetaEngine);
diff --git a/engines/testbed/metaengine.cpp b/engines/testbed/metaengine.cpp
new file mode 100644
index 0000000000..b0c00692cf
--- /dev/null
+++ b/engines/testbed/metaengine.cpp
@@ -0,0 +1,71 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "common/system.h"
+
+#include "engines/advancedDetector.h"
+
+#include "testbed/testbed.h"
+#include "testbed/testsuite.h"
+
+class TestbedMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "testbed";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription * /* desc */) const override {
+		// Instantiate Engine even if the game data is not found.
+		*engine = new Testbed::TestbedEngine(syst);
+		return true;
+	}
+
+	const Common::AchievementsInfo getAchievementsInfo(const Common::String &target) const override {
+		Common::AchievementsInfo result;
+		result.platform = Common::UNK_ACHIEVEMENTS;
+		result.appId = "testbed";
+		Common::AchievementDescription testSuiteFinalAchievement = {"EVERYTHINGWORKS", true, "Everything works!", "Completed all available testsuites"};
+		result.descriptions.push_back(testSuiteFinalAchievement);
+
+		Common::Array<Testbed::Testsuite *> testsuiteList;
+		Testbed::TestbedEngine::pushTestsuites(testsuiteList);
+		for (Common::Array<Testbed::Testsuite *>::const_iterator i = testsuiteList.begin(); i != testsuiteList.end(); ++i) {
+			Common::AchievementDescription it = {(*i)->getName(), false, (*i)->getDescription(), 0};
+			result.descriptions.push_back(it);
+			delete (*i);
+		}
+
+		return result;
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override {
+		return false;
+	}
+};
+
+#if PLUGIN_ENABLED_DYNAMIC(TESTBED)
+	REGISTER_PLUGIN_DYNAMIC(TESTBED, PLUGIN_TYPE_ENGINE, TestbedMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TESTBED, PLUGIN_TYPE_ENGINE, TestbedMetaEngineConnect);
+#endif
diff --git a/engines/testbed/module.mk b/engines/testbed/module.mk
index c1a13086d2..f63cb70efa 100644
--- a/engines/testbed/module.mk
+++ b/engines/testbed/module.mk
@@ -3,10 +3,10 @@ MODULE := engines/testbed
 MODULE_OBJS := \
 	config.o \
 	config-params.o \
-	detection.o \
 	events.o \
 	fs.o \
 	graphics.o \
+	metaengine.o \
 	midi.o \
 	misc.o \
 	networking.o \
@@ -44,3 +44,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: b1be077085ffcafb3a9b4b687cc17dd1c113b549
    https://github.com/scummvm/scummvm/commit/b1be077085ffcafb3a9b4b687cc17dd1c113b549
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TINSEL: Split detection features & adapt to new plugins.

Changed paths:
  A engines/tinsel/detection.h
  A engines/tinsel/detection_enums.h
  A engines/tinsel/metaengine.cpp
    configure
    engines/tinsel/detection.cpp
    engines/tinsel/module.mk
    engines/tinsel/tinsel.h


diff --git a/configure b/configure
index aab9dd0298..b68a69e01c 100755
--- a/configure
+++ b/configure
@@ -6167,7 +6167,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
-								  "TEENAGENT" "TESTBED")
+								  "TEENAGENT" "TESTBED" "TINSEL")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/tinsel/detection.cpp b/engines/tinsel/detection.cpp
index 744c916fe5..e4e364539a 100644
--- a/engines/tinsel/detection.cpp
+++ b/engines/tinsel/detection.cpp
@@ -25,53 +25,9 @@
 #include "engines/advancedDetector.h"
 #include "common/file.h"
 #include "common/md5.h"
-#include "common/savefile.h"
 
-#include "tinsel/bmv.h"
-#include "tinsel/cursor.h"
-#include "tinsel/tinsel.h"
-#include "tinsel/savescn.h"	// needed by TinselMetaEngine::listSaves
-
-namespace Tinsel {
-
-struct TinselGameDescription {
-	ADGameDescription desc;
-
-	int gameID;
-	int gameType;
-	uint32 features;
-	uint16 version;
-};
-
-uint32 TinselEngine::getGameID() const {
-	return _gameDescription->gameID;
-}
-
-uint32 TinselEngine::getFeatures() const {
-	return _gameDescription->features;
-}
-
-Common::Language TinselEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-Common::Platform TinselEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-uint16 TinselEngine::getVersion() const {
-	return _gameDescription->version;
-}
-
-bool TinselEngine::getIsADGFDemo() const {
-	return (bool)(_gameDescription->desc.flags & ADGF_DEMO);
-}
-
-bool TinselEngine::isV1CD() const {
-	return (bool)(_gameDescription->desc.flags & ADGF_CD);
-}
-
-} // End of namespace Tinsel
+#include "tinsel/detection.h"
+#include "tinsel/detection_enums.h"
 
 static const PlainGameDescriptor tinselGames[] = {
 	{"dw", "Discworld"},
@@ -98,125 +54,9 @@ public:
 		return "Tinsel (C) Psygnosis";
 	}
 
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool TinselMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSimpleSavesNames) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSavesSupportCreationDate);
-}
-
-bool Tinsel::TinselEngine::hasFeature(EngineFeature f) const {
-	return
-#if 0
-		// FIXME: It is possible to return to the launcher from tinsel.
-		// But then any attempt to re-enter the engine will lead to
-		// a crash or at least seriously broken behavior.
-		//
-		// This is because the Tinsel engine makes use of tons of
-		// global variables (static and non-static) which are never
-		// explicitly re-initialized when the engine is started
-		// for a second time.
-		(f == kSupportsReturnToLauncher) ||
-#endif
-		(f == kSupportsLoadingDuringRuntime);
-}
-
-SaveStateDescriptor TinselMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName;
-	fileName = Common::String::format("%s.%03u", target, slot);
-
-	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (!file) {
-		return SaveStateDescriptor();
-	}
-
-	file->readUint32LE();		// skip id
-	file->readUint32LE();		// skip size
-	uint32 ver = file->readUint32LE();
-	char saveDesc[Tinsel::SG_DESC_LEN];
-	file->read(saveDesc, sizeof(saveDesc));
-
-	saveDesc[Tinsel::SG_DESC_LEN - 1] = 0;
-	SaveStateDescriptor desc(slot, saveDesc);
-
-	int8 tm_year = file->readUint16LE();
-	int8 tm_mon = file->readSByte();
-	int8 tm_mday = file->readSByte();
-	int8 tm_hour = file->readSByte();
-	int8 tm_min = file->readSByte();
-	file->readSByte(); // skip secs
-
-	desc.setSaveDate(1900 + tm_year, 1 + tm_mon, tm_mday);
-	desc.setSaveTime(tm_hour, tm_min);
-
-	if (ver >= 3) {
-		uint32 playTime = file->readUint32LE(); // playTime in seconds
-		desc.setPlayTime(playTime);
-	}
-
-	delete file;
-	return desc;
-}
-
-namespace Tinsel {
-extern int getList(Common::SaveFileManager *saveFileMan, const Common::String &target);
-}
-
-SaveStateList TinselMetaEngine::listSaves(const char *target) const {
-	Common::String pattern = target;
-	pattern = pattern + ".###";
-	Common::StringArray files = g_system->getSavefileManager()->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	int slotNum = 0;
-	for (Common::StringArray::const_iterator file = files.begin(); file != files.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		slotNum = atoi(file->c_str() + file->size() - 3);
-
-		const Common::String &fname = *file;
-		Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fname);
-		if (in) {
-			in->readUint32LE();		// skip id
-			in->readUint32LE();		// skip size
-			in->readUint32LE();		// skip version
-			char saveDesc[Tinsel::SG_DESC_LEN];
-			in->read(saveDesc, sizeof(saveDesc));
-
-			saveDesc[Tinsel::SG_DESC_LEN - 1] = 0;
-
-			saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-			delete in;
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-bool TinselMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Tinsel::TinselGameDescription *gd = (const Tinsel::TinselGameDescription *)desc;
-	if (gd) {
-		*engine = new Tinsel::TinselEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
 struct SizeMD5 {
 	int size;
 	Common::String md5;
@@ -365,95 +205,4 @@ ADDetectedGame TinselMetaEngine::fallbackDetect(const FileMap &allFilesXXX, cons
 	return matched;
 }
 
-int TinselMetaEngine::getMaximumSaveSlot() const { return 99; }
-
-void TinselMetaEngine::removeSaveState(const char *target, int slot) const {
-	Tinsel::setNeedLoad();
-	// Same issue here as with loadGameState(): we need the physical savegame
-	// slot. Refer to bug #3387551.
-	int listSlot = -1;
-	const int numStates = Tinsel::getList(g_system->getSavefileManager(), target);
-	for (int i = 0; i < numStates; ++i) {
-		const char *fileName = Tinsel::ListEntry(i, Tinsel::LE_NAME);
-		const int saveSlot = atoi(fileName + strlen(fileName) - 3);
-
-		if (saveSlot == slot) {
-			listSlot = i;
-			break;
-		}
-	}
-
-	g_system->getSavefileManager()->removeSavefile(Tinsel::ListEntry(listSlot, Tinsel::LE_NAME));
-	Tinsel::setNeedLoad();
-	Tinsel::getList(g_system->getSavefileManager(), target);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(TINSEL)
-	REGISTER_PLUGIN_DYNAMIC(TINSEL, PLUGIN_TYPE_ENGINE, TinselMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TINSEL, PLUGIN_TYPE_ENGINE, TinselMetaEngine);
-#endif
-
-namespace Tinsel {
-
-Common::Error TinselEngine::loadGameState(int slot) {
-	// FIXME: Hopefully this is only used when loading games via
-	// the launcher, since we do a hacky savegame slot to savelist
-	// entry mapping here.
-	//
-	// You might wonder why is needed and here is the answer:
-	// The save/load dialog of the GMM operates with the physical
-	// savegame slots, while Tinsel internally uses entry numbers in
-	// a savelist (which is sorted latest to first). Now to allow
-	// proper loading of (especially Discworld2) saves we need to
-	// get a savelist entry number instead of the physical slot.
-	//
-	// There are different possible solutions:
-	//
-	// One way to fix this would be to pass the filename instead of
-	// the savelist entry number to RestoreGame, though it could make
-	// problems how DW2 handles CD switches. Normally DW2 would pass
-	// '-2' as slot when it changes CDs.
-	//
-	// Another way would be to convert all of Tinsel to use physical
-	// slot numbers instead of savelist entry numbers for loading.
-	// This would also allow '-2' as slot for CD changes without
-	// any major hackery.
-
-	int listSlot = -1;
-	const int numStates = Tinsel::getList();
-	for (int i = 0; i < numStates; ++i) {
-		const char *fileName = Tinsel::ListEntry(i, Tinsel::LE_NAME);
-		const int saveSlot = atoi(fileName + strlen(fileName) - 3);
-
-		if (saveSlot == slot) {
-			listSlot = i;
-			break;
-		}
-	}
-
-	if (listSlot == -1)
-		return Common::kUnknownError;	// TODO: proper error code
-
-	RestoreGame(listSlot);
-	return Common::kNoError;	// TODO: return success/failure
-}
-
-#if 0
-Common::Error TinselEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
-	Common::String saveName = _vm->getSavegameFilename((int16)(slot + 1));
-	char saveDesc[SG_DESC_LEN];
-	Common::strlcpy(saveDesc, desc, SG_DESC_LEN);
-	SaveGame((char *)saveName.c_str(), saveDesc);
-	ProcessSRQueue();			// This shouldn't be needed, but for some reason it is...
-	return Common::kNoError;	// TODO: return success/failure
-}
-#endif
-
-bool TinselEngine::canLoadGameStateCurrently() { return !_bmv->MoviePlaying(); }
-
-#if 0
-bool TinselEngine::canSaveGameStateCurrently() { return isCursorShown(); }
-#endif
-
-} // End of namespace Tinsel
+REGISTER_PLUGIN_STATIC(TINSEL_DETECTION, PLUGIN_TYPE_METAENGINE, TinselMetaEngine);
diff --git a/engines/tinsel/detection.h b/engines/tinsel/detection.h
new file mode 100644
index 0000000000..797b928296
--- /dev/null
+++ b/engines/tinsel/detection.h
@@ -0,0 +1,34 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Tinsel {
+
+struct TinselGameDescription {
+	ADGameDescription desc;
+
+	int gameID;
+	int gameType;
+	uint32 features;
+	uint16 version;
+};
+
+} // End of namespace Tinsel
diff --git a/engines/tinsel/detection_enums.h b/engines/tinsel/detection_enums.h
new file mode 100644
index 0000000000..9134ecb0e4
--- /dev/null
+++ b/engines/tinsel/detection_enums.h
@@ -0,0 +1,60 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Tinsel {
+
+enum TinselGameID {
+	GID_DW1 = 0,
+	GID_DW2 = 1
+};
+
+enum TinselGameFeatures {
+	GF_SCNFILES = 1 << 0,
+	GF_ENHANCED_AUDIO_SUPPORT = 1 << 1,
+	GF_ALT_MIDI = 1 << 2,		// Alternate sequence in midi.dat file
+
+	// The GF_USE_?FLAGS values specify how many country flags are displayed
+	// in the subtitles options dialog.
+	// None of these defined -> 1 language, in ENGLISH.TXT
+	GF_USE_3FLAGS = 1 << 3,	// French, German, Spanish
+	GF_USE_4FLAGS = 1 << 4,	// French, German, Spanish, Italian
+	GF_USE_5FLAGS = 1 << 5	// All 5 flags
+};
+
+/**
+ * The following is the ScummVM definitions of the various Tinsel versions:
+ * TINSEL_V0 - This was an early engine version that was only used in the Discworld 1
+ *			demo.
+ * TINSEL_V1 - This was the engine version used by Discworld 1. Note that there were two
+ *			major releases: an earlier version that used *.gra files, and a later one that
+ *			used *.scn files, and contained certain script and engine bugfixes. In ScummVM,
+ *			we treat both releases as 'Tinsel 1', since the engine fixes from the later
+ *			version work equally well the earlier version data.
+ * TINSEL_V2 - This is the engine used for the Discworld 2 game.
+ */
+enum TinselEngineVersion {
+	TINSEL_V0 = 0,
+	TINSEL_V1 = 1,
+	TINSEL_V2 = 2
+};
+
+} // End of namespace Tinsel
diff --git a/engines/tinsel/metaengine.cpp b/engines/tinsel/metaengine.cpp
new file mode 100644
index 0000000000..a5a5eb3c67
--- /dev/null
+++ b/engines/tinsel/metaengine.cpp
@@ -0,0 +1,281 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/savefile.h"
+
+#include "engines/advancedDetector.h"
+
+#include "tinsel/bmv.h"
+#include "tinsel/cursor.h"
+#include "tinsel/tinsel.h"
+#include "tinsel/savescn.h"	// needed by TinselMetaEngine::
+
+#include "tinsel/detection.h"
+
+namespace Tinsel {
+
+uint32 TinselEngine::getGameID() const {
+	return _gameDescription->gameID;
+}
+
+uint32 TinselEngine::getFeatures() const {
+	return _gameDescription->features;
+}
+
+Common::Language TinselEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+Common::Platform TinselEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+uint16 TinselEngine::getVersion() const {
+	return _gameDescription->version;
+}
+
+bool TinselEngine::getIsADGFDemo() const {
+	return (bool)(_gameDescription->desc.flags & ADGF_DEMO);
+}
+
+bool TinselEngine::isV1CD() const {
+	return (bool)(_gameDescription->desc.flags & ADGF_CD);
+}
+
+} // End of namespace Tinsel
+
+class TinselMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const  override{
+		return "tinsel";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool TinselMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSimpleSavesNames) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSavesSupportCreationDate);
+}
+
+bool Tinsel::TinselEngine::hasFeature(EngineFeature f) const {
+	return
+#if 0
+		// FIXME: It is possible to return to the launcher from tinsel.
+		// But then any attempt to re-enter the engine will lead to
+		// a crash or at least seriously broken behavior.
+		//
+		// This is because the Tinsel engine makes use of tons of
+		// global variables (static and non-static) which are never
+		// explicitly re-initialized when the engine is started
+		// for a second time.
+		(f == kSupportsReturnToLauncher) ||
+#endif
+		(f == kSupportsLoadingDuringRuntime);
+}
+
+SaveStateDescriptor TinselMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName;
+	fileName = Common::String::format("%s.%03u", target, slot);
+
+	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (!file) {
+		return SaveStateDescriptor();
+	}
+
+	file->readUint32LE();		// skip id
+	file->readUint32LE();		// skip size
+	uint32 ver = file->readUint32LE();
+	char saveDesc[Tinsel::SG_DESC_LEN];
+	file->read(saveDesc, sizeof(saveDesc));
+
+	saveDesc[Tinsel::SG_DESC_LEN - 1] = 0;
+	SaveStateDescriptor desc(slot, saveDesc);
+
+	int8 tm_year = file->readUint16LE();
+	int8 tm_mon = file->readSByte();
+	int8 tm_mday = file->readSByte();
+	int8 tm_hour = file->readSByte();
+	int8 tm_min = file->readSByte();
+	file->readSByte(); // skip secs
+
+	desc.setSaveDate(1900 + tm_year, 1 + tm_mon, tm_mday);
+	desc.setSaveTime(tm_hour, tm_min);
+
+	if (ver >= 3) {
+		uint32 playTime = file->readUint32LE(); // playTime in seconds
+		desc.setPlayTime(playTime);
+	}
+
+	delete file;
+	return desc;
+}
+
+namespace Tinsel {
+extern int getList(Common::SaveFileManager *saveFileMan, const Common::String &target);
+}
+
+SaveStateList TinselMetaEngineConnect::listSaves(const char *target) const {
+	Common::String pattern = target;
+	pattern = pattern + ".###";
+	Common::StringArray files = g_system->getSavefileManager()->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	int slotNum = 0;
+	for (Common::StringArray::const_iterator file = files.begin(); file != files.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		slotNum = atoi(file->c_str() + file->size() - 3);
+
+		const Common::String &fname = *file;
+		Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fname);
+		if (in) {
+			in->readUint32LE();		// skip id
+			in->readUint32LE();		// skip size
+			in->readUint32LE();		// skip version
+			char saveDesc[Tinsel::SG_DESC_LEN];
+			in->read(saveDesc, sizeof(saveDesc));
+
+			saveDesc[Tinsel::SG_DESC_LEN - 1] = 0;
+
+			saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+			delete in;
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+bool TinselMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Tinsel::TinselGameDescription *gd = (const Tinsel::TinselGameDescription *)desc;
+	if (gd) {
+		*engine = new Tinsel::TinselEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+int TinselMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+
+void TinselMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Tinsel::setNeedLoad();
+	// Same issue here as with loadGameState(): we need the physical savegame
+	// slot. Refer to bug #3387551.
+	int listSlot = -1;
+	const int numStates = Tinsel::getList(g_system->getSavefileManager(), target);
+	for (int i = 0; i < numStates; ++i) {
+		const char *fileName = Tinsel::ListEntry(i, Tinsel::LE_NAME);
+		const int saveSlot = atoi(fileName + strlen(fileName) - 3);
+
+		if (saveSlot == slot) {
+			listSlot = i;
+			break;
+		}
+	}
+
+	g_system->getSavefileManager()->removeSavefile(Tinsel::ListEntry(listSlot, Tinsel::LE_NAME));
+	Tinsel::setNeedLoad();
+	Tinsel::getList(g_system->getSavefileManager(), target);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(TINSEL)
+	REGISTER_PLUGIN_DYNAMIC(TINSEL, PLUGIN_TYPE_ENGINE, TinselMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TINSEL, PLUGIN_TYPE_ENGINE, TinselMetaEngineConnect);
+#endif
+
+namespace Tinsel {
+
+Common::Error TinselEngine::loadGameState(int slot) {
+	// FIXME: Hopefully this is only used when loading games via
+	// the launcher, since we do a hacky savegame slot to savelist
+	// entry mapping here.
+	//
+	// You might wonder why is needed and here is the answer:
+	// The save/load dialog of the GMM operates with the physical
+	// savegame slots, while Tinsel internally uses entry numbers in
+	// a savelist (which is sorted latest to first). Now to allow
+	// proper loading of (especially Discworld2) saves we need to
+	// get a savelist entry number instead of the physical slot.
+	//
+	// There are different possible solutions:
+	//
+	// One way to fix this would be to pass the filename instead of
+	// the savelist entry number to RestoreGame, though it could make
+	// problems how DW2 handles CD switches. Normally DW2 would pass
+	// '-2' as slot when it changes CDs.
+	//
+	// Another way would be to convert all of Tinsel to use physical
+	// slot numbers instead of savelist entry numbers for loading.
+	// This would also allow '-2' as slot for CD changes without
+	// any major hackery.
+
+	int listSlot = -1;
+	const int numStates = Tinsel::getList();
+	for (int i = 0; i < numStates; ++i) {
+		const char *fileName = Tinsel::ListEntry(i, Tinsel::LE_NAME);
+		const int saveSlot = atoi(fileName + strlen(fileName) - 3);
+
+		if (saveSlot == slot) {
+			listSlot = i;
+			break;
+		}
+	}
+
+	if (listSlot == -1)
+		return Common::kUnknownError;	// TODO: proper error code
+
+	RestoreGame(listSlot);
+	return Common::kNoError;	// TODO: return success/failure
+}
+
+#if 0
+Common::Error TinselEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
+	Common::String saveName = _vm->getSavegameFilename((int16)(slot + 1));
+	char saveDesc[SG_DESC_LEN];
+	Common::strlcpy(saveDesc, desc, SG_DESC_LEN);
+	SaveGame((char *)saveName.c_str(), saveDesc);
+	ProcessSRQueue();			// This shouldn't be needed, but for some reason it is...
+	return Common::kNoError;	// TODO: return success/failure
+}
+#endif
+
+bool TinselEngine::canLoadGameStateCurrently() { return !_bmv->MoviePlaying(); }
+
+#if 0
+bool TinselEngine::canSaveGameStateCurrently() { return isCursorShown(); }
+#endif
+
+} // End of namespace Tinsel
diff --git a/engines/tinsel/module.mk b/engines/tinsel/module.mk
index 3485bac74b..1a76fd192d 100644
--- a/engines/tinsel/module.mk
+++ b/engines/tinsel/module.mk
@@ -11,7 +11,6 @@ MODULE_OBJS := \
 	config.o \
 	cursor.o \
 	debugger.o \
-	detection.o \
 	dialogs.o \
 	drives.o \
 	effect.o \
@@ -22,6 +21,7 @@ MODULE_OBJS := \
 	handle.o \
 	heapmem.o \
 	mareels.o \
+	metaengine.o \
 	move.o \
 	multiobj.o \
 	music.o \
@@ -54,3 +54,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tinsel/tinsel.h b/engines/tinsel/tinsel.h
index b73c779afb..ad529d15ef 100644
--- a/engines/tinsel/tinsel.h
+++ b/engines/tinsel/tinsel.h
@@ -38,6 +38,7 @@
 #include "tinsel/graphics.h"
 #include "tinsel/sound.h"
 #include "tinsel/dw.h"
+#include "tinsel/detection_enums.h"
 
 /**
  * This is the namespace of the Tinsel engine.
@@ -63,41 +64,6 @@ class Cursor;
 
 typedef Common::List<Common::Rect> RectList;
 
-enum TinselGameID {
-	GID_DW1 = 0,
-	GID_DW2 = 1
-};
-
-enum TinselGameFeatures {
-	GF_SCNFILES = 1 << 0,
-	GF_ENHANCED_AUDIO_SUPPORT = 1 << 1,
-	GF_ALT_MIDI = 1 << 2,		// Alternate sequence in midi.dat file
-
-	// The GF_USE_?FLAGS values specify how many country flags are displayed
-	// in the subtitles options dialog.
-	// None of these defined -> 1 language, in ENGLISH.TXT
-	GF_USE_3FLAGS = 1 << 3,	// French, German, Spanish
-	GF_USE_4FLAGS = 1 << 4,	// French, German, Spanish, Italian
-	GF_USE_5FLAGS = 1 << 5	// All 5 flags
-};
-
-/**
- * The following is the ScummVM definitions of the various Tinsel versions:
- * TINSEL_V0 - This was an early engine version that was only used in the Discworld 1
- *			demo.
- * TINSEL_V1 - This was the engine version used by Discworld 1. Note that there were two
- *			major releases: an earlier version that used *.gra files, and a later one that
- *			used *.scn files, and contained certain script and engine bugfixes. In ScummVM,
- *			we treat both releases as 'Tinsel 1', since the engine fixes from the later
- *			version work equally well the earlier version data.
- * TINSEL_V2 - This is the engine used for the Discworld 2 game.
- */
-enum TinselEngineVersion {
-	TINSEL_V0 = 0,
-	TINSEL_V1 = 1,
-	TINSEL_V2 = 2
-};
-
 enum {
 	kTinselDebugAnimations = 1 << 0,
 	kTinselDebugActions = 1 << 1,


Commit: dae6013369be1fabae3d78b087a9063dbce8157b
    https://github.com/scummvm/scummvm/commit/dae6013369be1fabae3d78b087a9063dbce8157b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TITANIC: Split detection features & adapt to new plugins.

Changed paths:
  A engines/titanic/detection.h
  A engines/titanic/metaengine.cpp
    configure
    engines/titanic/detection.cpp
    engines/titanic/module.mk


diff --git a/configure b/configure
index b68a69e01c..3b7881fb4b 100755
--- a/configure
+++ b/configure
@@ -6167,7 +6167,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
-								  "TEENAGENT" "TESTBED" "TINSEL")
+								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/titanic/detection.cpp b/engines/titanic/detection.cpp
index 66cd05f0cf..c3aaf829b2 100644
--- a/engines/titanic/detection.cpp
+++ b/engines/titanic/detection.cpp
@@ -20,33 +20,12 @@
  *
  */
 
-#include "titanic/core/project_item.h"
-#include "titanic/events.h"
-#include "titanic/support/simple_file.h"
-#include "titanic/titanic.h"
 #include "base/plugins.h"
-#include "common/savefile.h"
 #include "common/str-array.h"
 #include "common/memstream.h"
 #include "engines/advancedDetector.h"
-#include "common/system.h"
-#include "graphics/surface.h"
 
-namespace Titanic {
-
-struct TitanicGameDescription {
-	ADGameDescription desc;
-};
-
-uint32 TitanicEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language TitanicEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-} // End of namespace Titanic
+#include "titanic/detection.h"
 
 static const PlainGameDescriptor TitanicGames[] = {
 	{"titanic", "Starship Titanic"},
@@ -72,119 +51,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Starship Titanic (C) The Digital Village";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool TitanicMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Titanic::TitanicEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool TitanicMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Titanic::TitanicGameDescription *gd = (const Titanic::TitanicGameDescription *)desc;
-	*engine = new Titanic::TitanicEngine(syst, gd);
-
-	return gd != 0;
-}
-
-SaveStateList TitanicMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.0##", target);
-	Titanic::TitanicSavegameHeader header;
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		const char *ext = strrchr(file->c_str(), '.');
-		int slot = ext ? atoi(ext + 1) : -1;
-
-		if (slot >= 0 && slot <= MAX_SAVES) {
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-			if (in) {
-				Titanic::CompressedFile cf;
-				cf.open(in);
-
-				if (Titanic::CProjectItem::readSavegameHeader(&cf, header))
-					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
-
-				cf.close();
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int TitanicMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVES;
-}
-
-void TitanicMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor TitanicMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
-
-	if (f) {
-		Titanic::CompressedFile file;
-		file.open(f);
-
-		Titanic::TitanicSavegameHeader header;
-		if (!Titanic::CProjectItem::readSavegameHeader(&file, header, false)) {
-			file.close();
-			return SaveStateDescriptor();
-		}
-
-		file.close();
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header._saveName);
-
-		if (header._version) {
-			desc.setThumbnail(header._thumbnail);
-			desc.setSaveDate(header._year, header._month, header._day);
-			desc.setSaveTime(header._hour, header._minute);
-			desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
-		}
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-
-#if PLUGIN_ENABLED_DYNAMIC(TITANIC)
-	REGISTER_PLUGIN_DYNAMIC(TITANIC, PLUGIN_TYPE_ENGINE, TitanicMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TITANIC, PLUGIN_TYPE_ENGINE, TitanicMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(TITANIC_DETECTION, PLUGIN_TYPE_METAENGINE, TitanicMetaEngine);
diff --git a/engines/titanic/detection.h b/engines/titanic/detection.h
new file mode 100644
index 0000000000..2febb57538
--- /dev/null
+++ b/engines/titanic/detection.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Titanic {
+
+struct TitanicGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Titanic
diff --git a/engines/titanic/metaengine.cpp b/engines/titanic/metaengine.cpp
new file mode 100644
index 0000000000..1883f04e2c
--- /dev/null
+++ b/engines/titanic/metaengine.cpp
@@ -0,0 +1,168 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "titanic/core/project_item.h"
+#include "titanic/events.h"
+#include "titanic/support/simple_file.h"
+#include "titanic/titanic.h"
+#include "base/plugins.h"
+#include "common/savefile.h"
+#include "common/str-array.h"
+#include "common/memstream.h"
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+#include "graphics/surface.h"
+#include "titanic/detection.h"
+
+namespace Titanic {
+
+uint32 TitanicEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language TitanicEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+} // End of namespace Titanic
+
+class TitanicMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "titanic";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool TitanicMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Titanic::TitanicEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool TitanicMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Titanic::TitanicGameDescription *gd = (const Titanic::TitanicGameDescription *)desc;
+	*engine = new Titanic::TitanicEngine(syst, gd);
+
+	return gd != 0;
+}
+
+SaveStateList TitanicMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.0##", target);
+	Titanic::TitanicSavegameHeader header;
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		const char *ext = strrchr(file->c_str(), '.');
+		int slot = ext ? atoi(ext + 1) : -1;
+
+		if (slot >= 0 && slot <= MAX_SAVES) {
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+			if (in) {
+				Titanic::CompressedFile cf;
+				cf.open(in);
+
+				if (Titanic::CProjectItem::readSavegameHeader(&cf, header))
+					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
+
+				cf.close();
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int TitanicMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVES;
+}
+
+void TitanicMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor TitanicMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
+
+	if (f) {
+		Titanic::CompressedFile file;
+		file.open(f);
+
+		Titanic::TitanicSavegameHeader header;
+		if (!Titanic::CProjectItem::readSavegameHeader(&file, header, false)) {
+			file.close();
+			return SaveStateDescriptor();
+		}
+
+		file.close();
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header._saveName);
+
+		if (header._version) {
+			desc.setThumbnail(header._thumbnail);
+			desc.setSaveDate(header._year, header._month, header._day);
+			desc.setSaveTime(header._hour, header._minute);
+			desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
+		}
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(TITANIC)
+	REGISTER_PLUGIN_DYNAMIC(TITANIC, PLUGIN_TYPE_ENGINE, TitanicMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TITANIC, PLUGIN_TYPE_ENGINE, TitanicMetaEngineConnect);
+#endif
diff --git a/engines/titanic/module.mk b/engines/titanic/module.mk
index dc7473da10..92cb2a6cd6 100644
--- a/engines/titanic/module.mk
+++ b/engines/titanic/module.mk
@@ -3,7 +3,6 @@ MODULE := engines/titanic
 MODULE_OBJS := \
 	continue_save_dialog.o \
 	debugger.o \
-	detection.o \
 	events.o \
 	game_location.o \
 	game_manager.o \
@@ -325,6 +324,7 @@ MODULE_OBJS := \
 	messages/messages.o \
 	messages/mouse_messages.o \
 	messages/service_elevator_door.o \
+	metaengine.o \
 	moves/call_pellerator.o \
 	moves/enter_bomb_room.o \
 	moves/enter_bridge.o \
@@ -531,3 +531,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 2360e21dd18facbbbe0afbf986ec93f54659d90f
    https://github.com/scummvm/scummvm/commit/2360e21dd18facbbbe0afbf986ec93f54659d90f
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TOLTECS: Split detection features & adapt to new plugins.

Changed paths:
  A engines/toltecs/detection.h
  A engines/toltecs/metaengine.cpp
    configure
    engines/toltecs/detection.cpp
    engines/toltecs/module.mk


diff --git a/configure b/configure
index 3b7881fb4b..07aa665b90 100755
--- a/configure
+++ b/configure
@@ -6167,7 +6167,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
-								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC")
+								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/toltecs/detection.cpp b/engines/toltecs/detection.cpp
index 93841619b1..201d6aba02 100644
--- a/engines/toltecs/detection.cpp
+++ b/engines/toltecs/detection.cpp
@@ -30,24 +30,9 @@
 #include "common/system.h"
 
 #include "toltecs/toltecs.h"
+#include "toltecs/detection.h"
 
 
-namespace Toltecs {
-
-struct ToltecsGameDescription {
-	ADGameDescription desc;
-};
-
-uint32 ToltecsEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language ToltecsEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-}
-
 static const PlainGameDescriptor toltecsGames[] = {
 	{"toltecs", "3 Skulls of the Toltecs"},
 	{0, 0}
@@ -248,146 +233,13 @@ public:
 		return "3 Skulls of the Toltecs (C) Revistronic 1996";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool ToltecsMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Toltecs::ToltecsEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool ToltecsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Toltecs::ToltecsGameDescription *gd = (const Toltecs::ToltecsGameDescription *)desc;
-	if (gd) {
-		*engine = new Toltecs::ToltecsEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
 const ExtraGuiOptions ToltecsMetaEngine::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	options.push_back(toltecsExtraGuiOption);
 	return options;
 }
 
-SaveStateList ToltecsMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Toltecs::ToltecsEngine::SaveHeader header;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	Common::StringArray filenames;
-	filenames = saveFileMan->listSavefiles(pattern.c_str());
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
-			if (in) {
-				if (Toltecs::ToltecsEngine::readSaveHeader(in, header) == Toltecs::ToltecsEngine::kRSHENoError) {
-					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
-				}
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int ToltecsMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-void ToltecsMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::String filename = Toltecs::ToltecsEngine::getSavegameFilename(target, slot);
-
-	saveFileMan->removeSavefile(filename.c_str());
-
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-	filenames = saveFileMan->listSavefiles(pattern.c_str());
-	Common::sort(filenames.begin(), filenames.end());	// Sort (hopefully ensuring we are sorted numerically..)
-
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		// Rename every slot greater than the deleted slot,
-		if (slotNum > slot) {
-			saveFileMan->renameSavefile(file->c_str(), filename.c_str());
-			filename = Toltecs::ToltecsEngine::getSavegameFilename(target, ++slot);
-		}
-	}
-}
-
-SaveStateDescriptor ToltecsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Toltecs::ToltecsEngine::getSavegameFilename(target, slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
-
-	if (in) {
-		Toltecs::ToltecsEngine::SaveHeader header;
-		Toltecs::ToltecsEngine::kReadSaveHeaderError error;
-
-		error = Toltecs::ToltecsEngine::readSaveHeader(in, header, false);
-		delete in;
-
-		if (error == Toltecs::ToltecsEngine::kRSHENoError) {
-			SaveStateDescriptor desc(slot, header.description);
-
-			desc.setThumbnail(header.thumbnail);
-
-			if (header.version > 0) {
-				int day = (header.saveDate >> 24) & 0xFF;
-				int month = (header.saveDate >> 16) & 0xFF;
-				int year = header.saveDate & 0xFFFF;
-
-				desc.setSaveDate(year, month, day);
-
-				int hour = (header.saveTime >> 16) & 0xFF;
-				int minutes = (header.saveTime >> 8) & 0xFF;
-
-				desc.setSaveTime(hour, minutes);
-
-				desc.setPlayTime(header.playTime * 1000);
-			}
-
-			return desc;
-		}
-	}
-
-	return SaveStateDescriptor();
-} // End of namespace Toltecs
-
-#if PLUGIN_ENABLED_DYNAMIC(TOLTECS)
-	REGISTER_PLUGIN_DYNAMIC(TOLTECS, PLUGIN_TYPE_ENGINE, ToltecsMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TOLTECS, PLUGIN_TYPE_ENGINE, ToltecsMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(TOLTECS_DETECTION, PLUGIN_TYPE_METAENGINE, ToltecsMetaEngine);
diff --git a/engines/toltecs/detection.h b/engines/toltecs/detection.h
new file mode 100644
index 0000000000..982a997d4c
--- /dev/null
+++ b/engines/toltecs/detection.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Toltecs {
+
+struct ToltecsGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Toltecs
diff --git a/engines/toltecs/metaengine.cpp b/engines/toltecs/metaengine.cpp
new file mode 100644
index 0000000000..e3dda22ed2
--- /dev/null
+++ b/engines/toltecs/metaengine.cpp
@@ -0,0 +1,190 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+
+#include "common/translation.h"
+#include "common/savefile.h"
+#include "common/str-array.h"
+#include "common/system.h"
+
+#include "toltecs/toltecs.h"
+#include "toltecs/detection.h"
+
+namespace Toltecs {
+
+uint32 ToltecsEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language ToltecsEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+} // End of namespace Toltecs
+
+class ToltecsMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "toltecs";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+    SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool ToltecsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Toltecs::ToltecsEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool ToltecsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Toltecs::ToltecsGameDescription *gd = (const Toltecs::ToltecsGameDescription *)desc;
+	if (gd) {
+		*engine = new Toltecs::ToltecsEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList ToltecsMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Toltecs::ToltecsEngine::SaveHeader header;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	Common::StringArray filenames;
+	filenames = saveFileMan->listSavefiles(pattern.c_str());
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
+			if (in) {
+				if (Toltecs::ToltecsEngine::readSaveHeader(in, header) == Toltecs::ToltecsEngine::kRSHENoError) {
+					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
+				}
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int ToltecsMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+void ToltecsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::String filename = Toltecs::ToltecsEngine::getSavegameFilename(target, slot);
+
+	saveFileMan->removeSavefile(filename.c_str());
+
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+	filenames = saveFileMan->listSavefiles(pattern.c_str());
+	Common::sort(filenames.begin(), filenames.end());	// Sort (hopefully ensuring we are sorted numerically..)
+
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		// Rename every slot greater than the deleted slot,
+		if (slotNum > slot) {
+			saveFileMan->renameSavefile(file->c_str(), filename.c_str());
+			filename = Toltecs::ToltecsEngine::getSavegameFilename(target, ++slot);
+		}
+	}
+}
+
+SaveStateDescriptor ToltecsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Toltecs::ToltecsEngine::getSavegameFilename(target, slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
+
+	if (in) {
+		Toltecs::ToltecsEngine::SaveHeader header;
+		Toltecs::ToltecsEngine::kReadSaveHeaderError error;
+
+		error = Toltecs::ToltecsEngine::readSaveHeader(in, header, false);
+		delete in;
+
+		if (error == Toltecs::ToltecsEngine::kRSHENoError) {
+			SaveStateDescriptor desc(slot, header.description);
+
+			desc.setThumbnail(header.thumbnail);
+
+			if (header.version > 0) {
+				int day = (header.saveDate >> 24) & 0xFF;
+				int month = (header.saveDate >> 16) & 0xFF;
+				int year = header.saveDate & 0xFFFF;
+
+				desc.setSaveDate(year, month, day);
+
+				int hour = (header.saveTime >> 16) & 0xFF;
+				int minutes = (header.saveTime >> 8) & 0xFF;
+
+				desc.setSaveTime(hour, minutes);
+
+				desc.setPlayTime(header.playTime * 1000);
+			}
+
+			return desc;
+		}
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(TOLTECS)
+	REGISTER_PLUGIN_DYNAMIC(TOLTECS, PLUGIN_TYPE_ENGINE, ToltecsMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TOLTECS, PLUGIN_TYPE_ENGINE, ToltecsMetaEngineConnect);
+#endif
+
diff --git a/engines/toltecs/module.mk b/engines/toltecs/module.mk
index 0de1eef733..146de8caa6 100644
--- a/engines/toltecs/module.mk
+++ b/engines/toltecs/module.mk
@@ -3,8 +3,8 @@ MODULE := engines/toltecs
 MODULE_OBJS = \
 	animation.o \
 	console.o \
-	detection.o \
 	menu.o \
+	metaengine.o \
 	microtiles.o \
 	movie.o \
 	music.o \
@@ -27,3 +27,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 02c71c91f5132206d9c6660b32ddb78080875ed1
    https://github.com/scummvm/scummvm/commit/02c71c91f5132206d9c6660b32ddb78080875ed1
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TONY: Split detection features & adapt to new plugins.

Changed paths:
  A engines/tony/detection.h
  A engines/tony/metaengine.cpp
    configure
    engines/tony/detection.cpp
    engines/tony/module.mk


diff --git a/configure b/configure
index 07aa665b90..3e0c14ac83 100755
--- a/configure
+++ b/configure
@@ -6167,7 +6167,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
-								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS")
+								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/tony/detection.cpp b/engines/tony/detection.cpp
index a694035a86..d02ddea22c 100644
--- a/engines/tony/detection.cpp
+++ b/engines/tony/detection.cpp
@@ -22,41 +22,9 @@
 
 #include "base/plugins.h"
 
-#include "common/memstream.h"
 #include "engines/advancedDetector.h"
-#include "common/system.h"
-#include "graphics/surface.h"
 
-#include "tony/tony.h"
-#include "tony/game.h"
-
-namespace Tony {
-
-enum {
-	GF_COMPRESSED = (1 << 0)
-};
-
-struct TonyGameDescription {
-	ADGameDescription desc;
-};
-
-uint32 TonyEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language TonyEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-bool TonyEngine::getIsDemo() const {
-	return _gameDescription->desc.flags & ADGF_DEMO;
-}
-
-bool TonyEngine::isCompressed() const {
-	return _gameDescription->desc.flags & GF_COMPRESSED;
-}
-
-} // End of namespace Tony
+#include "tony/detection.h"
 
 static const PlainGameDescriptor tonyGames[] = {
 	{"tony", "Tony Tough and the Night of Roasted Moths"},
@@ -81,107 +49,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Tony Tough and the Night of Roasted Moths (C) Protonic Interactive";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool TonyMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail);
-}
-
-bool Tony::TonyEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool TonyMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Tony::TonyGameDescription *gd = (const Tony::TonyGameDescription *)desc;
-	if (gd) {
-		*engine = new Tony::TonyEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList TonyMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = "tony.0##";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 999) {
-			byte thumbnailData[160 * 120 * 2];
-			Common::String saveName;
-			byte difficulty;
-
-			if (Tony::RMOptionScreen::loadThumbnailFromSaveState(slotNum, thumbnailData, saveName, difficulty)) {
-				// Add the save name to the savegame list
-				saveList.push_back(SaveStateDescriptor(slotNum, saveName));
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int TonyMetaEngine::getMaximumSaveSlot() const {
-	return 99;
-}
-
-void TonyMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Tony::TonyEngine::getSaveStateFileName(slot);
-
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor TonyMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String saveName;
-	byte difficulty;
-
-	Graphics::Surface *to = new Graphics::Surface();
-	to->create(160, 120, Graphics::PixelFormat(2, 5, 5, 5, 0, 10, 5, 0, 0));
-
-	if (Tony::RMOptionScreen::loadThumbnailFromSaveState(slot, (byte *)to->getPixels(), saveName, difficulty)) {
-#ifdef SCUMM_BIG_ENDIAN
-		uint16 *pixels = (uint16 *)to->getPixels();
-		for (int i = 0; i < to->w * to->h; ++i)
-			pixels[i] = READ_LE_UINT16(pixels + i);
-#endif
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, saveName);
-		desc.setDeletableFlag(true);
-		desc.setWriteProtectedFlag(false);
-		desc.setThumbnail(to);
-
-		return desc;
-	}
-
-	delete to;
-	return SaveStateDescriptor();
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(TONY)
-	REGISTER_PLUGIN_DYNAMIC(TONY, PLUGIN_TYPE_ENGINE, TonyMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TONY, PLUGIN_TYPE_ENGINE, TonyMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(TONY_DETECTION, PLUGIN_TYPE_METAENGINE, TonyMetaEngine);
diff --git a/engines/tony/detection.h b/engines/tony/detection.h
new file mode 100644
index 0000000000..561bb22590
--- /dev/null
+++ b/engines/tony/detection.h
@@ -0,0 +1,33 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Tony {
+
+enum {
+	GF_COMPRESSED = (1 << 0)
+};
+
+struct TonyGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Tony
diff --git a/engines/tony/metaengine.cpp b/engines/tony/metaengine.cpp
new file mode 100644
index 0000000000..8c2f6949de
--- /dev/null
+++ b/engines/tony/metaengine.cpp
@@ -0,0 +1,163 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "common/memstream.h"
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+#include "graphics/surface.h"
+
+#include "tony/tony.h"
+#include "tony/game.h"
+#include "tony/detection.h"
+
+namespace Tony {
+
+uint32 TonyEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language TonyEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+bool TonyEngine::getIsDemo() const {
+	return _gameDescription->desc.flags & ADGF_DEMO;
+}
+
+bool TonyEngine::isCompressed() const {
+	return _gameDescription->desc.flags & GF_COMPRESSED;
+}
+
+} // End of namespace Tony
+
+class TonyMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "tony";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool TonyMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail);
+}
+
+bool Tony::TonyEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool TonyMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Tony::TonyGameDescription *gd = (const Tony::TonyGameDescription *)desc;
+	if (gd) {
+		*engine = new Tony::TonyEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList TonyMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = "tony.0##";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 999) {
+			byte thumbnailData[160 * 120 * 2];
+			Common::String saveName;
+			byte difficulty;
+
+			if (Tony::RMOptionScreen::loadThumbnailFromSaveState(slotNum, thumbnailData, saveName, difficulty)) {
+				// Add the save name to the savegame list
+				saveList.push_back(SaveStateDescriptor(slotNum, saveName));
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int TonyMetaEngineConnect::getMaximumSaveSlot() const {
+	return 99;
+}
+
+void TonyMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Tony::TonyEngine::getSaveStateFileName(slot);
+
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor TonyMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String saveName;
+	byte difficulty;
+
+	Graphics::Surface *to = new Graphics::Surface();
+	to->create(160, 120, Graphics::PixelFormat(2, 5, 5, 5, 0, 10, 5, 0, 0));
+
+	if (Tony::RMOptionScreen::loadThumbnailFromSaveState(slot, (byte *)to->getPixels(), saveName, difficulty)) {
+#ifdef SCUMM_BIG_ENDIAN
+		uint16 *pixels = (uint16 *)to->getPixels();
+		for (int i = 0; i < to->w * to->h; ++i)
+			pixels[i] = READ_LE_UINT16(pixels + i);
+#endif
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, saveName);
+		desc.setDeletableFlag(true);
+		desc.setWriteProtectedFlag(false);
+		desc.setThumbnail(to);
+
+		return desc;
+	}
+
+	delete to;
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(TONY)
+	REGISTER_PLUGIN_DYNAMIC(TONY, PLUGIN_TYPE_ENGINE, TonyMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TONY, PLUGIN_TYPE_ENGINE, TonyMetaEngineConnect);
+#endif
diff --git a/engines/tony/module.mk b/engines/tony/module.mk
index d66cf6f065..f9f2b1c019 100644
--- a/engines/tony/module.mk
+++ b/engines/tony/module.mk
@@ -3,7 +3,6 @@ MODULE := engines/tony
 MODULE_OBJS := \
 	custom.o \
 	debugger.o \
-	detection.o \
 	font.o \
 	game.o \
 	gfxcore.o \
@@ -12,6 +11,7 @@ MODULE_OBJS := \
 	input.o \
 	inventory.o \
 	loc.o \
+	metaengine.o \
 	sound.o \
 	tony.o \
 	tonychar.o \
@@ -31,3 +31,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: cf5581f27f73fd13b43b620ac3629c5e533d73e1
    https://github.com/scummvm/scummvm/commit/cf5581f27f73fd13b43b620ac3629c5e533d73e1
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TOON: Split detection features & adapt to new plugins.

Changed paths:
  A engines/toon/metaengine.cpp
    configure
    engines/toon/detection.cpp
    engines/toon/module.mk


diff --git a/configure b/configure
index 3e0c14ac83..bc377ec745 100755
--- a/configure
+++ b/configure
@@ -6167,7 +6167,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
-								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY")
+								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/toon/detection.cpp b/engines/toon/detection.cpp
index 9ad65b735c..be3974cfdb 100644
--- a/engines/toon/detection.cpp
+++ b/engines/toon/detection.cpp
@@ -20,13 +20,9 @@
  *
  */
 
-#include "common/config-manager.h"
 #include "engines/advancedDetector.h"
-#include "common/savefile.h"
-#include "common/system.h"
+
 #include "base/plugins.h"
-#include "graphics/thumbnail.h"
-#include "toon/toon.h"
 
 static const PlainGameDescriptor toonGames[] = {
 	{ "toon", "Toonstruck" },
@@ -156,138 +152,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Toonstruck (C) 1996 Virgin Interactive";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool ToonMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-	    (f == kSupportsLoadingDuringStartup) ||
-	    (f == kSupportsDeleteSave) ||
-	    (f == kSavesSupportMetaInfo) ||
-	    (f == kSavesSupportThumbnail) ||
-	    (f == kSavesSupportCreationDate) ||
-	    (f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-void ToonMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-int ToonMetaEngine::getMaximumSaveSlot() const { return MAX_SAVE_SLOT; }
-
-SaveStateList ToonMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(filename->c_str() + filename->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= MAX_SAVE_SLOT) {
-			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
-			if (file) {
-				int32 version = file->readSint32BE();
-				if ( (version < 4) || (version > TOON_SAVEGAME_VERSION) ) {
-					delete file;
-					continue;
-				}
-
-				// read name
-				uint16 nameSize = file->readUint16BE();
-				if (nameSize >= 255) {
-					delete file;
-					continue;
-				}
-				char name[256];
-				file->read(name, nameSize);
-				name[nameSize] = 0;
-
-				saveList.push_back(SaveStateDescriptor(slotNum, name));
-				delete file;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor ToonMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (file) {
-
-		int32 version = file->readSint32BE();
-		if ( (version < 4) || (version > TOON_SAVEGAME_VERSION) ) {
-			delete file;
-			return SaveStateDescriptor();
-		}
-
-		uint32 saveNameLength = file->readUint16BE();
-		char saveName[256];
-		file->read(saveName, saveNameLength);
-		saveName[saveNameLength] = 0;
-
-		SaveStateDescriptor desc(slot, saveName);
-
-		Graphics::Surface *thumbnail = nullptr;
-		if (!Graphics::loadThumbnail(*file, thumbnail, false)) {
-			delete file;
-			return SaveStateDescriptor();
-		}
-		desc.setThumbnail(thumbnail);
-
-		uint32 saveDate = file->readUint32BE();
-		uint16 saveTime = file->readUint16BE();
-
-		int day = (saveDate >> 24) & 0xFF;
-		int month = (saveDate >> 16) & 0xFF;
-		int year = saveDate & 0xFFFF;
-
-		desc.setSaveDate(year, month, day);
-
-		int hour = (saveTime >> 8) & 0xFF;
-		int minutes = saveTime & 0xFF;
-
-		desc.setSaveTime(hour, minutes);
-
-		if (version >= 5) {
-			uint32 playTimeMsec = file->readUint32BE();
-			desc.setPlayTime(playTimeMsec);
-		}
-
-		delete file;
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-bool ToonMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Toon::ToonEngine(syst, desc);
-	}
-	return desc != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(TOON)
-	REGISTER_PLUGIN_DYNAMIC(TOON, PLUGIN_TYPE_ENGINE, ToonMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TOON, PLUGIN_TYPE_ENGINE, ToonMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(TOON_DETECTION, PLUGIN_TYPE_METAENGINE, ToonMetaEngine);
diff --git a/engines/toon/metaengine.cpp b/engines/toon/metaengine.cpp
new file mode 100644
index 0000000000..f75bad337e
--- /dev/null
+++ b/engines/toon/metaengine.cpp
@@ -0,0 +1,171 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/config-manager.h"
+#include "engines/advancedDetector.h"
+#include "common/savefile.h"
+#include "common/system.h"
+#include "base/plugins.h"
+#include "graphics/thumbnail.h"
+#include "toon/toon.h"
+
+class ToonMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "toon";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool ToonMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+	    (f == kSupportsLoadingDuringStartup) ||
+	    (f == kSupportsDeleteSave) ||
+	    (f == kSavesSupportMetaInfo) ||
+	    (f == kSavesSupportThumbnail) ||
+	    (f == kSavesSupportCreationDate) ||
+	    (f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+void ToonMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+int ToonMetaEngineConnect::getMaximumSaveSlot() const { return MAX_SAVE_SLOT; }
+
+SaveStateList ToonMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(filename->c_str() + filename->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= MAX_SAVE_SLOT) {
+			Common::InSaveFile *file = saveFileMan->openForLoading(*filename);
+			if (file) {
+				int32 version = file->readSint32BE();
+				if ( (version < 4) || (version > TOON_SAVEGAME_VERSION) ) {
+					delete file;
+					continue;
+				}
+
+				// read name
+				uint16 nameSize = file->readUint16BE();
+				if (nameSize >= 255) {
+					delete file;
+					continue;
+				}
+				char name[256];
+				file->read(name, nameSize);
+				name[nameSize] = 0;
+
+				saveList.push_back(SaveStateDescriptor(slotNum, name));
+				delete file;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor ToonMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (file) {
+
+		int32 version = file->readSint32BE();
+		if ( (version < 4) || (version > TOON_SAVEGAME_VERSION) ) {
+			delete file;
+			return SaveStateDescriptor();
+		}
+
+		uint32 saveNameLength = file->readUint16BE();
+		char saveName[256];
+		file->read(saveName, saveNameLength);
+		saveName[saveNameLength] = 0;
+
+		SaveStateDescriptor desc(slot, saveName);
+
+		Graphics::Surface *thumbnail = nullptr;
+		if (!Graphics::loadThumbnail(*file, thumbnail, false)) {
+			delete file;
+			return SaveStateDescriptor();
+		}
+		desc.setThumbnail(thumbnail);
+
+		uint32 saveDate = file->readUint32BE();
+		uint16 saveTime = file->readUint16BE();
+
+		int day = (saveDate >> 24) & 0xFF;
+		int month = (saveDate >> 16) & 0xFF;
+		int year = saveDate & 0xFFFF;
+
+		desc.setSaveDate(year, month, day);
+
+		int hour = (saveTime >> 8) & 0xFF;
+		int minutes = saveTime & 0xFF;
+
+		desc.setSaveTime(hour, minutes);
+
+		if (version >= 5) {
+			uint32 playTimeMsec = file->readUint32BE();
+			desc.setPlayTime(playTimeMsec);
+		}
+
+		delete file;
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+bool ToonMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Toon::ToonEngine(syst, desc);
+	}
+	return desc != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(TOON)
+	REGISTER_PLUGIN_DYNAMIC(TOON, PLUGIN_TYPE_ENGINE, ToonMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TOON, PLUGIN_TYPE_ENGINE, ToonMetaEngineConnect);
+#endif
\ No newline at end of file
diff --git a/engines/toon/module.mk b/engines/toon/module.mk
index 6387e62f46..c07fceae83 100644
--- a/engines/toon/module.mk
+++ b/engines/toon/module.mk
@@ -6,11 +6,11 @@ MODULE_OBJS := \
 	character.o \
 	console.o \
 	conversation.o \
-	detection.o \
 	drew.o \
 	flux.o \
 	font.o \
 	hotspot.o \
+	metaengine.o \
 	movie.o \
 	path.o \
 	picture.o \
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: d69a9b519fa4d10fa3a40675aed8e561d583dbf8
    https://github.com/scummvm/scummvm/commit/d69a9b519fa4d10fa3a40675aed8e561d583dbf8
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TOUCHE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/touche/metaengine.cpp
    configure
    engines/touche/detection.cpp
    engines/touche/module.mk


diff --git a/configure b/configure
index bc377ec745..46f99c8857 100755
--- a/configure
+++ b/configure
@@ -6167,7 +6167,8 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
-								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON")
+								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
+								  "TOUCHE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/touche/detection.cpp b/engines/touche/detection.cpp
index 584be68744..33605d33ee 100644
--- a/engines/touche/detection.cpp
+++ b/engines/touche/detection.cpp
@@ -20,15 +20,10 @@
  *
  */
 
-#include "common/config-manager.h"
 #include "engines/advancedDetector.h"
-#include "common/savefile.h"
-#include "common/system.h"
 
 #include "base/plugins.h"
 
-#include "touche/touche.h"
-
 static const PlainGameDescriptor toucheGames[] = {
 	{ "touche", "Touche: The Adventures of the Fifth Musketeer" },
 	{ 0, 0 }
@@ -147,76 +142,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Touche: The Adventures of the Fifth Musketeer (C) Clipper Software";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool ToucheMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave);
-}
-
-bool Touche::ToucheEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime) ||
-		(f == kSupportsSubtitleOptions);
-}
-
-bool ToucheMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Touche::ToucheEngine(syst, desc->language);
-	}
-	return desc != 0;
-}
-
-SaveStateList ToucheMetaEngine::listSaves(const char *target) const {
-	Common::String pattern = Touche::generateGameStateFileName(target, 0, true);
-	Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
-	bool slotsTable[Touche::kMaxSaveStates];
-	memset(slotsTable, 0, sizeof(slotsTable));
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		int slot = Touche::getGameStateFileSlot(file->c_str());
-		if (slot >= 0 && slot < Touche::kMaxSaveStates) {
-			slotsTable[slot] = true;
-		}
-	}
-	for (int slot = 0; slot < Touche::kMaxSaveStates; ++slot) {
-		if (slotsTable[slot]) {
-			Common::String file = Touche::generateGameStateFileName(target, slot);
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(file);
-			if (in) {
-				char description[64];
-				Touche::readGameStateDescription(in, description, sizeof(description) - 1);
-				if (description[0]) {
-					saveList.push_back(SaveStateDescriptor(slot, description));
-				}
-				delete in;
-			}
-		}
-	}
-	return saveList;
-}
-
-int ToucheMetaEngine::getMaximumSaveSlot() const {
-	return Touche::kMaxSaveStates - 1;
-}
-
-void ToucheMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Touche::generateGameStateFileName(target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(TOUCHE)
-	REGISTER_PLUGIN_DYNAMIC(TOUCHE, PLUGIN_TYPE_ENGINE, ToucheMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TOUCHE, PLUGIN_TYPE_ENGINE, ToucheMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(TOUCHE_DETECTION, PLUGIN_TYPE_METAENGINE, ToucheMetaEngine);
diff --git a/engines/touche/metaengine.cpp b/engines/touche/metaengine.cpp
new file mode 100644
index 0000000000..5d6e95e3f7
--- /dev/null
+++ b/engines/touche/metaengine.cpp
@@ -0,0 +1,109 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/config-manager.h"
+#include "engines/advancedDetector.h"
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "base/plugins.h"
+
+#include "touche/touche.h"
+
+class ToucheMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "touche";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool ToucheMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave);
+}
+
+bool Touche::ToucheEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime) ||
+		(f == kSupportsSubtitleOptions);
+}
+
+bool ToucheMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Touche::ToucheEngine(syst, desc->language);
+	}
+	return desc != 0;
+}
+
+SaveStateList ToucheMetaEngineConnect::listSaves(const char *target) const {
+	Common::String pattern = Touche::generateGameStateFileName(target, 0, true);
+	Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
+	bool slotsTable[Touche::kMaxSaveStates];
+	memset(slotsTable, 0, sizeof(slotsTable));
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		int slot = Touche::getGameStateFileSlot(file->c_str());
+		if (slot >= 0 && slot < Touche::kMaxSaveStates) {
+			slotsTable[slot] = true;
+		}
+	}
+	for (int slot = 0; slot < Touche::kMaxSaveStates; ++slot) {
+		if (slotsTable[slot]) {
+			Common::String file = Touche::generateGameStateFileName(target, slot);
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(file);
+			if (in) {
+				char description[64];
+				Touche::readGameStateDescription(in, description, sizeof(description) - 1);
+				if (description[0]) {
+					saveList.push_back(SaveStateDescriptor(slot, description));
+				}
+				delete in;
+			}
+		}
+	}
+	return saveList;
+}
+
+int ToucheMetaEngineConnect::getMaximumSaveSlot() const {
+	return Touche::kMaxSaveStates - 1;
+}
+
+void ToucheMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Touche::generateGameStateFileName(target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(TOUCHE)
+	REGISTER_PLUGIN_DYNAMIC(TOUCHE, PLUGIN_TYPE_ENGINE, ToucheMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TOUCHE, PLUGIN_TYPE_ENGINE, ToucheMetaEngineConnect);
+#endif
diff --git a/engines/touche/module.mk b/engines/touche/module.mk
index 710b3169de..7bedba30dc 100644
--- a/engines/touche/module.mk
+++ b/engines/touche/module.mk
@@ -2,9 +2,9 @@ MODULE := engines/touche
 
 MODULE_OBJS := \
 	console.o \
-	detection.o \
 	graphics.o \
 	menu.o \
+	metaengine.o \
 	midi.o \
 	opcodes.o \
 	resource.o \
@@ -19,3 +19,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: d001efc53422103ab2a6a53b6cf40688367cc6de
    https://github.com/scummvm/scummvm/commit/d001efc53422103ab2a6a53b6cf40688367cc6de
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TSAGE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/tsage/detection.h
  A engines/tsage/detection_enums.h
  A engines/tsage/metaengine.cpp
    configure
    engines/tsage/detection.cpp
    engines/tsage/module.mk
    engines/tsage/tsage.h


diff --git a/configure b/configure
index 46f99c8857..e4b139dead 100755
--- a/configure
+++ b/configure
@@ -6168,7 +6168,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
-								  "TOUCHE")
+								  "TOUCHE" "TSAGE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/tsage/detection.cpp b/engines/tsage/detection.cpp
index 962d0ceca2..129572ac21 100644
--- a/engines/tsage/detection.cpp
+++ b/engines/tsage/detection.cpp
@@ -20,42 +20,12 @@
  *
  */
 
-#include "common/config-manager.h"
-#include "common/system.h"
-#include "common/savefile.h"
-
 #include "engines/advancedDetector.h"
 
 #include "base/plugins.h"
 
-#include "tsage/tsage.h"
-
-namespace TsAGE {
-
-struct tSageGameDescription {
-	ADGameDescription desc;
-
-	int gameID;
-	uint32 features;
-};
-
-const char *TSageEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-uint32 TSageEngine::getGameID() const {
-	return _gameDescription->gameID;
-}
-
-uint32 TSageEngine::getFeatures() const {
-	return _gameDescription->features;
-}
-
-Common::String TSageEngine::getPrimaryFilename() const {
-	return Common::String(_gameDescription->desc.filesDescriptions[0].fileName);
-}
-
-} // End of namespace TsAGE
+#include "tsage/detection.h"
+#include "tsage/detection_enums.h"
 
 static const PlainGameDescriptor tSageGameTitles[] = {
 	{ "ringworld", "Ringworld: Revenge of the Patriarch" },
@@ -67,10 +37,6 @@ static const PlainGameDescriptor tSageGameTitles[] = {
 
 #include "engines/tsage/detection_tables.h"
 
-enum {
-	MAX_SAVES = 100
-};
-
 class TSageMetaEngine : public AdvancedMetaEngine {
 public:
 	TSageMetaEngine() : AdvancedMetaEngine(TsAGE::gameDescriptions, sizeof(TsAGE::tSageGameDescription), tSageGameTitles) {
@@ -87,102 +53,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "(C) Tsunami Media";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override {
-		switch (f) {
-		case kSupportsListSaves:
-		case kSupportsDeleteSave:
-		case kSupportsLoadingDuringStartup:
-		case kSavesSupportMetaInfo:
-		case kSavesSupportThumbnail:
-		case kSavesSupportCreationDate:
-		case kSavesSupportPlayTime:
-		case kSimpleSavesNames:
-			return true;
-		default:
-			return false;
-		}
-	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
-		if (desc) {
-			*engine = new TsAGE::TSageEngine(syst, (const TsAGE::tSageGameDescription *)desc);
-		}
-		return desc != 0;
-	}
-
-	static Common::String generateGameStateFileName(const char *target, int slot) {
-		return Common::String::format("%s.%03d", target, slot);
-	}
-
-	SaveStateList listSaves(const char *target) const override {
-		Common::String pattern = target;
-		pattern += ".###";
-
-		Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
-		TsAGE::tSageSavegameHeader header;
-
-		SaveStateList saveList;
-		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-			const char *ext = strrchr(file->c_str(), '.');
-			int slot = ext ? atoi(ext + 1) : -1;
-
-			if (slot >= 0 && slot < MAX_SAVES) {
-				Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-				if (in) {
-					if (TsAGE::Saver::readSavegameHeader(in, header)) {
-						saveList.push_back(SaveStateDescriptor(slot, header._saveName));
-					}
-
-					delete in;
-				}
-			}
-		}
-
-		// Sort saves based on slot number.
-		Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-		return saveList;
-	}
-
-	int getMaximumSaveSlot() const override {
-		return MAX_SAVES - 1;
-	}
-
-	void removeSaveState(const char *target, int slot) const override {
-		Common::String filename = Common::String::format("%s.%03d", target, slot);
-		g_system->getSavefileManager()->removeSavefile(filename);
-	}
-
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
-		Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(
-			generateGameStateFileName(target, slot));
-
-		if (f) {
-			TsAGE::tSageSavegameHeader header;
-			if (!TsAGE::Saver::readSavegameHeader(f, header, false)) {
-				delete f;
-				return SaveStateDescriptor();
-			}
-
-			delete f;
-
-			// Create the return descriptor
-			SaveStateDescriptor desc(slot, header._saveName);
-			desc.setThumbnail(header._thumbnail);
-			desc.setSaveDate(header._saveYear, header._saveMonth, header._saveDay);
-			desc.setSaveTime(header._saveHour, header._saveMinutes);
-			desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
-
-			return desc;
-		}
-
-		return SaveStateDescriptor();
-	}
 };
 
-#if PLUGIN_ENABLED_DYNAMIC(TSAGE)
-	REGISTER_PLUGIN_DYNAMIC(TSAGE, PLUGIN_TYPE_ENGINE, TSageMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TSAGE, PLUGIN_TYPE_ENGINE, TSageMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(TSAGE_DETECTION, PLUGIN_TYPE_METAENGINE, TSageMetaEngine);
diff --git a/engines/tsage/detection.h b/engines/tsage/detection.h
new file mode 100644
index 0000000000..07a6fe8020
--- /dev/null
+++ b/engines/tsage/detection.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace TsAGE {
+
+struct tSageGameDescription {
+	ADGameDescription desc;
+
+	int gameID;
+	uint32 features;
+};
+
+} // End of namespace TsAGE
diff --git a/engines/tsage/detection_enums.h b/engines/tsage/detection_enums.h
new file mode 100644
index 0000000000..d7c7a76b47
--- /dev/null
+++ b/engines/tsage/detection_enums.h
@@ -0,0 +1,39 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace TsAGE {
+
+enum {
+	GType_Ringworld = 0,
+	GType_BlueForce = 1,
+	GType_Ringworld2 = 2,
+	GType_Sherlock1 = 5
+};
+
+enum {
+	GF_DEMO = 1 << 0,
+	GF_CD = 1 << 1,
+	GF_FLOPPY = 1 << 2,
+	GF_ALT_REGIONS = 1 << 3
+};
+
+} // End of namespace TsAGE
diff --git a/engines/tsage/metaengine.cpp b/engines/tsage/metaengine.cpp
new file mode 100644
index 0000000000..a3dd011fa1
--- /dev/null
+++ b/engines/tsage/metaengine.cpp
@@ -0,0 +1,162 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/config-manager.h"
+#include "common/system.h"
+#include "common/savefile.h"
+
+#include "engines/advancedDetector.h"
+
+#include "base/plugins.h"
+
+#include "tsage/tsage.h"
+#include "tsage/detection.h"
+
+namespace TsAGE {
+
+const char *TSageEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+uint32 TSageEngine::getGameID() const {
+	return _gameDescription->gameID;
+}
+
+uint32 TSageEngine::getFeatures() const {
+	return _gameDescription->features;
+}
+
+Common::String TSageEngine::getPrimaryFilename() const {
+	return Common::String(_gameDescription->desc.filesDescriptions[0].fileName);
+}
+
+} // End of namespace TsAGE
+
+enum {
+	MAX_SAVES = 100
+};
+
+class TSageMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "tsage";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override {
+		switch (f) {
+		case kSupportsListSaves:
+		case kSupportsDeleteSave:
+		case kSupportsLoadingDuringStartup:
+		case kSavesSupportMetaInfo:
+		case kSavesSupportThumbnail:
+		case kSavesSupportCreationDate:
+		case kSavesSupportPlayTime:
+		case kSimpleSavesNames:
+			return true;
+		default:
+			return false;
+		}
+	}
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
+		if (desc) {
+			*engine = new TsAGE::TSageEngine(syst, (const TsAGE::tSageGameDescription *)desc);
+		}
+		return desc != 0;
+	}
+
+	static Common::String generateGameStateFileName(const char *target, int slot) {
+		return Common::String::format("%s.%03d", target, slot);
+	}
+
+	SaveStateList listSaves(const char *target) const override {
+		Common::String pattern = target;
+		pattern += ".###";
+
+		Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
+		TsAGE::tSageSavegameHeader header;
+
+		SaveStateList saveList;
+		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+			const char *ext = strrchr(file->c_str(), '.');
+			int slot = ext ? atoi(ext + 1) : -1;
+
+			if (slot >= 0 && slot < MAX_SAVES) {
+				Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+				if (in) {
+					if (TsAGE::Saver::readSavegameHeader(in, header)) {
+						saveList.push_back(SaveStateDescriptor(slot, header._saveName));
+					}
+
+					delete in;
+				}
+			}
+		}
+
+		// Sort saves based on slot number.
+		Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+		return saveList;
+	}
+
+	int getMaximumSaveSlot() const override {
+		return MAX_SAVES - 1;
+	}
+
+	void removeSaveState(const char *target, int slot) const override {
+		Common::String filename = Common::String::format("%s.%03d", target, slot);
+		g_system->getSavefileManager()->removeSavefile(filename);
+	}
+
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
+		Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(
+			generateGameStateFileName(target, slot));
+
+		if (f) {
+			TsAGE::tSageSavegameHeader header;
+			if (!TsAGE::Saver::readSavegameHeader(f, header, false)) {
+				delete f;
+				return SaveStateDescriptor();
+			}
+
+			delete f;
+
+			// Create the return descriptor
+			SaveStateDescriptor desc(slot, header._saveName);
+			desc.setThumbnail(header._thumbnail);
+			desc.setSaveDate(header._saveYear, header._saveMonth, header._saveDay);
+			desc.setSaveTime(header._saveHour, header._saveMinutes);
+			desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
+
+			return desc;
+		}
+
+		return SaveStateDescriptor();
+	}
+
+};
+
+#if PLUGIN_ENABLED_DYNAMIC(TSAGE)
+	REGISTER_PLUGIN_DYNAMIC(TSAGE, PLUGIN_TYPE_ENGINE, TSageMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TSAGE, PLUGIN_TYPE_ENGINE, TSageMetaEngineConnect);
+#endif
\ No newline at end of file
diff --git a/engines/tsage/module.mk b/engines/tsage/module.mk
index b58c748567..222932b223 100644
--- a/engines/tsage/module.mk
+++ b/engines/tsage/module.mk
@@ -17,11 +17,11 @@ MODULE_OBJS := \
 	converse.o \
 	core.o \
 	debugger.o \
-	detection.o \
 	dialogs.o \
 	events.o \
 	globals.o \
 	graphics.o \
+	metaengine.o \
 	resources.o \
 	ringworld/ringworld_demo.o \
 	ringworld/ringworld_dialogs.o \
@@ -61,3 +61,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tsage/tsage.h b/engines/tsage/tsage.h
index 8824e5f0af..06b6f53ae3 100644
--- a/engines/tsage/tsage.h
+++ b/engines/tsage/tsage.h
@@ -32,24 +32,11 @@
 #include "tsage/events.h"
 #include "tsage/graphics.h"
 #include "tsage/resources.h"
+#include "tsage/detection_enums.h"
 
 
 namespace TsAGE {
 
-enum {
-	GType_Ringworld = 0,
-	GType_BlueForce = 1,
-	GType_Ringworld2 = 2,
-	GType_Sherlock1 = 5
-};
-
-enum {
-	GF_DEMO = 1 << 0,
-	GF_CD = 1 << 1,
-	GF_FLOPPY = 1 << 2,
-	GF_ALT_REGIONS = 1 << 3
-};
-
 enum {
 	kRingDebugScripts = 1 << 0,
 	ktSageSound = 1 << 1,


Commit: 7c7263564b7e644518b04917a64afaf2c50af7ab
    https://github.com/scummvm/scummvm/commit/7c7263564b7e644518b04917a64afaf2c50af7ab
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TUCKER: Split detection features & adapt to new plugins.

Changed paths:
  A engines/tucker/detection_enums.h
  A engines/tucker/metaengine.cpp
    configure
    engines/tucker/detection.cpp
    engines/tucker/module.mk
    engines/tucker/tucker.h


diff --git a/configure b/configure
index e4b139dead..999cc56b7d 100755
--- a/configure
+++ b/configure
@@ -6168,7 +6168,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
-								  "TOUCHE" "TSAGE")
+								  "TOUCHE" "TSAGE" "TUCKER")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/tucker/detection.cpp b/engines/tucker/detection.cpp
index 449af94910..50d618721e 100644
--- a/engines/tucker/detection.cpp
+++ b/engines/tucker/detection.cpp
@@ -22,13 +22,8 @@
 
 #include "common/config-manager.h"
 #include "engines/advancedDetector.h"
-#include "common/savefile.h"
-#include "common/system.h"
-#include "common/fs.h"
 #include "base/plugins.h"
-#include "graphics/thumbnail.h"
-
-#include "tucker/tucker.h"
+#include "tucker/detection_enums.h"
 
 static const PlainGameDescriptor tuckerGames[] = {
 	{ "tucker", "Bud Tucker in Double Trouble" },
@@ -139,28 +134,6 @@ public:
 		return "Bud Tucker in Double Trouble (C) Merit Studios";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override {
-		switch (f) {
-		case kSupportsListSaves:
-		case kSupportsLoadingDuringStartup:
-		case kSupportsDeleteSave:
-		case kSavesSupportMetaInfo:
-		case kSavesSupportThumbnail:
-		case kSavesSupportCreationDate:
-		case kSavesSupportPlayTime:
-			return true;
-		default:
-			return false;
-		}
-	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
-		if (desc) {
-			*engine = new Tucker::TuckerEngine(syst, desc->language, desc->flags);
-		}
-		return desc != nullptr;
-	}
-
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override {
 		for (Common::FSList::const_iterator d = fslist.begin(); d != fslist.end(); ++d) {
 			Common::FSList audiofslist;
@@ -176,101 +149,6 @@ public:
 		return ADDetectedGame();
 	}
 
-	SaveStateList listSaves(const char *target) const override {
-		Common::String pattern = Tucker::generateGameStateFileName(target, 0, true);
-		Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
-		Tucker::TuckerEngine::SavegameHeader header;
-		SaveStateList saveList;
-
-		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-			int slot;
-			const char *ext = strrchr(file->c_str(), '.');
-			if (ext && (slot = atoi(ext + 1)) >= 0 && slot <= Tucker::kLastSaveSlot) {
-				Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-				if (in) {
-					if (Tucker::TuckerEngine::readSavegameHeader(in, header) == Tucker::TuckerEngine::kSavegameNoError) {
-						saveList.push_back(SaveStateDescriptor(slot, header.description));
-					}
-
-					delete in;
-				}
-			}
-		}
-
-		// Sort saves based on slot number.
-		Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-		return saveList;
-	}
-
-	int getMaximumSaveSlot() const override {
-		return Tucker::kLastSaveSlot;
-	}
-
-	virtual int getAutosaveSlot() const override {
-		return Tucker::kAutoSaveSlot;
-	}
-
-	void removeSaveState(const char *target, int slot) const override {
-		Common::String filename = Tucker::generateGameStateFileName(target, slot);
-		g_system->getSavefileManager()->removeSavefile(filename);
-	}
-
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
-		Common::String fileName = Common::String::format("%s.%d", target, slot);
-		Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
-
-		if (!file) {
-			return SaveStateDescriptor();
-		}
-
-		Tucker::TuckerEngine::SavegameHeader header;
-		Tucker::TuckerEngine::SavegameError savegameError = Tucker::TuckerEngine::readSavegameHeader(file, header, false);
-		if (savegameError) {
-			delete file;
-			return SaveStateDescriptor();
-		}
-
-		SaveStateDescriptor desc(slot, header.description);
-
-		if (slot == Tucker::kAutoSaveSlot) {
-			bool autosaveAllowed = Tucker::TuckerEngine::isAutosaveAllowed(target);
-			desc.setDeletableFlag(!autosaveAllowed);
-			desc.setWriteProtectedFlag(autosaveAllowed);
-		}
-
-		if (header.version >= 2) {
-			// creation/play time
-			if (header.saveDate) {
-				int day   = (header.saveDate >> 24) & 0xFF;
-				int month = (header.saveDate >> 16) & 0xFF;
-				int year  =  header.saveDate        & 0xFFFF;
-				desc.setSaveDate(year, month, day);
-			}
-
-			if (header.saveTime) {
-				int hour    = (header.saveTime >> 16) & 0xFF;
-				int minutes = (header.saveTime >>  8) & 0xFF;
-				desc.setSaveTime(hour, minutes);
-			}
-
-			if (header.playTime) {
-				desc.setPlayTime(header.playTime * 1000);
-			}
-
-			// thumbnail
-			if (header.thumbnail) {
-				desc.setThumbnail(header.thumbnail);
-			}
-		}
-
-		delete file;
-		return desc;
-	}
-
 };
 
-#if PLUGIN_ENABLED_DYNAMIC(TUCKER)
-	REGISTER_PLUGIN_DYNAMIC(TUCKER, PLUGIN_TYPE_ENGINE, TuckerMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(TUCKER, PLUGIN_TYPE_ENGINE, TuckerMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(TUCKER_DETECTION, PLUGIN_TYPE_METAENGINE, TuckerMetaEngine);
diff --git a/engines/tucker/detection_enums.h b/engines/tucker/detection_enums.h
new file mode 100644
index 0000000000..0d59b4a191
--- /dev/null
+++ b/engines/tucker/detection_enums.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Tucker {
+
+enum GameFlag {
+	kGameFlagDemo = 1 << 0,
+	kGameFlagEncodedData = 1 << 1,
+	kGameFlagNoSubtitles = 1 << 2,
+	kGameFlagIntroOnly = 1 << 3
+};
+
+} // End of namespace Tucker
diff --git a/engines/tucker/metaengine.cpp b/engines/tucker/metaengine.cpp
new file mode 100644
index 0000000000..222dad100c
--- /dev/null
+++ b/engines/tucker/metaengine.cpp
@@ -0,0 +1,156 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/savefile.h"
+#include "common/system.h"
+#include "common/fs.h"
+#include "engines/advancedDetector.h"
+#include "base/plugins.h"
+#include "graphics/thumbnail.h"
+
+#include "tucker/tucker.h"
+
+class TuckerMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "tucker";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override {
+		switch (f) {
+		case kSupportsListSaves:
+		case kSupportsLoadingDuringStartup:
+		case kSupportsDeleteSave:
+		case kSavesSupportMetaInfo:
+		case kSavesSupportThumbnail:
+		case kSavesSupportCreationDate:
+		case kSavesSupportPlayTime:
+			return true;
+		default:
+			return false;
+		}
+	}
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
+		if (desc) {
+			*engine = new Tucker::TuckerEngine(syst, desc->language, desc->flags);
+		}
+		return desc != nullptr;
+	}
+
+    SaveStateList listSaves(const char *target) const override {
+		Common::String pattern = Tucker::generateGameStateFileName(target, 0, true);
+		Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
+		Tucker::TuckerEngine::SavegameHeader header;
+		SaveStateList saveList;
+
+		for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+			int slot;
+			const char *ext = strrchr(file->c_str(), '.');
+			if (ext && (slot = atoi(ext + 1)) >= 0 && slot <= Tucker::kLastSaveSlot) {
+				Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+				if (in) {
+					if (Tucker::TuckerEngine::readSavegameHeader(in, header) == Tucker::TuckerEngine::kSavegameNoError) {
+						saveList.push_back(SaveStateDescriptor(slot, header.description));
+					}
+
+					delete in;
+				}
+			}
+		}
+
+		// Sort saves based on slot number.
+		Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+		return saveList;
+	}
+
+	int getMaximumSaveSlot() const override {
+		return Tucker::kLastSaveSlot;
+	}
+
+	virtual int getAutosaveSlot() const override {
+		return Tucker::kAutoSaveSlot;
+	}
+
+	void removeSaveState(const char *target, int slot) const override {
+		Common::String filename = Tucker::generateGameStateFileName(target, slot);
+		g_system->getSavefileManager()->removeSavefile(filename);
+	}
+
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
+		Common::String fileName = Common::String::format("%s.%d", target, slot);
+		Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
+
+		if (!file) {
+			return SaveStateDescriptor();
+		}
+
+		Tucker::TuckerEngine::SavegameHeader header;
+		Tucker::TuckerEngine::SavegameError savegameError = Tucker::TuckerEngine::readSavegameHeader(file, header, false);
+		if (savegameError) {
+			delete file;
+			return SaveStateDescriptor();
+		}
+
+		SaveStateDescriptor desc(slot, header.description);
+
+		if (slot == Tucker::kAutoSaveSlot) {
+			bool autosaveAllowed = Tucker::TuckerEngine::isAutosaveAllowed(target);
+			desc.setDeletableFlag(!autosaveAllowed);
+			desc.setWriteProtectedFlag(autosaveAllowed);
+		}
+
+		if (header.version >= 2) {
+			// creation/play time
+			if (header.saveDate) {
+				int day   = (header.saveDate >> 24) & 0xFF;
+				int month = (header.saveDate >> 16) & 0xFF;
+				int year  =  header.saveDate        & 0xFFFF;
+				desc.setSaveDate(year, month, day);
+			}
+
+			if (header.saveTime) {
+				int hour    = (header.saveTime >> 16) & 0xFF;
+				int minutes = (header.saveTime >>  8) & 0xFF;
+				desc.setSaveTime(hour, minutes);
+			}
+
+			if (header.playTime) {
+				desc.setPlayTime(header.playTime * 1000);
+			}
+
+			// thumbnail
+			if (header.thumbnail) {
+				desc.setThumbnail(header.thumbnail);
+			}
+		}
+
+		delete file;
+		return desc;
+	}
+};
+
+#if PLUGIN_ENABLED_DYNAMIC(TUCKER)
+	REGISTER_PLUGIN_DYNAMIC(TUCKER, PLUGIN_TYPE_ENGINE, TuckerMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(TUCKER, PLUGIN_TYPE_ENGINE, TuckerMetaEngineConnect);
+#endif
diff --git a/engines/tucker/module.mk b/engines/tucker/module.mk
index d11c68b746..df02f313e2 100644
--- a/engines/tucker/module.mk
+++ b/engines/tucker/module.mk
@@ -2,9 +2,9 @@ MODULE := engines/tucker
 
 MODULE_OBJS := \
 	console.o \
-	detection.o \
 	graphics.o \
 	locations.o \
+	metaengine.o \
 	resource.o \
 	saveload.o \
 	sequences.o \
@@ -18,3 +18,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tucker/tucker.h b/engines/tucker/tucker.h
index cee52f7804..9340d9a3cf 100644
--- a/engines/tucker/tucker.h
+++ b/engines/tucker/tucker.h
@@ -38,6 +38,7 @@
 #include "engines/engine.h"
 
 #include "tucker/console.h"
+#include "tucker/detection_enums.h"
 
 namespace Audio {
 class RewindableAudioStream;
@@ -361,13 +362,6 @@ enum InputKey {
 	kInputKeyCount
 };
 
-enum GameFlag {
-	kGameFlagDemo = 1 << 0,
-	kGameFlagEncodedData = 1 << 1,
-	kGameFlagNoSubtitles = 1 << 2,
-	kGameFlagIntroOnly = 1 << 3
-};
-
 enum CompressedSoundType {
 	kSoundTypeFx,
 	kSoundTypeMusic,


Commit: 52cdf076717e4d804c78384ad4c4685195d93d23
    https://github.com/scummvm/scummvm/commit/52cdf076717e4d804c78384ad4c4685195d93d23
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
VOYEUR: Split detection features & adapt to new plugins.

Changed paths:
  A engines/voyeur/detection.h
  A engines/voyeur/metaengine.cpp
    configure
    engines/voyeur/detection.cpp
    engines/voyeur/module.mk


diff --git a/configure b/configure
index 999cc56b7d..9fdf7bfd61 100755
--- a/configure
+++ b/configure
@@ -6168,7 +6168,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
-								  "TOUCHE" "TSAGE" "TUCKER")
+								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/voyeur/detection.cpp b/engines/voyeur/detection.cpp
index 5692efd242..1afa7bec50 100644
--- a/engines/voyeur/detection.cpp
+++ b/engines/voyeur/detection.cpp
@@ -20,41 +20,12 @@
  *
  */
 
-#include "voyeur/voyeur.h"
-
 #include "base/plugins.h"
-#include "common/savefile.h"
+
 #include "common/str-array.h"
 #include "common/memstream.h"
 #include "engines/advancedDetector.h"
-#include "common/system.h"
-#include "graphics/surface.h"
-
-#define MAX_SAVES 99
-
-namespace Voyeur {
-
-struct VoyeurGameDescription {
-	ADGameDescription desc;
-};
-
-uint32 VoyeurEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language VoyeurEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-Common::Platform VoyeurEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-bool VoyeurEngine::getIsDemo() const {
-	return _gameDescription->desc.flags & ADGF_DEMO;
-}
-
-} // End of namespace Voyeur
+#include "voyeur/detection.h"
 
 static const PlainGameDescriptor voyeurGames[] = {
 	{"voyeur", "Voyeur"},
@@ -80,106 +51,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Voyeur (C) Philips P.O.V. Entertainment Group";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool VoyeurMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Voyeur::VoyeurEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool VoyeurMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Voyeur::VoyeurGameDescription *gd = (const Voyeur::VoyeurGameDescription *)desc;
-	if (gd) {
-		*engine = new Voyeur::VoyeurEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList VoyeurMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.0##", target);
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	Voyeur::VoyeurSavegameHeader header;
-
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		const char *ext = strrchr(file->c_str(), '.');
-		int slot = ext ? atoi(ext + 1) : -1;
-
-		if (slot >= 0 && slot <= MAX_SAVES) {
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-			if (in) {
-				if (header.read(in)) {
-					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
-				}
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int VoyeurMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVES;
-}
-
-void VoyeurMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor VoyeurMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
-
-	if (f) {
-		Voyeur::VoyeurSavegameHeader header;
-		header.read(f, false);
-		delete f;
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header._saveName);
-		desc.setThumbnail(header._thumbnail);
-		desc.setSaveDate(header._saveYear, header._saveMonth, header._saveDay);
-		desc.setSaveTime(header._saveHour, header._saveMinutes);
-		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-
-#if PLUGIN_ENABLED_DYNAMIC(VOYEUR)
-	REGISTER_PLUGIN_DYNAMIC(VOYEUR, PLUGIN_TYPE_ENGINE, VoyeurMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(VOYEUR, PLUGIN_TYPE_ENGINE, VoyeurMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(VOYEUR_DETECTION, PLUGIN_TYPE_METAENGINE, VoyeurMetaEngine);
diff --git a/engines/voyeur/detection.h b/engines/voyeur/detection.h
new file mode 100644
index 0000000000..fb030d0aea
--- /dev/null
+++ b/engines/voyeur/detection.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Voyeur {
+
+struct VoyeurGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Voyeur
diff --git a/engines/voyeur/metaengine.cpp b/engines/voyeur/metaengine.cpp
new file mode 100644
index 0000000000..ee145ef19f
--- /dev/null
+++ b/engines/voyeur/metaengine.cpp
@@ -0,0 +1,162 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "voyeur/voyeur.h"
+
+#include "engines/advancedDetector.h"
+
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "graphics/surface.h"
+
+#include "voyeur/detection.h"
+
+#define MAX_SAVES 99
+
+namespace Voyeur {
+
+uint32 VoyeurEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language VoyeurEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+Common::Platform VoyeurEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+bool VoyeurEngine::getIsDemo() const {
+	return _gameDescription->desc.flags & ADGF_DEMO;
+}
+
+} // End of namespace Voyeur
+
+class VoyeurMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "voyeur";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool VoyeurMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Voyeur::VoyeurEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool VoyeurMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Voyeur::VoyeurGameDescription *gd = (const Voyeur::VoyeurGameDescription *)desc;
+	if (gd) {
+		*engine = new Voyeur::VoyeurEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList VoyeurMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.0##", target);
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	Voyeur::VoyeurSavegameHeader header;
+
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		const char *ext = strrchr(file->c_str(), '.');
+		int slot = ext ? atoi(ext + 1) : -1;
+
+		if (slot >= 0 && slot <= MAX_SAVES) {
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+			if (in) {
+				if (header.read(in)) {
+					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
+				}
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int VoyeurMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVES;
+}
+
+void VoyeurMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor VoyeurMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
+
+	if (f) {
+		Voyeur::VoyeurSavegameHeader header;
+		header.read(f, false);
+		delete f;
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header._saveName);
+		desc.setThumbnail(header._thumbnail);
+		desc.setSaveDate(header._saveYear, header._saveMonth, header._saveDay);
+		desc.setSaveTime(header._saveHour, header._saveMinutes);
+		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(VOYEUR)
+	REGISTER_PLUGIN_DYNAMIC(VOYEUR, PLUGIN_TYPE_ENGINE, VoyeurMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(VOYEUR, PLUGIN_TYPE_ENGINE, VoyeurMetaEngineConnect);
+#endif
diff --git a/engines/voyeur/module.mk b/engines/voyeur/module.mk
index a38bdd9ab2..ae6b7625b5 100644
--- a/engines/voyeur/module.mk
+++ b/engines/voyeur/module.mk
@@ -4,10 +4,10 @@ MODULE_OBJS := \
 	animation.o \
 	data.o \
 	debugger.o \
-	detection.o \
 	events.o \
 	files.o \
 	files_threads.o \
+	metaengine.o \
 	screen.o \
 	sound.o \
 	staticres.o \
@@ -21,3 +21,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 46f1ba1f1fc5c3a66788368bd823bb82b34acc88
    https://github.com/scummvm/scummvm/commit/46f1ba1f1fc5c3a66788368bd823bb82b34acc88
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
WAGE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/wage/metaengine.cpp
    configure
    engines/wage/detection.cpp
    engines/wage/module.mk


diff --git a/configure b/configure
index 9fdf7bfd61..2ad5dab442 100755
--- a/configure
+++ b/configure
@@ -6168,7 +6168,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
-								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR")
+								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/wage/detection.cpp b/engines/wage/detection.cpp
index ccecfed9cd..6a1b243745 100644
--- a/engines/wage/detection.cpp
+++ b/engines/wage/detection.cpp
@@ -24,18 +24,6 @@
 #include "base/plugins.h"
 
 #include "engines/advancedDetector.h"
-#include "common/system.h"
-#include "common/savefile.h"
-
-#include "wage/wage.h"
-
-namespace Wage {
-
-const char *WageEngine::getGameFile() const {
-	return _gameDescription->filesDescriptions[0].fileName;
-}
-
-}
 
 static const PlainGameDescriptor wageGames[] = {
 	{"afm", "Another Fine Mess"},
@@ -69,97 +57,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "World Builder (C) Silicon Beach Software";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool WageMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Wage::WageEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool WageMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Wage::WageEngine(syst, desc);
-	}
-	return desc != 0;
-}
-
-SaveStateList WageMetaEngine::listSaves(const char *target) const {
-	const uint32 WAGEflag = MKTAG('W','A','G','E');
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	char saveDesc[128] = {0};
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				saveDesc[0] = 0;
-				in->seek(in->size() - 8);
-				uint32 offset = in->readUint32BE();
-				uint32 type = in->readUint32BE();
-				if (type == WAGEflag) {
-					in->seek(offset);
-
-					type = in->readUint32BE();
-					if (type == WAGEflag) {
-						in->read(saveDesc, 127);
-					}
-				}
-				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int WageMetaEngine::getMaximumSaveSlot() const { return 999; }
-
-void WageMetaEngine::removeSaveState(const char *target, int slot) const {
-	g_system->getSavefileManager()->removeSavefile(Common::String::format("%s.%03d", target, slot));
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(WAGE)
-	REGISTER_PLUGIN_DYNAMIC(WAGE, PLUGIN_TYPE_ENGINE, WageMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(WAGE, PLUGIN_TYPE_ENGINE, WageMetaEngine);
-#endif
-
-namespace Wage {
-
-bool WageEngine::canLoadGameStateCurrently() {
-	return true;
-}
-
-bool WageEngine::canSaveGameStateCurrently() {
-	return true;
-}
-
-} // End of namespace Wage
+REGISTER_PLUGIN_STATIC(WAGE_DETECTION, PLUGIN_TYPE_METAENGINE, WageMetaEngine);
diff --git a/engines/wage/metaengine.cpp b/engines/wage/metaengine.cpp
new file mode 100644
index 0000000000..234ec45dcf
--- /dev/null
+++ b/engines/wage/metaengine.cpp
@@ -0,0 +1,139 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "common/system.h"
+#include "common/savefile.h"
+
+#include "engines/advancedDetector.h"
+
+#include "wage/wage.h"
+
+namespace Wage {
+
+const char *WageEngine::getGameFile() const {
+	return _gameDescription->filesDescriptions[0].fileName;
+}
+
+} // End of namespace Wage
+
+class WageMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "wage";
+	}
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool WageMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Wage::WageEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool WageMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Wage::WageEngine(syst, desc);
+	}
+	return desc != 0;
+}
+
+SaveStateList WageMetaEngineConnect::listSaves(const char *target) const {
+	const uint32 WAGEflag = MKTAG('W','A','G','E');
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	char saveDesc[128] = {0};
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				saveDesc[0] = 0;
+				in->seek(in->size() - 8);
+				uint32 offset = in->readUint32BE();
+				uint32 type = in->readUint32BE();
+				if (type == WAGEflag) {
+					in->seek(offset);
+
+					type = in->readUint32BE();
+					if (type == WAGEflag) {
+						in->read(saveDesc, 127);
+					}
+				}
+				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int WageMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+
+void WageMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	g_system->getSavefileManager()->removeSavefile(Common::String::format("%s.%03d", target, slot));
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(WAGE)
+	REGISTER_PLUGIN_DYNAMIC(WAGE, PLUGIN_TYPE_ENGINE, WageMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(WAGE, PLUGIN_TYPE_ENGINE, WageMetaEngineConnect);
+#endif
+
+namespace Wage {
+
+bool WageEngine::canLoadGameStateCurrently() {
+	return true;
+}
+
+bool WageEngine::canSaveGameStateCurrently() {
+	return true;
+}
+
+} // End of namespace Wage
diff --git a/engines/wage/module.mk b/engines/wage/module.mk
index 9f11e16db0..86b4b86c8c 100644
--- a/engines/wage/module.mk
+++ b/engines/wage/module.mk
@@ -4,10 +4,10 @@ MODULE_OBJS := \
 	combat.o \
 	debugger.o \
 	design.o \
-	detection.o \
 	dialog.o \
 	entities.o \
 	gui.o \
+	metaengine.o \
 	randomhat.o \
 	saveload.o \
 	script.o \
@@ -26,3 +26,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 9208a65a1fec99c0ba7038f99389c7833e1ec595
    https://github.com/scummvm/scummvm/commit/9208a65a1fec99c0ba7038f99389c7833e1ec595
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
AVALANCHE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/avalanche/detection.h
  A engines/avalanche/metaengine.cpp
    configure
    engines/avalanche/detection.cpp
    engines/avalanche/module.mk


diff --git a/configure b/configure
index 2ad5dab442..3cb3122803 100755
--- a/configure
+++ b/configure
@@ -6168,7 +6168,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
-								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE")
+								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/avalanche/detection.cpp b/engines/avalanche/detection.cpp
index 9ea9b649b4..d6baf0f64e 100644
--- a/engines/avalanche/detection.cpp
+++ b/engines/avalanche/detection.cpp
@@ -25,31 +25,14 @@
  * Copyright (c) 1994-1995 Mike, Mark and Thomas Thurman.
  */
 
-#include "avalanche/avalanche.h"
 
-#include "common/system.h"
-#include "common/savefile.h"
 
+#include "base/plugins.h"
 #include "engines/advancedDetector.h"
-#include "graphics/thumbnail.h"
 
-namespace Avalanche {
-
-struct AvalancheGameDescription {
-	ADGameDescription desc;
-};
-
-uint32 AvalancheEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
+#include "avalanche/detection.h"
 
-const char *AvalancheEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-Common::Platform AvalancheEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
+namespace Avalanche {
 
 static const PlainGameDescriptor avalancheGames[] = {
 	{"avalanche", "Lord Avalot d'Argent"},
@@ -89,140 +72,8 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Avalanche (C) 1994-1995 Mike, Mark and Thomas Thurman.";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-
-	int getMaximumSaveSlot() const override { return 99; }
-	SaveStateList listSaves(const char *target) const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool AvalancheMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
-	if (gd)
-		*engine = new AvalancheEngine(syst, (const AvalancheGameDescription *)gd);
-	return gd != 0;
-}
-
-bool AvalancheMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSimpleSavesNames);
-}
-
-SaveStateList AvalancheMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern.toUppercase();
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
-		const Common::String &fname = *filename;
-		int slotNum = atoi(fname.c_str() + fname.size() - 3);
-		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
-			Common::InSaveFile *file = saveFileMan->openForLoading(fname);
-			if (file) {
-				// Check for our signature.
-				uint32 signature = file->readUint32LE();
-				if (signature != MKTAG('A', 'V', 'A', 'L')) {
-					warning("Savegame of incompatible type!");
-					delete file;
-					continue;
-				}
-
-				// Check version.
-				byte saveVersion = file->readByte();
-				if (saveVersion > kSavegameVersion) {
-					warning("Savegame of incompatible version!");
-					delete file;
-					continue;
-				}
-
-				// Read name.
-				uint32 nameSize = file->readUint32LE();
-				if (nameSize >= 255) {
-					delete file;
-					continue;
-				}
-				char *name = new char[nameSize + 1];
-				file->read(name, nameSize);
-				name[nameSize] = 0;
-
-				saveList.push_back(SaveStateDescriptor(slotNum, name));
-				delete[] name;
-				delete file;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void AvalancheMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-SaveStateDescriptor AvalancheMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (f) {
-		// Check for our signature.
-		uint32 signature = f->readUint32LE();
-		if (signature != MKTAG('A', 'V', 'A', 'L')) {
-			warning("Savegame of incompatible type!");
-			delete f;
-			return SaveStateDescriptor();
-		}
-
-		// Check version.
-		byte saveVersion = f->readByte();
-		if (saveVersion > kSavegameVersion) {
-			warning("Savegame of a too recent version!");
-			delete f;
-			return SaveStateDescriptor();
-		}
-
-		// Read the description.
-		uint32 descSize = f->readUint32LE();
-		Common::String description;
-		for (uint32 i = 0; i < descSize; i++) {
-			char actChar = f->readByte();
-			description += actChar;
-		}
-
-		SaveStateDescriptor desc(slot, description);
-
-		Graphics::Surface *thumbnail;
-		if (!Graphics::loadThumbnail(*f, thumbnail)) {
-			warning("Cannot read thumbnail data, possibly broken savegame");
-			delete f;
-			return SaveStateDescriptor();
-		}
-		desc.setThumbnail(thumbnail);
-
-		delete f;
-		return desc;
-	}
-	return SaveStateDescriptor();
-}
-
 } // End of namespace Avalanche
 
-#if PLUGIN_ENABLED_DYNAMIC(AVALANCHE)
-	REGISTER_PLUGIN_DYNAMIC(AVALANCHE, PLUGIN_TYPE_ENGINE, Avalanche::AvalancheMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(AVALANCHE, PLUGIN_TYPE_ENGINE, Avalanche::AvalancheMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(AVALANCHE_DETECTION, PLUGIN_TYPE_METAENGINE, Avalanche::AvalancheMetaEngine);
diff --git a/engines/avalanche/detection.h b/engines/avalanche/detection.h
new file mode 100644
index 0000000000..01512a0558
--- /dev/null
+++ b/engines/avalanche/detection.h
@@ -0,0 +1,35 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+/*
+ * This code is based on the original source code of Lord Avalot d'Argent version 1.3.
+ * Copyright (c) 1994-1995 Mike, Mark and Thomas Thurman.
+ */
+
+
+namespace Avalanche {
+
+struct AvalancheGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Avalanche
diff --git a/engines/avalanche/metaengine.cpp b/engines/avalanche/metaengine.cpp
new file mode 100644
index 0000000000..f004c89964
--- /dev/null
+++ b/engines/avalanche/metaengine.cpp
@@ -0,0 +1,198 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+/*
+ * This code is based on the original source code of Lord Avalot d'Argent version 1.3.
+ * Copyright (c) 1994-1995 Mike, Mark and Thomas Thurman.
+ */
+
+#include "avalanche/avalanche.h"
+
+#include "common/system.h"
+#include "common/savefile.h"
+
+#include "engines/advancedDetector.h"
+#include "graphics/thumbnail.h"
+
+#include "avalanche/detection.h"
+
+
+namespace Avalanche {
+
+uint32 AvalancheEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+const char *AvalancheEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+Common::Platform AvalancheEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+} // End of namespace Avalanche
+
+namespace Avalanche {
+
+class AvalancheMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "avalanche";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	int getMaximumSaveSlot() const override { return 99; }
+	SaveStateList listSaves(const char *target) const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool AvalancheMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+	if (gd)
+		*engine = new AvalancheEngine(syst, (const AvalancheGameDescription *)gd);
+	return gd != 0;
+}
+
+bool AvalancheMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSimpleSavesNames);
+}
+
+SaveStateList AvalancheMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern.toUppercase();
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
+		const Common::String &fname = *filename;
+		int slotNum = atoi(fname.c_str() + fname.size() - 3);
+		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
+			Common::InSaveFile *file = saveFileMan->openForLoading(fname);
+			if (file) {
+				// Check for our signature.
+				uint32 signature = file->readUint32LE();
+				if (signature != MKTAG('A', 'V', 'A', 'L')) {
+					warning("Savegame of incompatible type!");
+					delete file;
+					continue;
+				}
+
+				// Check version.
+				byte saveVersion = file->readByte();
+				if (saveVersion > kSavegameVersion) {
+					warning("Savegame of incompatible version!");
+					delete file;
+					continue;
+				}
+
+				// Read name.
+				uint32 nameSize = file->readUint32LE();
+				if (nameSize >= 255) {
+					delete file;
+					continue;
+				}
+				char *name = new char[nameSize + 1];
+				file->read(name, nameSize);
+				name[nameSize] = 0;
+
+				saveList.push_back(SaveStateDescriptor(slotNum, name));
+				delete[] name;
+				delete file;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void AvalancheMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+SaveStateDescriptor AvalancheMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (f) {
+		// Check for our signature.
+		uint32 signature = f->readUint32LE();
+		if (signature != MKTAG('A', 'V', 'A', 'L')) {
+			warning("Savegame of incompatible type!");
+			delete f;
+			return SaveStateDescriptor();
+		}
+
+		// Check version.
+		byte saveVersion = f->readByte();
+		if (saveVersion > kSavegameVersion) {
+			warning("Savegame of a too recent version!");
+			delete f;
+			return SaveStateDescriptor();
+		}
+
+		// Read the description.
+		uint32 descSize = f->readUint32LE();
+		Common::String description;
+		for (uint32 i = 0; i < descSize; i++) {
+			char actChar = f->readByte();
+			description += actChar;
+		}
+
+		SaveStateDescriptor desc(slot, description);
+
+		Graphics::Surface *thumbnail;
+		if (!Graphics::loadThumbnail(*f, thumbnail)) {
+			warning("Cannot read thumbnail data, possibly broken savegame");
+			delete f;
+			return SaveStateDescriptor();
+		}
+		desc.setThumbnail(thumbnail);
+
+		delete f;
+		return desc;
+	}
+	return SaveStateDescriptor();
+}
+
+} // End of namespace Avalanche
+
+#if PLUGIN_ENABLED_DYNAMIC(AVALANCHE)
+	REGISTER_PLUGIN_DYNAMIC(AVALANCHE, PLUGIN_TYPE_ENGINE, Avalanche::AvalancheMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(AVALANCHE, PLUGIN_TYPE_ENGINE, Avalanche::AvalancheMetaEngineConnect);
+#endif
diff --git a/engines/avalanche/module.mk b/engines/avalanche/module.mk
index 919ff0334f..f8380b9bd1 100644
--- a/engines/avalanche/module.mk
+++ b/engines/avalanche/module.mk
@@ -7,7 +7,6 @@ MODULE_OBJS = \
 	background.o \
 	closing.o \
 	console.o \
-	detection.o \
 	graphics.o \
 	dropdown.o \
 	parser.o \
@@ -15,6 +14,7 @@ MODULE_OBJS = \
 	sequence.o \
 	sound.o \
 	timer.o \
+	metaengine.o \
 	nim.o \
 	clock.o \
 	ghostroom.o \
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: c4ba47a65d46ea6744cfe9de77fe3b2cad556c47
    https://github.com/scummvm/scummvm/commit/c4ba47a65d46ea6744cfe9de77fe3b2cad556c47
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BBVS: Split detection features & adapt to new plugins.

Changed paths:
  A engines/bbvs/detection_enums.h
  A engines/bbvs/metaengine.cpp
    configure
    engines/bbvs/bbvs.h
    engines/bbvs/detection.cpp
    engines/bbvs/module.mk


diff --git a/configure b/configure
index 3cb3122803..608f133b14 100755
--- a/configure
+++ b/configure
@@ -6168,7 +6168,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
-								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE")
+								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/bbvs/bbvs.h b/engines/bbvs/bbvs.h
index 84dee3a2b9..d513c679f2 100644
--- a/engines/bbvs/bbvs.h
+++ b/engines/bbvs/bbvs.h
@@ -24,6 +24,7 @@
 #define BBVS_BBVS_H
 
 #include "audio/mixer.h"
+
 #include "common/array.h"
 #include "common/events.h"
 #include "common/file.h"
@@ -32,8 +33,11 @@
 #include "common/str.h"
 #include "common/substream.h"
 #include "common/system.h"
+
 #include "engines/engine.h"
 
+#include "bbvs/detection_enums.h"
+
 struct ADGameDescription;
 
 namespace Bbvs {
@@ -59,10 +63,6 @@ class SoundMan;
 
 #define BBVS_SAVEGAME_VERSION 0
 
-enum {
-	GF_GUILANGSWITCH =    (1 << 0) // If GUI language switch is required for menus
-};
-
 enum {
 	kVerbLook      = 0,
 	kVerbUse       = 1,
diff --git a/engines/bbvs/detection.cpp b/engines/bbvs/detection.cpp
index ddbf173384..af1942f411 100644
--- a/engines/bbvs/detection.cpp
+++ b/engines/bbvs/detection.cpp
@@ -20,14 +20,10 @@
  *
  */
 
-#include "bbvs/bbvs.h"
-
-#include "common/config-manager.h"
 #include "engines/advancedDetector.h"
-#include "common/savefile.h"
-#include "common/system.h"
 #include "base/plugins.h"
-#include "graphics/thumbnail.h"
+
+#include "bbvs/detection_enums.h"
 
 static const PlainGameDescriptor bbvsGames[] = {
 	{ "bbvs", "Beavis and Butt-head in Virtual Stupidity" },
@@ -113,93 +109,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "(C) 1995 Viacom New Media";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	int getMaximumSaveSlot() const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool BbvsMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-	    (f == kSupportsDeleteSave) ||
-	    (f == kSupportsLoadingDuringStartup) ||
-	    (f == kSavesSupportMetaInfo) ||
-	    (f == kSavesSupportThumbnail) ||
-	    (f == kSavesSupportCreationDate) ||
-		(f == kSimpleSavesNames);
-}
-
-void BbvsMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-int BbvsMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-SaveStateList BbvsMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Bbvs::BbvsEngine::SaveHeader header;
-	Common::String pattern = target;
-	pattern += ".###";
-	Common::StringArray filenames;
-	filenames = saveFileMan->listSavefiles(pattern.c_str());
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 3);
-		if (slotNum >= 0 && slotNum <= 999) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
-			if (in) {
-				if (Bbvs::BbvsEngine::readSaveHeader(in, header) == Bbvs::BbvsEngine::kRSHENoError) {
-					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
-				}
-				delete in;
-			}
-		}
-	}
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor BbvsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Bbvs::BbvsEngine::getSavegameFilename(target, slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
-	if (in) {
-		Bbvs::BbvsEngine::SaveHeader header;
-		Bbvs::BbvsEngine::kReadSaveHeaderError error;
-		error = Bbvs::BbvsEngine::readSaveHeader(in, header, false);
-		delete in;
-		if (error == Bbvs::BbvsEngine::kRSHENoError) {
-			SaveStateDescriptor desc(slot, header.description);
-			// Slot 0 is used for the "Continue" save
-			desc.setDeletableFlag(slot != 0);
-			desc.setWriteProtectedFlag(slot == 0);
-			desc.setThumbnail(header.thumbnail);
-			desc.setSaveDate(header.saveDate & 0xFFFF, (header.saveDate >> 16) & 0xFF, (header.saveDate >> 24) & 0xFF);
-			desc.setSaveTime((header.saveTime >> 16) & 0xFF, (header.saveTime >> 8) & 0xFF);
-			desc.setPlayTime(header.playTime * 1000);
-			return desc;
-		}
-	}
-	return SaveStateDescriptor();
-}
-
-bool BbvsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Bbvs::BbvsEngine(syst, desc);
-	}
-	return desc != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(BBVS)
-	REGISTER_PLUGIN_DYNAMIC(BBVS, PLUGIN_TYPE_ENGINE, BbvsMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(BBVS, PLUGIN_TYPE_ENGINE, BbvsMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(BBVS_DETECTION, PLUGIN_TYPE_METAENGINE, BbvsMetaEngine);
diff --git a/engines/bbvs/detection_enums.h b/engines/bbvs/detection_enums.h
new file mode 100644
index 0000000000..70bef6ec10
--- /dev/null
+++ b/engines/bbvs/detection_enums.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Bbvs {
+
+enum {
+	GF_GUILANGSWITCH =    (1 << 0) // If GUI language switch is required for menus
+};
+
+} // End of namespace Bbvs
diff --git a/engines/bbvs/metaengine.cpp b/engines/bbvs/metaengine.cpp
new file mode 100644
index 0000000000..e1c335d45a
--- /dev/null
+++ b/engines/bbvs/metaengine.cpp
@@ -0,0 +1,127 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "bbvs/bbvs.h"
+
+#include "common/config-manager.h"
+#include "engines/advancedDetector.h"
+#include "common/savefile.h"
+#include "common/system.h"
+#include "base/plugins.h"
+#include "graphics/thumbnail.h"
+
+class BbvsMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "bbvs";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	int getMaximumSaveSlot() const override;
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool BbvsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+	    (f == kSupportsDeleteSave) ||
+	    (f == kSupportsLoadingDuringStartup) ||
+	    (f == kSavesSupportMetaInfo) ||
+	    (f == kSavesSupportThumbnail) ||
+	    (f == kSavesSupportCreationDate) ||
+		(f == kSimpleSavesNames);
+}
+
+void BbvsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+int BbvsMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+SaveStateList BbvsMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Bbvs::BbvsEngine::SaveHeader header;
+	Common::String pattern = target;
+	pattern += ".###";
+	Common::StringArray filenames;
+	filenames = saveFileMan->listSavefiles(pattern.c_str());
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 3);
+		if (slotNum >= 0 && slotNum <= 999) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(file->c_str());
+			if (in) {
+				if (Bbvs::BbvsEngine::readSaveHeader(in, header) == Bbvs::BbvsEngine::kRSHENoError) {
+					saveList.push_back(SaveStateDescriptor(slotNum, header.description));
+				}
+				delete in;
+			}
+		}
+	}
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor BbvsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Bbvs::BbvsEngine::getSavegameFilename(target, slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
+	if (in) {
+		Bbvs::BbvsEngine::SaveHeader header;
+		Bbvs::BbvsEngine::kReadSaveHeaderError error;
+		error = Bbvs::BbvsEngine::readSaveHeader(in, header, false);
+		delete in;
+		if (error == Bbvs::BbvsEngine::kRSHENoError) {
+			SaveStateDescriptor desc(slot, header.description);
+			// Slot 0 is used for the "Continue" save
+			desc.setDeletableFlag(slot != 0);
+			desc.setWriteProtectedFlag(slot == 0);
+			desc.setThumbnail(header.thumbnail);
+			desc.setSaveDate(header.saveDate & 0xFFFF, (header.saveDate >> 16) & 0xFF, (header.saveDate >> 24) & 0xFF);
+			desc.setSaveTime((header.saveTime >> 16) & 0xFF, (header.saveTime >> 8) & 0xFF);
+			desc.setPlayTime(header.playTime * 1000);
+			return desc;
+		}
+	}
+	return SaveStateDescriptor();
+}
+
+bool BbvsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Bbvs::BbvsEngine(syst, desc);
+	}
+	return desc != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(BBVS)
+	REGISTER_PLUGIN_DYNAMIC(BBVS, PLUGIN_TYPE_ENGINE, BbvsMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(BBVS, PLUGIN_TYPE_ENGINE, BbvsMetaEngineConnect);
+#endif
diff --git a/engines/bbvs/module.mk b/engines/bbvs/module.mk
index 90c62d0acb..e20210494a 100644
--- a/engines/bbvs/module.mk
+++ b/engines/bbvs/module.mk
@@ -2,11 +2,11 @@ MODULE := engines/bbvs
 
 MODULE_OBJS := \
 	bbvs.o \
-	detection.o \
 	dialogs.o \
 	gamemodule.o \
 	graphics.o \
 	logic.o \
+	metaengine.o \
 	saveload.o \
 	scene.o \
 	sound.o \
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: de141e7826f6373c1985d95aab7d51a85887866e
    https://github.com/scummvm/scummvm/commit/de141e7826f6373c1985d95aab7d51a85887866e
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BLADERUNNER: Split detection features & adapt to new plugins.

Changed paths:
  A engines/bladerunner/metaengine.cpp
    configure
    engines/bladerunner/detection.cpp
    engines/bladerunner/module.mk


diff --git a/configure b/configure
index 608f133b14..5ee99ebb97 100755
--- a/configure
+++ b/configure
@@ -6168,7 +6168,8 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
-								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS")
+								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
+								  "BLADERUNNER")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/bladerunner/detection.cpp b/engines/bladerunner/detection.cpp
index 0b182dda68..ecef2d5b34 100644
--- a/engines/bladerunner/detection.cpp
+++ b/engines/bladerunner/detection.cpp
@@ -99,12 +99,6 @@ public:
 	const char *getEngineId() const override;
 	const char *getName() const override;
 	const char *getOriginalCopyright() const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
 BladeRunnerMetaEngine::BladeRunnerMetaEngine()
@@ -126,42 +120,4 @@ const char *BladeRunnerMetaEngine::getOriginalCopyright() const {
 	return "Blade Runner (C) 1997 Westwood Studios";
 }
 
-bool BladeRunnerMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	*engine = new BladeRunner::BladeRunnerEngine(syst, desc);
-
-	return true;
-}
-
-bool BladeRunnerMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		f == kSupportsListSaves ||
-		f == kSupportsLoadingDuringStartup ||
-		f == kSupportsDeleteSave ||
-		f == kSavesSupportMetaInfo ||
-		f == kSavesSupportThumbnail ||
-		f == kSavesSupportCreationDate ||
-		f == kSavesSupportPlayTime ||
-		f == kSimpleSavesNames;
-}
-
-SaveStateList BladeRunnerMetaEngine::listSaves(const char *target) const {
-	return BladeRunner::SaveFileManager::list(target);
-}
-
-int BladeRunnerMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-void BladeRunnerMetaEngine::removeSaveState(const char *target, int slot) const {
-	BladeRunner::SaveFileManager::remove(target, slot);
-}
-
-SaveStateDescriptor BladeRunnerMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	return BladeRunner::SaveFileManager::queryMetaInfos(target, slot);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(BLADERUNNER)
-	REGISTER_PLUGIN_DYNAMIC(BLADERUNNER, PLUGIN_TYPE_ENGINE, BladeRunnerMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(BLADERUNNER, PLUGIN_TYPE_ENGINE, BladeRunnerMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(BLADERUNNER_DETECTION, PLUGIN_TYPE_METAENGINE, BladeRunnerMetaEngine);
diff --git a/engines/bladerunner/metaengine.cpp b/engines/bladerunner/metaengine.cpp
new file mode 100644
index 0000000000..3ed0c04ccf
--- /dev/null
+++ b/engines/bladerunner/metaengine.cpp
@@ -0,0 +1,91 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+#include "bladerunner/bladerunner.h"
+#include "bladerunner/detection_tables.h"
+#include "bladerunner/savefile.h"
+
+#include "common/config-manager.h"
+#include "common/system.h"
+#include "common/savefile.h"
+#include "common/serializer.h"
+#include "common/translation.h"
+
+#include "engines/advancedDetector.h"
+
+class BladeRunnerMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override;
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+const char *BladeRunnerMetaEngineConnect::getName() const {
+	return "bladerunner";
+}
+
+bool BladeRunnerMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	*engine = new BladeRunner::BladeRunnerEngine(syst, desc);
+
+	return true;
+}
+
+bool BladeRunnerMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		f == kSupportsListSaves ||
+		f == kSupportsLoadingDuringStartup ||
+		f == kSupportsDeleteSave ||
+		f == kSavesSupportMetaInfo ||
+		f == kSavesSupportThumbnail ||
+		f == kSavesSupportCreationDate ||
+		f == kSavesSupportPlayTime ||
+		f == kSimpleSavesNames;
+}
+
+SaveStateList BladeRunnerMetaEngineConnect::listSaves(const char *target) const {
+	return BladeRunner::SaveFileManager::list(target);
+}
+
+int BladeRunnerMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+void BladeRunnerMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	BladeRunner::SaveFileManager::remove(target, slot);
+}
+
+SaveStateDescriptor BladeRunnerMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	return BladeRunner::SaveFileManager::queryMetaInfos(target, slot);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(BLADERUNNER)
+	REGISTER_PLUGIN_DYNAMIC(BLADERUNNER, PLUGIN_TYPE_ENGINE, BladeRunnerMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(BLADERUNNER, PLUGIN_TYPE_ENGINE, BladeRunnerMetaEngineConnect);
+#endif
diff --git a/engines/bladerunner/module.mk b/engines/bladerunner/module.mk
index 984de0aa27..aae2394a9b 100644
--- a/engines/bladerunner/module.mk
+++ b/engines/bladerunner/module.mk
@@ -22,7 +22,6 @@ MODULE_OBJS = \
 	debugger.o \
 	decompress_lcw.o \
 	decompress_lzo.o \
-	detection.o \
 	dialogue_menu.o \
 	framelimiter.o \
 	fog.o \
@@ -36,6 +35,7 @@ MODULE_OBJS = \
 	light.o \
 	lights.o \
 	matrix.o \
+	metaengine.o \
 	mouse.o \
 	movement_track.o \
 	music.o \
@@ -288,3 +288,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 6ade053c01fa867f87344ec3dc4c05a53b44b41e
    https://github.com/scummvm/scummvm/commit/6ade053c01fa867f87344ec3dc4c05a53b44b41e
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CHEWY: Split detection features & adapt to new plugins.

Changed paths:
  A engines/chewy/detection.h
  A engines/chewy/metaengine.cpp
    configure
    engines/chewy/detection.cpp
    engines/chewy/module.mk


diff --git a/configure b/configure
index 5ee99ebb97..6fdf4d007b 100755
--- a/configure
+++ b/configure
@@ -6169,7 +6169,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
-								  "BLADERUNNER")
+								  "BLADERUNNER" "CHEWY")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/chewy/detection.cpp b/engines/chewy/detection.cpp
index 0f747e7fb5..17ed3f2b25 100644
--- a/engines/chewy/detection.cpp
+++ b/engines/chewy/detection.cpp
@@ -20,30 +20,10 @@
  *
  */
 
-#include "common/savefile.h"
-#include "common/system.h"
 #include "base/plugins.h"
-
 #include "engines/advancedDetector.h"
 
-#include "chewy/chewy.h"
-
-
-namespace Chewy {
-
-struct ChewyGameDescription {
-	ADGameDescription desc;
-};
-
-uint32 ChewyEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language ChewyEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-}
+#include "chewy/detection.h"
 
 static const PlainGameDescriptor chewyGames[] = {
 	{"chewy", "Chewy: Esc from F5"},
@@ -128,61 +108,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Chewy: Esc from F5 (C) 1995 New Generation Software";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool ChewyMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime);
-}
-
-bool Chewy::ChewyEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool ChewyMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Chewy::ChewyGameDescription *gd = (const Chewy::ChewyGameDescription *)desc;
-	if (gd) {
-		*engine = new Chewy::ChewyEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList ChewyMetaEngine::listSaves(const char *target) const {
-	SaveStateList saveList;
-
-	return saveList;
-}
-
-int ChewyMetaEngine::getMaximumSaveSlot() const {
-	return 999;
-}
-
-void ChewyMetaEngine::removeSaveState(const char *target, int slot) const {
-}
-
-SaveStateDescriptor ChewyMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-
-	return SaveStateDescriptor();
-} // End of namespace Chewy
-
-#if PLUGIN_ENABLED_DYNAMIC(CHEWY)
-	REGISTER_PLUGIN_DYNAMIC(CHEWY, PLUGIN_TYPE_ENGINE, ChewyMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(CHEWY, PLUGIN_TYPE_ENGINE, ChewyMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(CHEWY_DETECTION, PLUGIN_TYPE_METAENGINE, ChewyMetaEngine);
diff --git a/engines/chewy/detection.h b/engines/chewy/detection.h
new file mode 100644
index 0000000000..6d9a4e8937
--- /dev/null
+++ b/engines/chewy/detection.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Chewy {
+
+struct ChewyGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Chewy
diff --git a/engines/chewy/metaengine.cpp b/engines/chewy/metaengine.cpp
new file mode 100644
index 0000000000..bf14b79ebb
--- /dev/null
+++ b/engines/chewy/metaengine.cpp
@@ -0,0 +1,106 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/savefile.h"
+#include "common/system.h"
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+
+#include "chewy/chewy.h"
+#include "chewy/detection.h"
+
+namespace Chewy {
+
+uint32 ChewyEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language ChewyEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+} // End of namespace Chewy
+
+class ChewyMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "chewy";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool ChewyMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime);
+}
+
+bool Chewy::ChewyEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool ChewyMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Chewy::ChewyGameDescription *gd = (const Chewy::ChewyGameDescription *)desc;
+	if (gd) {
+		*engine = new Chewy::ChewyEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList ChewyMetaEngineConnect::listSaves(const char *target) const {
+	SaveStateList saveList;
+
+	return saveList;
+}
+
+int ChewyMetaEngineConnect::getMaximumSaveSlot() const {
+	return 999;
+}
+
+void ChewyMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+}
+
+SaveStateDescriptor ChewyMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(CHEWY)
+	REGISTER_PLUGIN_DYNAMIC(CHEWY, PLUGIN_TYPE_ENGINE, ChewyMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(CHEWY, PLUGIN_TYPE_ENGINE, ChewyMetaEngineConnect);
+#endif
diff --git a/engines/chewy/module.mk b/engines/chewy/module.mk
index 5752e28adf..87d8042c52 100644
--- a/engines/chewy/module.mk
+++ b/engines/chewy/module.mk
@@ -4,9 +4,9 @@ MODULE_OBJS = \
 	chewy.o \
 	cursor.o \
 	console.o \
-	detection.o \
 	events.o \
 	graphics.o \
+	metaengine.o \
 	resource.o \
 	scene.o \
 	sound.o \
@@ -20,3 +20,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: ec3ccf5eb03ed347263abbd2fe6d87e3d0cc65b4
    https://github.com/scummvm/scummvm/commit/ec3ccf5eb03ed347263abbd2fe6d87e3d0cc65b4
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CINE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/cine/detection.h
  A engines/cine/detection_enums.h
  A engines/cine/metaengine.cpp
    configure
    engines/cine/cine.h
    engines/cine/detection.cpp
    engines/cine/module.mk
    engines/cine/saveload.cpp


diff --git a/configure b/configure
index 6fdf4d007b..34dd47418d 100755
--- a/configure
+++ b/configure
@@ -6169,7 +6169,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
-								  "BLADERUNNER" "CHEWY")
+								  "BLADERUNNER" "CHEWY" "CINE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/cine/cine.h b/engines/cine/cine.h
index 6bc04b3c5d..aec244e440 100644
--- a/engines/cine/cine.h
+++ b/engines/cine/cine.h
@@ -48,6 +48,7 @@
 #include "cine/various.h"
 #include "cine/console.h"
 #include "cine/sound.h"
+#include "cine/detection_enums.h"
 
 //#define DUMP_SCRIPTS
 
@@ -81,18 +82,6 @@
  */
 namespace Cine {
 
-enum CineGameType {
-	GType_FW = 1,
-	GType_OS
-};
-
-enum CineGameFeatures {
-	GF_CD =   1 << 0,
-	GF_DEMO = 1 << 1,
-	GF_ALT_FONT = 1 << 2,
-	GF_CRYPTED_BOOT_PRC = 1 << 3
-};
-
 struct CINEGameDescription;
 struct SeqListElement;
 
diff --git a/engines/cine/detection.cpp b/engines/cine/detection.cpp
index e51c079dcb..311c922507 100644
--- a/engines/cine/detection.cpp
+++ b/engines/cine/detection.cpp
@@ -24,34 +24,10 @@
 
 #include "engines/advancedDetector.h"
 
-#include "common/system.h"
-#include "common/textconsole.h"
 #include "common/translation.h"
-#include "common/util.h"
 
-#include "cine/cine.h"
-#include "cine/various.h"
-
-namespace Cine {
-
-#define MAX_SAVEGAMES (ARRAYSIZE(Cine::currentSaveName))
-#define SAVEGAME_NAME_LEN (sizeof(Cine::currentSaveName[0]))
-#define SAVELIST_SIZE (MAX_SAVEGAMES * SAVEGAME_NAME_LEN)
-
-struct CINEGameDescription {
-	ADGameDescription desc;
-
-	int gameType;
-	uint32 features;
-};
-
-bool CineEngine::mayHave256Colors() const { return getGameType() == Cine::GType_OS && getPlatform() == Common::kPlatformDOS; }
-int CineEngine::getGameType() const { return _gameDescription->gameType; }
-uint32 CineEngine::getFeatures() const { return _gameDescription->features; }
-Common::Language CineEngine::getLanguage() const { return _gameDescription->desc.language; }
-Common::Platform CineEngine::getPlatform() const { return _gameDescription->desc.platform; }
-
-} // End of namespace Cine
+#include "cine/detection.h"
+#include "cine/detection_enums.h"
 
 static const PlainGameDescriptor cineGames[] = {
 	{"fw", "Future Wars"},
@@ -101,293 +77,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Cinematique evo 1 (C) Delphine Software";
 	}
-
-	Common::Error createInstance(OSystem *syst, Engine **engine) const override {
-		return AdvancedMetaEngine::createInstance(syst, engine);
-	}
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	Common::String getSavegameFile(int saveGameIdx, const char *target = nullptr) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool CineMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSavesUseExtendedFormat);
-}
-
-bool Cine::CineEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool CineMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Cine::CINEGameDescription *gd = (const Cine::CINEGameDescription *)desc;
-	if (gd) {
-		*engine = new Cine::CineEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList CineMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	SaveStateList saveList;
-
-	Common::String pattern;
-
-	Common::StringArray::const_iterator file;
-
-	Common::String filename = target;
-	filename += ".dir";
-	Common::InSaveFile *in = saveFileMan->openForLoading(filename);
-	bool foundAutosave = false;
-	if (in) {
-		typedef char CommandeType[SAVEGAME_NAME_LEN];
-		CommandeType saveNames[MAX_SAVEGAMES];
-
-		// Initialize all savegames' descriptions to empty strings
-		// so that if the savegames' descriptions can only be partially read from file
-		// then the missing ones are correctly set to empty strings.
-		memset(saveNames, 0, sizeof(saveNames));
-
-		in->read(saveNames, SAVELIST_SIZE);
-		CommandeType saveDesc;
-
-		pattern = target;
-		pattern += ".#*";
-		Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
-
-		for (file = filenames.begin(); file != filenames.end(); ++file) {
-			// Obtain the extension part of the filename, since it corresponds to the save slot number
-			Common::String ext = Common::lastPathComponent(*file, '.');
-			int slotNum = (int)ext.asUint64();
-
-			if (ext.equals(Common::String::format("%d", slotNum)) &&
-				slotNum >= 0 && slotNum < MAX_SAVEGAMES) {
-				// Copy the savegame description making sure it ends with a trailing zero
-				strncpy(saveDesc, saveNames[slotNum], SAVEGAME_NAME_LEN);
-				saveDesc[sizeof(CommandeType) - 1] = 0;
-
-				SaveStateDescriptor saveStateDesc(slotNum, saveDesc);
-				saveStateDesc.setAutosave(slotNum == getAutosaveSlot());
-				saveStateDesc.setWriteProtectedFlag(saveStateDesc.isAutosave());
-
-				if (saveStateDesc.getDescription().empty()) {
-					if (saveStateDesc.isAutosave()) {
-						saveStateDesc.setDescription(_("Unnamed autosave"));
-					} else {
-						saveStateDesc.setDescription(_("Unnamed savegame"));
-					}
-				}
-
-				if (saveStateDesc.isAutosave()) {
-					foundAutosave = true;
-				}
-
-				saveList.push_back(saveStateDesc);
-			}
-		}
-	}
-
-	delete in;
-
-	// No saving on empty autosave slot
-	if (!foundAutosave) {
-		SaveStateDescriptor desc;
-		desc.setDescription(_("Empty autosave"));
-		desc.setSaveSlot(getAutosaveSlot());
-		desc.setWriteProtectedFlag(true);
-		saveList.push_back(desc);
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int CineMetaEngine::getMaximumSaveSlot() const { return MAX_SAVEGAMES - 1; }
-
-Common::String CineMetaEngine::getSavegameFile(int saveGameIdx, const char *target) const {
-	return Common::String::format("%s.%d", target == nullptr ? getEngineId() : target, saveGameIdx);
-}
-
-SaveStateDescriptor CineMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	if (slot < 0 || slot > getMaximumSaveSlot()) {
-		// HACK: Try to make SaveLoadChooserGrid::open() not use save slot
-		// numbers over the maximum save slot number for "New save".
-		SaveStateDescriptor desc;
-		desc.setWriteProtectedFlag(true);
-		return desc;
-	}
-
-	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(
-		getSavegameFile(slot, target)));
-
-	if (f) {
-		// Create the return descriptor
-		SaveStateDescriptor desc;
-
-		ExtendedSavegameHeader header;
-		if (readSavegameHeader(f.get(), &header, false)) {
-			parseSavegameHeader(&header, &desc);
-			desc.setThumbnail(header.thumbnail);
-		} else {
-			// Load savegame descriptions from index file
-			typedef char CommandeType[SAVEGAME_NAME_LEN];
-			CommandeType saveNames[MAX_SAVEGAMES];
-			memset(saveNames, 0, sizeof(saveNames));
-
-			Common::InSaveFile *in;
-			in = g_system->getSavefileManager()->openForLoading(Common::String::format("%s.dir", target));
-
-			if (in) {
-				in->read(saveNames, SAVELIST_SIZE);
-				delete in;
-			}
-
-			saveNames[slot][SAVEGAME_NAME_LEN - 1] = 0;
-			Common::String saveNameStr((const char *)saveNames[slot]);
-			desc.setDescription(saveNameStr);
-		}
-
-		if (desc.getDescription().empty()) {
-			desc.setDescription(_("Unnamed savegame"));
-		}
-
-		desc.setSaveSlot(slot);
-		desc.setAutosave(slot == getAutosaveSlot());
-		desc.setWriteProtectedFlag(desc.isAutosave());
-
-		return desc;
-	}
-
-	// No saving on empty autosave slot
-	if (slot == getAutosaveSlot()) {
-		SaveStateDescriptor desc;
-		desc.setDescription(_("Empty autosave"));
-		desc.setSaveSlot(slot);
-		desc.setAutosave(true);		
-		desc.setWriteProtectedFlag(true);
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-void CineMetaEngine::removeSaveState(const char *target, int slot) const {
-	if (slot < 0 || slot >= MAX_SAVEGAMES) {
-		return;
-	}
-
-	// Load savegame descriptions from index file
-	typedef char CommandeType[SAVEGAME_NAME_LEN];
-	CommandeType saveNames[MAX_SAVEGAMES];
-
-	// Initialize all savegames' descriptions to empty strings
-	// so that if the savegames' descriptions can only be partially read from file
-	// then the missing ones are correctly set to empty strings.
-	memset(saveNames, 0, sizeof(saveNames));
-
-	Common::InSaveFile *in;
-	in = g_system->getSavefileManager()->openForLoading(Common::String::format("%s.dir", target));
-
-	if (!in)
-		return;
-
-	in->read(saveNames, SAVELIST_SIZE);
-	delete in;
-
-	// Set description for selected slot
-	char slotName[SAVEGAME_NAME_LEN];
-	slotName[0] = 0;
-	Common::strlcpy(saveNames[slot], slotName, SAVEGAME_NAME_LEN);
-
-	// Update savegame descriptions
-	Common::String indexFile = Common::String::format("%s.dir", target);
-	Common::OutSaveFile *out = g_system->getSavefileManager()->openForSaving(indexFile);
-	if (!out) {
-		warning("Unable to open file %s for saving", indexFile.c_str());
-		return;
-	}
-
-	out->write(saveNames, SAVELIST_SIZE);
-	delete out;
-
-	// Delete save file
-	Common::String saveFileName = getSavegameFile(slot, target);
-
-	g_system->getSavefileManager()->removeSavefile(saveFileName);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(CINE)
-	REGISTER_PLUGIN_DYNAMIC(CINE, PLUGIN_TYPE_ENGINE, CineMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(CINE, PLUGIN_TYPE_ENGINE, CineMetaEngine);
-#endif
-
-namespace Cine {
-
-Common::Error CineEngine::loadGameState(int slot) {
-	bool gameLoaded = makeLoad(getSaveStateName(slot));
-
-	return gameLoaded ? Common::kNoError : Common::kUnknownError;
-}
-
-Common::Error CineEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
-	if (slot < 0 || slot >= MAX_SAVEGAMES) {
-		return Common::kCreatingFileFailed;
-	}
-
-	// Load savegame descriptions from index file
-	loadSaveDirectory();
-
-	// Set description for selected slot making sure it ends with a trailing zero
-	strncpy(currentSaveName[slot], desc.c_str(), sizeof(CommandeType));
-	currentSaveName[slot][sizeof(CommandeType) - 1] = 0;
-
-	// Update savegame descriptions
-	Common::String indexFile = _targetName + ".dir";
-
-	Common::OutSaveFile *fHandle = _saveFileMan->openForSaving(indexFile);
-	if (!fHandle) {
-		warning("Unable to open file %s for saving", indexFile.c_str());
-		return Common::kUnknownError;
-	}
-
-	fHandle->write(currentSaveName, SAVELIST_SIZE);
-	delete fHandle;
-
-	// Save game
-	makeSave(getSaveStateName(slot), getTotalPlayTime() / 1000, desc, isAutosave);
-
-	checkDataDisk(-1);
-
-	return Common::kNoError;
-}
-
-Common::String CineEngine::getSaveStateName(int slot) const {
-	return getMetaEngine().getSavegameFile(slot, _targetName.c_str());
-}
-
-bool CineEngine::canLoadGameStateCurrently() {
-	return (!disableSystemMenu && !inMenu);
-}
-
-bool CineEngine::canSaveGameStateCurrently() {
-	return (allowPlayerInput && !disableSystemMenu && !inMenu);
-}
-
-} // End of namespace Cine
+REGISTER_PLUGIN_STATIC(CINE_DETECTION, PLUGIN_TYPE_METAENGINE, CineMetaEngine);
diff --git a/engines/cine/detection.h b/engines/cine/detection.h
new file mode 100644
index 0000000000..5021d69934
--- /dev/null
+++ b/engines/cine/detection.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Cine {
+
+struct CINEGameDescription {
+	ADGameDescription desc;
+
+	int gameType;
+	uint32 features;
+};
+
+} // End of namespace Cine
diff --git a/engines/cine/detection_enums.h b/engines/cine/detection_enums.h
new file mode 100644
index 0000000000..3acc17b12b
--- /dev/null
+++ b/engines/cine/detection_enums.h
@@ -0,0 +1,37 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Cine {
+
+enum CineGameType {
+	GType_FW = 1,
+	GType_OS
+};
+
+enum CineGameFeatures {
+	GF_CD =   1 << 0,
+	GF_DEMO = 1 << 1,
+	GF_ALT_FONT = 1 << 2,
+	GF_CRYPTED_BOOT_PRC = 1 << 3
+};
+
+} // End of namespace Cine
diff --git a/engines/cine/metaengine.cpp b/engines/cine/metaengine.cpp
new file mode 100644
index 0000000000..12c2d0a7bc
--- /dev/null
+++ b/engines/cine/metaengine.cpp
@@ -0,0 +1,346 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+
+#include "common/system.h"
+#include "common/textconsole.h"
+#include "common/translation.h"
+#include "common/util.h"
+
+#include "cine/cine.h"
+#include "cine/various.h"
+
+#include "cine/detection.h"
+
+namespace Cine {
+
+#define MAX_SAVEGAMES (ARRAYSIZE(Cine::currentSaveName))
+#define SAVEGAME_NAME_LEN (sizeof(Cine::currentSaveName[0]))
+#define SAVELIST_SIZE (MAX_SAVEGAMES * SAVEGAME_NAME_LEN)
+
+bool CineEngine::mayHave256Colors() const { return getGameType() == Cine::GType_OS && getPlatform() == Common::kPlatformDOS; }
+int CineEngine::getGameType() const { return _gameDescription->gameType; }
+uint32 CineEngine::getFeatures() const { return _gameDescription->features; }
+Common::Language CineEngine::getLanguage() const { return _gameDescription->desc.language; }
+Common::Platform CineEngine::getPlatform() const { return _gameDescription->desc.platform; }
+
+} // End of namespace Cine
+
+class CineMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "cine";
+	}
+
+    Common::Error createInstance(OSystem *syst, Engine **engine) const override {
+		return AdvancedMetaEngineConnect::createInstance(syst, engine);
+	}
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	Common::String getSavegameFile(int saveGameIdx, const char *target = nullptr) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool CineMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSavesUseExtendedFormat);
+}
+
+bool Cine::CineEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool CineMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Cine::CINEGameDescription *gd = (const Cine::CINEGameDescription *)desc;
+	if (gd) {
+		*engine = new Cine::CineEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList CineMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	SaveStateList saveList;
+
+	Common::String pattern;
+
+	Common::StringArray::const_iterator file;
+
+	Common::String filename = target;
+	filename += ".dir";
+	Common::InSaveFile *in = saveFileMan->openForLoading(filename);
+	bool foundAutosave = false;
+	if (in) {
+		typedef char CommandeType[SAVEGAME_NAME_LEN];
+		CommandeType saveNames[MAX_SAVEGAMES];
+
+		// Initialize all savegames' descriptions to empty strings
+		// so that if the savegames' descriptions can only be partially read from file
+		// then the missing ones are correctly set to empty strings.
+		memset(saveNames, 0, sizeof(saveNames));
+
+		in->read(saveNames, SAVELIST_SIZE);
+		CommandeType saveDesc;
+
+		pattern = target;
+		pattern += ".#*";
+		Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
+
+		for (file = filenames.begin(); file != filenames.end(); ++file) {
+			// Obtain the extension part of the filename, since it corresponds to the save slot number
+			Common::String ext = Common::lastPathComponent(*file, '.');
+			int slotNum = (int)ext.asUint64();
+
+			if (ext.equals(Common::String::format("%d", slotNum)) &&
+				slotNum >= 0 && slotNum < MAX_SAVEGAMES) {
+				// Copy the savegame description making sure it ends with a trailing zero
+				strncpy(saveDesc, saveNames[slotNum], SAVEGAME_NAME_LEN);
+				saveDesc[sizeof(CommandeType) - 1] = 0;
+
+				SaveStateDescriptor saveStateDesc(slotNum, saveDesc);
+				saveStateDesc.setAutosave(slotNum == getAutosaveSlot());
+				saveStateDesc.setWriteProtectedFlag(saveStateDesc.isAutosave());
+
+				if (saveStateDesc.getDescription().empty()) {
+					if (saveStateDesc.isAutosave()) {
+						saveStateDesc.setDescription(_("Unnamed autosave"));
+					} else {
+						saveStateDesc.setDescription(_("Unnamed savegame"));
+					}
+				}
+
+				if (saveStateDesc.isAutosave()) {
+					foundAutosave = true;
+				}
+
+				saveList.push_back(saveStateDesc);
+			}
+		}
+	}
+
+	delete in;
+
+	// No saving on empty autosave slot
+	if (!foundAutosave) {
+		SaveStateDescriptor desc;
+		desc.setDescription(_("Empty autosave"));
+		desc.setSaveSlot(getAutosaveSlot());
+		desc.setWriteProtectedFlag(true);
+		saveList.push_back(desc);
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int CineMetaEngineConnect::getMaximumSaveSlot() const { return MAX_SAVEGAMES - 1; }
+
+Common::String CineMetaEngineConnect::getSavegameFile(int saveGameIdx, const char *target) const {
+	return Common::String::format("%s.%d", target == nullptr ? getEngineId() : target, saveGameIdx);
+}
+
+SaveStateDescriptor CineMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	if (slot < 0 || slot > getMaximumSaveSlot()) {
+		// HACK: Try to make SaveLoadChooserGrid::open() not use save slot
+		// numbers over the maximum save slot number for "New save".
+		SaveStateDescriptor desc;
+		desc.setWriteProtectedFlag(true);
+		return desc;
+	}
+
+	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(
+		getSavegameFile(slot, target)));
+
+	if (f) {
+		// Create the return descriptor
+		SaveStateDescriptor desc;
+
+		ExtendedSavegameHeader header;
+		if (readSavegameHeader(f.get(), &header, false)) {
+			parseSavegameHeader(&header, &desc);
+			desc.setThumbnail(header.thumbnail);
+		} else {
+			// Load savegame descriptions from index file
+			typedef char CommandeType[SAVEGAME_NAME_LEN];
+			CommandeType saveNames[MAX_SAVEGAMES];
+			memset(saveNames, 0, sizeof(saveNames));
+
+			Common::InSaveFile *in;
+			in = g_system->getSavefileManager()->openForLoading(Common::String::format("%s.dir", target));
+
+			if (in) {
+				in->read(saveNames, SAVELIST_SIZE);
+				delete in;
+			}
+
+			saveNames[slot][SAVEGAME_NAME_LEN - 1] = 0;
+			Common::String saveNameStr((const char *)saveNames[slot]);
+			desc.setDescription(saveNameStr);
+		}
+
+		if (desc.getDescription().empty()) {
+			desc.setDescription(_("Unnamed savegame"));
+		}
+
+		desc.setSaveSlot(slot);
+		desc.setAutosave(slot == getAutosaveSlot());
+		desc.setWriteProtectedFlag(desc.isAutosave());
+
+		return desc;
+	}
+
+	// No saving on empty autosave slot
+	if (slot == getAutosaveSlot()) {
+		SaveStateDescriptor desc;
+		desc.setDescription(_("Empty autosave"));
+		desc.setSaveSlot(slot);
+		desc.setAutosave(true);		
+		desc.setWriteProtectedFlag(true);
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+void CineMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	if (slot < 0 || slot >= MAX_SAVEGAMES) {
+		return;
+	}
+
+	// Load savegame descriptions from index file
+	typedef char CommandeType[SAVEGAME_NAME_LEN];
+	CommandeType saveNames[MAX_SAVEGAMES];
+
+	// Initialize all savegames' descriptions to empty strings
+	// so that if the savegames' descriptions can only be partially read from file
+	// then the missing ones are correctly set to empty strings.
+	memset(saveNames, 0, sizeof(saveNames));
+
+	Common::InSaveFile *in;
+	in = g_system->getSavefileManager()->openForLoading(Common::String::format("%s.dir", target));
+
+	if (!in)
+		return;
+
+	in->read(saveNames, SAVELIST_SIZE);
+	delete in;
+
+	// Set description for selected slot
+	char slotName[SAVEGAME_NAME_LEN];
+	slotName[0] = 0;
+	Common::strlcpy(saveNames[slot], slotName, SAVEGAME_NAME_LEN);
+
+	// Update savegame descriptions
+	Common::String indexFile = Common::String::format("%s.dir", target);
+	Common::OutSaveFile *out = g_system->getSavefileManager()->openForSaving(indexFile);
+	if (!out) {
+		warning("Unable to open file %s for saving", indexFile.c_str());
+		return;
+	}
+
+	out->write(saveNames, SAVELIST_SIZE);
+	delete out;
+
+	// Delete save file
+	Common::String saveFileName = getSavegameFile(slot, target);
+
+	g_system->getSavefileManager()->removeSavefile(saveFileName);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(CINE)
+	REGISTER_PLUGIN_DYNAMIC(CINE, PLUGIN_TYPE_ENGINE, CineMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(CINE, PLUGIN_TYPE_ENGINE, CineMetaEngineConnect);
+#endif
+
+namespace Cine {
+
+Common::Error CineEngine::loadGameState(int slot) {
+	bool gameLoaded = makeLoad(getSaveStateName(slot));
+
+	return gameLoaded ? Common::kNoError : Common::kUnknownError;
+}
+
+Common::Error CineEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
+	if (slot < 0 || slot >= MAX_SAVEGAMES) {
+		return Common::kCreatingFileFailed;
+	}
+
+	// Load savegame descriptions from index file
+	loadSaveDirectory();
+
+	// Set description for selected slot making sure it ends with a trailing zero
+	strncpy(currentSaveName[slot], desc.c_str(), sizeof(CommandeType));
+	currentSaveName[slot][sizeof(CommandeType) - 1] = 0;
+
+	// Update savegame descriptions
+	Common::String indexFile = _targetName + ".dir";
+
+	Common::OutSaveFile *fHandle = _saveFileMan->openForSaving(indexFile);
+	if (!fHandle) {
+		warning("Unable to open file %s for saving", indexFile.c_str());
+		return Common::kUnknownError;
+	}
+
+	fHandle->write(currentSaveName, SAVELIST_SIZE);
+	delete fHandle;
+
+	// Save game
+	makeSave(getSaveStateName(slot), getTotalPlayTime() / 1000, desc, isAutosave);
+
+	checkDataDisk(-1);
+
+	return Common::kNoError;
+}
+
+Common::String CineEngine::getSaveStateName(int slot) const {
+	return getMetaEngineConnect().getSavegameFile(slot, _targetName.c_str());
+}
+
+bool CineEngine::canLoadGameStateCurrently() {
+	return (!disableSystemMenu && !inMenu);
+}
+
+bool CineEngine::canSaveGameStateCurrently() {
+	return (allowPlayerInput && !disableSystemMenu && !inMenu);
+}
+
+} // End of namespace Cine
+
diff --git a/engines/cine/module.mk b/engines/cine/module.mk
index 6e77449c59..510d3d0043 100644
--- a/engines/cine/module.mk
+++ b/engines/cine/module.mk
@@ -6,9 +6,9 @@ MODULE_OBJS := \
 	bg_list.o \
 	console.o \
 	cine.o \
-	detection.o \
 	gfx.o \
 	main_loop.o \
+	metaengine.o \
 	msg.o \
 	object.o \
 	pal.o \
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cine/saveload.cpp b/engines/cine/saveload.cpp
index 6b03f4fcd3..f5cd98cb7a 100644
--- a/engines/cine/saveload.cpp
+++ b/engines/cine/saveload.cpp
@@ -879,7 +879,7 @@ bool CineEngine::makeLoad(const Common::String &saveName) {
 		}
 
 		ExtendedSavegameHeader header;
-		if (MetaEngine::readSavegameHeader(saveFile.get(), &header)) {
+		if (MetaEngineConnect::readSavegameHeader(saveFile.get(), &header)) {
 			setTotalPlayTime(header.playtime * 1000); // Seconds to milliseconds
 		}
 	}
@@ -1030,7 +1030,7 @@ void CineEngine::makeSave(const Common::String &saveFileName, uint32 playtime,
 		renderer->popSavedBackBuffer(BEFORE_OPENING_MENU);
 	}
 
-	MetaEngine::appendExtendedSave(fHandle.get(), playtime, desc, isAutosave);
+	MetaEngineConnect::appendExtendedSave(fHandle.get(), playtime, desc, isAutosave);
 
 	renderer->restoreSavedBackBuffer(BEFORE_TAKING_THUMBNAIL);
 


Commit: 2712bccff6811818869c1c370638468fd51a692d
    https://github.com/scummvm/scummvm/commit/2712bccff6811818869c1c370638468fd51a692d
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CRUISE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/cruise/detection.h
  A engines/cruise/metaengine.cpp
    configure
    engines/cruise/detection.cpp
    engines/cruise/module.mk


diff --git a/configure b/configure
index 34dd47418d..ff2a5ba60b 100755
--- a/configure
+++ b/configure
@@ -6169,7 +6169,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
-								  "BLADERUNNER" "CHEWY" "CINE")
+								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/cruise/detection.cpp b/engines/cruise/detection.cpp
index 03c20fbfc0..b47cdb59ee 100644
--- a/engines/cruise/detection.cpp
+++ b/engines/cruise/detection.cpp
@@ -21,31 +21,9 @@
  */
 
 #include "base/plugins.h"
-#include "common/savefile.h"
-#include "common/system.h"
 #include "engines/advancedDetector.h"
 
-#include "cruise/cruise.h"
-#include "cruise/saveload.h"
-
-namespace Cruise {
-
-struct CRUISEGameDescription {
-	ADGameDescription desc;
-};
-
-const char *CruiseEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-Common::Language CruiseEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-Common::Platform CruiseEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-}
+#include "cruise/detection.h"
 
 static const PlainGameDescriptor cruiseGames[] = {
 	{"cruise", "Cruise for a Corpse"},
@@ -209,90 +187,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Cinematique evo 2 (C) Delphine Software";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	int getMaximumSaveSlot() const override { return 99; }
-	SaveStateList listSaves(const char *target) const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool CruiseMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSupportsLoadingDuringStartup);
-}
-
-SaveStateList CruiseMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern("cruise.s##");
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-
-		if (slotNum >= 0 && slotNum <= 99) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				Cruise::CruiseSavegameHeader header;
-				if (Cruise::readSavegameHeader(in, header))
-					saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void CruiseMetaEngine::removeSaveState(const char *target, int slot) const {
-	g_system->getSavefileManager()->removeSavefile(Cruise::CruiseEngine::getSavegameFile(slot));
-}
-
-SaveStateDescriptor CruiseMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(
-		Cruise::CruiseEngine::getSavegameFile(slot));
-
-	if (f) {
-		Cruise::CruiseSavegameHeader header;
-		if (!Cruise::readSavegameHeader(f, header, false)) {
-			delete f;
-			return SaveStateDescriptor();
-		}
-
-		delete f;
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header.saveName);
-		desc.setThumbnail(header.thumbnail);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-bool CruiseMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Cruise::CRUISEGameDescription *gd = (const Cruise::CRUISEGameDescription *)desc;
-	if (gd) {
-		*engine = new Cruise::CruiseEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-
-#if PLUGIN_ENABLED_DYNAMIC(CRUISE)
-	REGISTER_PLUGIN_DYNAMIC(CRUISE, PLUGIN_TYPE_ENGINE, CruiseMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(CRUISE, PLUGIN_TYPE_ENGINE, CruiseMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(CRUISE_DETECTION, PLUGIN_TYPE_METAENGINE, CruiseMetaEngine);
diff --git a/engines/cruise/detection.h b/engines/cruise/detection.h
new file mode 100644
index 0000000000..6953a3a0b6
--- /dev/null
+++ b/engines/cruise/detection.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Cruise {
+
+struct CRUISEGameDescription {
+	ADGameDescription desc;
+};
+
+} // End of namespace Cruise
diff --git a/engines/cruise/metaengine.cpp b/engines/cruise/metaengine.cpp
new file mode 100644
index 0000000000..83abf985fe
--- /dev/null
+++ b/engines/cruise/metaengine.cpp
@@ -0,0 +1,138 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+#include "common/savefile.h"
+#include "common/system.h"
+#include "engines/advancedDetector.h"
+
+#include "cruise/cruise.h"
+#include "cruise/saveload.h"
+#include "cruise/detection.h"
+
+namespace Cruise {
+
+const char *CruiseEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+Common::Language CruiseEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+Common::Platform CruiseEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+} // End of namespace Cruise
+
+class CruiseMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "cruise";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	int getMaximumSaveSlot() const override { return 99; }
+
+	SaveStateList listSaves(const char *target) const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool CruiseMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSupportsLoadingDuringStartup);
+}
+
+SaveStateList CruiseMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern("cruise.s##");
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+
+		if (slotNum >= 0 && slotNum <= 99) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				Cruise::CruiseSavegameHeader header;
+				if (Cruise::readSavegameHeader(in, header))
+					saveList.push_back(SaveStateDescriptor(slotNum, header.saveName));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void CruiseMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	g_system->getSavefileManager()->removeSavefile(Cruise::CruiseEngine::getSavegameFile(slot));
+}
+
+SaveStateDescriptor CruiseMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(
+		Cruise::CruiseEngine::getSavegameFile(slot));
+
+	if (f) {
+		Cruise::CruiseSavegameHeader header;
+		if (!Cruise::readSavegameHeader(f, header, false)) {
+			delete f;
+			return SaveStateDescriptor();
+		}
+
+		delete f;
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header.saveName);
+		desc.setThumbnail(header.thumbnail);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+bool CruiseMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Cruise::CRUISEGameDescription *gd = (const Cruise::CRUISEGameDescription *)desc;
+	if (gd) {
+		*engine = new Cruise::CruiseEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(CRUISE)
+	REGISTER_PLUGIN_DYNAMIC(CRUISE, PLUGIN_TYPE_ENGINE, CruiseMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(CRUISE, PLUGIN_TYPE_ENGINE, CruiseMetaEngineConnect);
+#endif
diff --git a/engines/cruise/module.mk b/engines/cruise/module.mk
index ae07d20956..8487ff3ff0 100644
--- a/engines/cruise/module.mk
+++ b/engines/cruise/module.mk
@@ -12,13 +12,13 @@ MODULE_OBJS := \
 	debugger.o \
 	decompiler.o \
 	delphine-unpack.o \
-	detection.o \
 	font.o \
 	function.o \
 	gfxModule.o \
 	linker.o \
 	mainDraw.o \
 	menu.o \
+	metaengine.o \
 	mouse.o \
 	object.o \
 	overlay.o \
@@ -40,3 +40,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: fb458421cfd18b67c0a047bfabd0f9f1b824995c
    https://github.com/scummvm/scummvm/commit/fb458421cfd18b67c0a047bfabd0f9f1b824995c
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CRYO: Split detection features & adapt to new plugins.

Changed paths:
  A engines/cryo/metaengine.cpp
    configure
    engines/cryo/detection.cpp
    engines/cryo/module.mk


diff --git a/configure b/configure
index ff2a5ba60b..7672173232 100755
--- a/configure
+++ b/configure
@@ -6169,7 +6169,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
-								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE")
+								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/cryo/detection.cpp b/engines/cryo/detection.cpp
index 09aff0c7fe..37b1d60a08 100644
--- a/engines/cryo/detection.cpp
+++ b/engines/cryo/detection.cpp
@@ -23,18 +23,7 @@
 #include "base/plugins.h"
 
 #include "engines/advancedDetector.h"
-#include "common/file.h"
 
-#include "cryo/cryo.h"
-
-
-namespace Cryo {
-
-const char *CryoEngine::getGameId() const { return _gameDescription->gameId; }
-bool CryoEngine::isDemo() const { return _gameDescription->flags & ADGF_DEMO; }
-Common::Platform CryoEngine::getPlatform() const { return _gameDescription->platform; }
-
-}
 
 static const PlainGameDescriptor cryoGames[] = {
 	{"losteden", "Lost Eden"},
@@ -146,24 +135,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Cryo Engine (C) Cryo Interactive";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool CryoMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return false;
-}
-
-bool CryoMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Cryo::CryoEngine(syst, desc);
-	}
-	return desc != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(CRYO)
-REGISTER_PLUGIN_DYNAMIC(CRYO, PLUGIN_TYPE_ENGINE, CryoMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(CRYO, PLUGIN_TYPE_ENGINE, CryoMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(CRYO_DETECTION, PLUGIN_TYPE_METAENGINE, CryoMetaEngine);
diff --git a/engines/cryo/metaengine.cpp b/engines/cryo/metaengine.cpp
new file mode 100644
index 0000000000..428b41d1c3
--- /dev/null
+++ b/engines/cryo/metaengine.cpp
@@ -0,0 +1,64 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+#include "common/file.h"
+
+#include "cryo/cryo.h"
+
+namespace Cryo {
+
+const char *CryoEngine::getGameId() const { return _gameDescription->gameId; }
+bool CryoEngine::isDemo() const { return _gameDescription->flags & ADGF_DEMO; }
+Common::Platform CryoEngine::getPlatform() const { return _gameDescription->platform; }
+
+} // End of namespace Cryo
+
+class CryoMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "cryo";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool CryoMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return false;
+}
+
+bool CryoMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Cryo::CryoEngine(syst, desc);
+	}
+	return desc != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(CRYO)
+	REGISTER_PLUGIN_DYNAMIC(CRYO, PLUGIN_TYPE_ENGINE, CryoMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(CRYO, PLUGIN_TYPE_ENGINE, CryoMetaEngineConnect);
+#endif
+
diff --git a/engines/cryo/module.mk b/engines/cryo/module.mk
index c8d3f8e7df..11227ac5ee 100644
--- a/engines/cryo/module.mk
+++ b/engines/cryo/module.mk
@@ -4,9 +4,9 @@ MODULE_OBJS = \
 	cryo.o \
 	cryolib.o \
 	debugger.o \
-	detection.o \
 	eden.o \
 	eden_graphics.o \
+	metaengine.o \
 	resource.o \
 	sound.o \
 	video.o
@@ -18,3 +18,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: e9ad5efad1fee37bc6bd06f0707ae4a3db1dc995
    https://github.com/scummvm/scummvm/commit/e9ad5efad1fee37bc6bd06f0707ae4a3db1dc995
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CRYOMNI3D: Split detection features & adapt to new plugins.

Changed paths:
  A engines/cryomni3d/detection.h
  A engines/cryomni3d/detection_enums.h
  A engines/cryomni3d/metaengine.cpp
    configure
    engines/cryomni3d/cryomni3d.h
    engines/cryomni3d/detection.cpp
    engines/cryomni3d/module.mk


diff --git a/configure b/configure
index 7672173232..b687a56688 100755
--- a/configure
+++ b/configure
@@ -6169,7 +6169,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
-								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO")
+								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/cryomni3d/cryomni3d.h b/engines/cryomni3d/cryomni3d.h
index 716ba11de3..d0dad279cf 100644
--- a/engines/cryomni3d/cryomni3d.h
+++ b/engines/cryomni3d/cryomni3d.h
@@ -38,6 +38,7 @@
 #include "cryomni3d/font_manager.h"
 #include "cryomni3d/objects.h"
 #include "cryomni3d/sprites.h"
+#include "cryomni3d/detection_enums.h"
 
 class OSystem;
 
@@ -63,24 +64,6 @@ namespace CryOmni3D {
 
 class DATSeekableStream;
 
-enum CryOmni3DGameType {
-	GType_VERSAILLES
-};
-
-enum CryOmni3DGameFeatures {
-	GF_VERSAILLES_FONTS_MASK               = (3 << 0), // Fonts flag mask
-	GF_VERSAILLES_FONTS_NUMERIC            = (0 << 0), // Fonts are font01.crf, ...
-	GF_VERSAILLES_FONTS_SET_A              = (1 << 0), // Fonts are for French Macintosh (development version)
-	GF_VERSAILLES_FONTS_SET_B              = (2 << 0), // Standard set (Helvet12 is used for debugging docs)
-	GF_VERSAILLES_FONTS_SET_C              = (3 << 0), // Fonts for Italian version (Helvet12 is used for docs texts)
-
-	GF_VERSAILLES_AUDIOPADDING_NO          = (0 << 2), // Audio files have underscore padding before extension
-	GF_VERSAILLES_AUDIOPADDING_YES         = (1 << 2), // Audio files have underscore padding before extension
-
-	GF_VERSAILLES_LINK_STANDARD            = (0 << 3), // Links file is lien_doc.txt
-	GF_VERSAILLES_LINK_LOCALIZED           = (1 << 3)  // Links file is taken from cryomni3d.dat
-};
-
 struct CryOmni3DGameDescription;
 
 // Engine Debug Flags
diff --git a/engines/cryomni3d/detection.cpp b/engines/cryomni3d/detection.cpp
index da307b9c49..bc969065b8 100644
--- a/engines/cryomni3d/detection.cpp
+++ b/engines/cryomni3d/detection.cpp
@@ -23,53 +23,15 @@
 #include "base/plugins.h"
 
 #include "engines/advancedDetector.h"
+
 #include "common/file.h"
 #include "common/md5.h"
-#include "common/savefile.h"
-#include "common/system.h"
-#include "common/textconsole.h"
-
-#include "cryomni3d/cryomni3d.h"
 
-#ifdef ENABLE_VERSAILLES
-#include "cryomni3d/versailles/engine.h"
-#endif
+#include "cryomni3d/detection.h"
+#include "cryomni3d/detection_enums.h"
 
 namespace CryOmni3D {
 
-struct CryOmni3DGameDescription {
-	ADGameDescription desc;
-
-	uint8 gameType;
-	uint32 features;
-};
-
-const char *CryOmni3DEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-uint32 CryOmni3DEngine::getFeatures() const {
-	return _gameDescription->features;
-}
-
-Common::Platform CryOmni3DEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-uint8 CryOmni3DEngine::getGameType() const {
-	return _gameDescription->gameType;
-}
-
-Common::Language CryOmni3DEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-bool CryOmni3DEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher)
-		|| (f == kSupportsSubtitleOptions);
-}
-
 static const PlainGameDescriptor cryomni3DGames[] = {
 	{"versailles", "Versailles 1685"},
 	{0, 0}
@@ -105,88 +67,8 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Cryo game Engine (C) 1997-2002 Cryo Interactive";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override { return 999; }
-	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool CryOmni3DMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves)
-		|| (f == kSupportsLoadingDuringStartup)
-		|| (f == kSupportsDeleteSave)
-		|| (f == kSimpleSavesNames);
-}
-
-SaveStateList CryOmni3DMetaEngine::listSaves(const char *target) const {
-	// Replicate constant here to shorten lines
-	static const uint kSaveDescriptionLen = CryOmni3DEngine::kSaveDescriptionLen;
-	SaveStateList saveList;
-
-	Common::SaveFileManager *saveMan = g_system->getSavefileManager();
-
-	char saveName[kSaveDescriptionLen + 1];
-	saveName[kSaveDescriptionLen] = '\0';
-	Common::String pattern = Common::String::format("%s.????", target);
-	Common::StringArray filenames = saveMan->listSavefiles(pattern);
-	sort(filenames.begin(), filenames.end());   // Sort (hopefully ensuring we are sorted numerically..)
-
-	int slotNum;
-
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end();
-			++file) {
-		// Obtain the last 4 digits of the filename, since they correspond to the save slot
-		slotNum = atoi(file->c_str() + file->size() - 4);
-
-		if (slotNum >= 1 && slotNum <= 99) {
-			Common::InSaveFile *in = saveMan->openForLoading(*file);
-			if (in) {
-				if (in->read(saveName, kSaveDescriptionLen) == kSaveDescriptionLen) {
-					saveList.push_back(SaveStateDescriptor(slotNum - 1, saveName));
-				}
-				delete in;
-			}
-		}
-	}
-
-	return saveList;
-}
-
-void CryOmni3DMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%04d", target, slot + 1);
-
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-bool CryOmni3DMetaEngine::createInstance(OSystem *syst, Engine **engine,
-		const ADGameDescription *desc) const {
-	const CryOmni3DGameDescription *gd = (const CryOmni3DGameDescription *)desc;
-
-	if (gd) {
-		switch (gd->gameType) {
-		case GType_VERSAILLES:
-#ifdef ENABLE_VERSAILLES
-			*engine = new Versailles::CryOmni3DEngine_Versailles(syst, gd);
-			break;
-#else
-			warning("Versailles support not compiled in");
-			return false;
-#endif
-		default:
-			error("Unknown Cryo Omni3D Engine");
-		}
-	}
-
-	return (gd != 0);
-}
-
 } // End of Namespace CryOmni3D
 
-#if PLUGIN_ENABLED_DYNAMIC(CRYOMNI3D)
-REGISTER_PLUGIN_DYNAMIC(CRYOMNI3D, PLUGIN_TYPE_ENGINE, CryOmni3D::CryOmni3DMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(CRYOMNI3D, PLUGIN_TYPE_ENGINE, CryOmni3D::CryOmni3DMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(CRYOMNI3D_DETECTION, PLUGIN_TYPE_METAENGINE, CryOmni3D::CryOmni3DMetaEngine);
diff --git a/engines/cryomni3d/detection.h b/engines/cryomni3d/detection.h
new file mode 100644
index 0000000000..4d3684b6ea
--- /dev/null
+++ b/engines/cryomni3d/detection.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace CryOmni3D {
+
+struct CryOmni3DGameDescription {
+	ADGameDescription desc;
+
+	uint8 gameType;
+	uint32 features;
+};
+
+} // End of namespace CryOmni3D
diff --git a/engines/cryomni3d/detection_enums.h b/engines/cryomni3d/detection_enums.h
new file mode 100644
index 0000000000..cf6ea30ef2
--- /dev/null
+++ b/engines/cryomni3d/detection_enums.h
@@ -0,0 +1,43 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace CryOmni3D {
+
+enum CryOmni3DGameType {
+	GType_VERSAILLES
+};
+
+enum CryOmni3DGameFeatures {
+	GF_VERSAILLES_FONTS_MASK               = (3 << 0), // Fonts flag mask
+	GF_VERSAILLES_FONTS_NUMERIC            = (0 << 0), // Fonts are font01.crf, ...
+	GF_VERSAILLES_FONTS_SET_A              = (1 << 0), // Fonts are for French Macintosh (development version)
+	GF_VERSAILLES_FONTS_SET_B              = (2 << 0), // Standard set (Helvet12 is used for debugging docs)
+	GF_VERSAILLES_FONTS_SET_C              = (3 << 0), // Fonts for Italian version (Helvet12 is used for docs texts)
+
+	GF_VERSAILLES_AUDIOPADDING_NO          = (0 << 2), // Audio files have underscore padding before extension
+	GF_VERSAILLES_AUDIOPADDING_YES         = (1 << 2), // Audio files have underscore padding before extension
+
+	GF_VERSAILLES_LINK_STANDARD            = (0 << 3), // Links file is lien_doc.txt
+	GF_VERSAILLES_LINK_LOCALIZED           = (1 << 3)  // Links file is taken from cryomni3d.dat
+};
+
+} // End of namespace CryOmni3D
diff --git a/engines/cryomni3d/metaengine.cpp b/engines/cryomni3d/metaengine.cpp
new file mode 100644
index 0000000000..edf688c661
--- /dev/null
+++ b/engines/cryomni3d/metaengine.cpp
@@ -0,0 +1,160 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+#include "common/file.h"
+#include "common/md5.h"
+#include "common/savefile.h"
+#include "common/system.h"
+#include "common/textconsole.h"
+#include "common/translation.h"
+
+#include "cryomni3d/cryomni3d.h"
+
+#ifdef ENABLE_VERSAILLES
+#include "cryomni3d/versailles/engine.h"
+#endif
+
+#include "cryomni3d/detection.h"
+
+namespace CryOmni3D {
+
+const char *CryOmni3DEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+uint32 CryOmni3DEngine::getFeatures() const {
+	return _gameDescription->features;
+}
+
+Common::Platform CryOmni3DEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+uint8 CryOmni3DEngine::getGameType() const {
+	return _gameDescription->gameType;
+}
+
+Common::Language CryOmni3DEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+bool CryOmni3DEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher)
+		|| (f == kSupportsSubtitleOptions);
+}
+
+
+class CryOmni3DMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "cryomni3d";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override { return 999; }
+	void removeSaveState(const char *target, int slot) const override;
+};
+
+bool CryOmni3DMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves)
+		|| (f == kSupportsLoadingDuringStartup)
+		|| (f == kSupportsDeleteSave)
+		|| (f == kSimpleSavesNames);
+}
+
+SaveStateList CryOmni3DMetaEngineConnect::listSaves(const char *target) const {
+	// Replicate constant here to shorten lines
+	static const uint kSaveDescriptionLen = CryOmni3DEngine::kSaveDescriptionLen;
+	SaveStateList saveList;
+
+	Common::SaveFileManager *saveMan = g_system->getSavefileManager();
+
+	char saveName[kSaveDescriptionLen + 1];
+	saveName[kSaveDescriptionLen] = '\0';
+	Common::String pattern = Common::String::format("%s.????", target);
+	Common::StringArray filenames = saveMan->listSavefiles(pattern);
+	sort(filenames.begin(), filenames.end());   // Sort (hopefully ensuring we are sorted numerically..)
+
+	int slotNum;
+
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end();
+			++file) {
+		// Obtain the last 4 digits of the filename, since they correspond to the save slot
+		slotNum = atoi(file->c_str() + file->size() - 4);
+
+		if (slotNum >= 1 && slotNum <= 99) {
+			Common::InSaveFile *in = saveMan->openForLoading(*file);
+			if (in) {
+				if (in->read(saveName, kSaveDescriptionLen) == kSaveDescriptionLen) {
+					saveList.push_back(SaveStateDescriptor(slotNum - 1, saveName));
+				}
+				delete in;
+			}
+		}
+	}
+
+	return saveList;
+}
+
+void CryOmni3DMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%04d", target, slot + 1);
+
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+bool CryOmni3DMetaEngineConnect::createInstance(OSystem *syst, Engine **engine,
+		const ADGameDescription *desc) const {
+	const CryOmni3DGameDescription *gd = (const CryOmni3DGameDescription *)desc;
+
+	if (gd) {
+		switch (gd->gameType) {
+		case GType_VERSAILLES:
+#ifdef ENABLE_VERSAILLES
+			*engine = new Versailles::CryOmni3DEngine_Versailles(syst, gd);
+			break;
+#else
+			warning("Versailles support not compiled in");
+			return false;
+#endif
+		default:
+			error("Unknown Cryo Omni3D Engine");
+		}
+	}
+
+	return (gd != 0);
+}
+
+} // End of namespace CryOmni3D
+
+#if PLUGIN_ENABLED_DYNAMIC(CRYOMNI3D)
+	REGISTER_PLUGIN_DYNAMIC(CRYOMNI3D, PLUGIN_TYPE_ENGINE, CryOmni3D::CryOmni3DMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(CRYOMNI3D, PLUGIN_TYPE_ENGINE, CryOmni3D::CryOmni3DMetaEngineConnect);
+#endif
diff --git a/engines/cryomni3d/module.mk b/engines/cryomni3d/module.mk
index 266a6e93da..2b8ed9dc7e 100644
--- a/engines/cryomni3d/module.mk
+++ b/engines/cryomni3d/module.mk
@@ -8,10 +8,10 @@ MODULE_OBJS = \
 	video/hnm_decoder.o \
 	cryomni3d.o \
 	datstream.o \
-	detection.o \
 	dialogs_manager.o \
 	fixed_image.o \
 	font_manager.o \
+	metaengine.o \
 	mouse_boxes.o \
 	objects.o \
 	omni3d.o \
@@ -39,3 +39,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 7944a7b0392254720b133a47a8188819b60d690e
    https://github.com/scummvm/scummvm/commit/7944a7b0392254720b133a47a8188819b60d690e
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DIRECTOR: Split detection features & adapt to new plugins.

Changed paths:
  A engines/director/detection.h
  A engines/director/detection_enums.h
  A engines/director/metaengine.cpp
    configure
    engines/director/detection.cpp
    engines/director/director.h
    engines/director/module.mk


diff --git a/configure b/configure
index b687a56688..bc0fbe0180 100755
--- a/configure
+++ b/configure
@@ -6169,7 +6169,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
-								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D")
+								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/director/detection.cpp b/engines/director/detection.cpp
index a95fcd6200..662ee94b83 100644
--- a/engines/director/detection.cpp
+++ b/engines/director/detection.cpp
@@ -25,72 +25,9 @@
 #include "engines/advancedDetector.h"
 
 #include "common/file.h"
-#include "common/config-manager.h"
 
-#include "director/director.h"
-
-namespace Director {
-
-struct DirectorGameDescription {
-	ADGameDescription desc;
-
-	DirectorGameGID gameGID;
-	uint16 version;
-};
-
-DirectorGameGID DirectorEngine::getGameGID() const {
-	return _gameDescription->gameGID;
-}
-
-const char *DirectorEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-Common::Platform DirectorEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-uint16 DirectorEngine::getDescriptionVersion() const {
-	return _gameDescription->version;
-}
-
-Common::Language DirectorEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-const char *DirectorEngine::getExtra() {
-	return _gameDescription->desc.extra;
-}
-
-Common::String DirectorEngine::getEXEName() const {
-	StartMovie startMovie = getStartMovie();
-	if (startMovie.startMovie.size() > 0)
-		return startMovie.startMovie;
-
-	return _gameDescription->desc.filesDescriptions[0].fileName;
-}
-
-StartMovie DirectorEngine::getStartMovie() const {
-	StartMovie startMovie;
-	startMovie.startFrame = -1;
-
-	if (ConfMan.hasKey("start_movie")) {
-		Common::String option = ConfMan.get("start_movie");
-		int atPos = option.findLastOf("@");
-		startMovie.startMovie = option.substr(0, atPos);
-		Common::String tail = option.substr(atPos + 1, option.size());
-		if (tail.size() > 0)
-			startMovie.startFrame = atoi(tail.c_str());
-	}
-	return startMovie;
-}
-
-bool DirectorEngine::hasFeature(EngineFeature f) const {
-	return false;
-		//(f == kSupportsReturnToLauncher);
-}
-
-} // End of Namespace Director
+#include "director/detection_enums.h"
+#include "director/detection.h"
 
 static const PlainGameDescriptor directorGames[] = {
 	{ "director",			"Macromedia Director Game" },
@@ -258,18 +195,8 @@ public:
 	}
 
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool DirectorMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Director::DirectorGameDescription *gd = (const Director::DirectorGameDescription *)desc;
-
-	if (gd)
-		*engine = new Director::DirectorEngine(syst, gd);
-
-	return (gd != 0);
-}
-
 static Director::DirectorGameDescription s_fallbackDesc = {
 	{
 		"director",
@@ -395,8 +322,4 @@ ADDetectedGame DirectorMetaEngine::fallbackDetect(const FileMap &allFiles, const
 	return ADDetectedGame();
 }
 
-#if PLUGIN_ENABLED_DYNAMIC(DIRECTOR)
-	REGISTER_PLUGIN_DYNAMIC(DIRECTOR, PLUGIN_TYPE_ENGINE, DirectorMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(DIRECTOR, PLUGIN_TYPE_ENGINE, DirectorMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(DIRECTOR_DETECTION, PLUGIN_TYPE_METAENGINE, DirectorMetaEngine);
diff --git a/engines/director/detection.h b/engines/director/detection.h
new file mode 100644
index 0000000000..2f15963e2b
--- /dev/null
+++ b/engines/director/detection.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Director {
+
+struct DirectorGameDescription {
+	ADGameDescription desc;
+
+	DirectorGameGID gameGID;
+	uint16 version;
+};
+
+} // End of namespace Director
diff --git a/engines/director/detection_enums.h b/engines/director/detection_enums.h
new file mode 100644
index 0000000000..0be492a98a
--- /dev/null
+++ b/engines/director/detection_enums.h
@@ -0,0 +1,31 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Director {
+
+enum DirectorGameGID {
+	GID_GENERIC,
+	GID_TEST,
+	GID_TESTALL
+};
+
+} // End of namespace Director
diff --git a/engines/director/director.h b/engines/director/director.h
index 56773ef74f..1b20960b97 100644
--- a/engines/director/director.h
+++ b/engines/director/director.h
@@ -36,6 +36,7 @@
 
 #include "director/types.h"
 #include "director/util.h"
+#include "director/detection_enums.h"
 
 namespace Common {
 class MacResManager;
@@ -53,12 +54,6 @@ class ManagedSurface;
 
 namespace Director {
 
-enum DirectorGameGID {
-	GID_GENERIC,
-	GID_TEST,
-	GID_TESTALL
-};
-
 class Archive;
 class Cast;
 struct DirectorGameDescription;
diff --git a/engines/director/metaengine.cpp b/engines/director/metaengine.cpp
new file mode 100644
index 0000000000..15f4313e56
--- /dev/null
+++ b/engines/director/metaengine.cpp
@@ -0,0 +1,111 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+
+#include "common/file.h"
+#include "common/config-manager.h"
+
+#include "director/director.h"
+#include "director/detection.h"
+
+namespace Director {
+
+DirectorGameGID DirectorEngine::getGameGID() const {
+	return _gameDescription->gameGID;
+}
+
+const char *DirectorEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+Common::Platform DirectorEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+uint16 DirectorEngine::getDescriptionVersion() const {
+	return _gameDescription->version;
+}
+
+Common::Language DirectorEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+const char *DirectorEngine::getExtra() {
+	return _gameDescription->desc.extra;
+}
+
+Common::String DirectorEngine::getEXEName() const {
+	StartMovie startMovie = getStartMovie();
+	if (startMovie.startMovie.size() > 0)
+		return startMovie.startMovie;
+
+	return _gameDescription->desc.filesDescriptions[0].fileName;
+}
+
+StartMovie DirectorEngine::getStartMovie() const {
+	StartMovie startMovie;
+	startMovie.startFrame = -1;
+
+	if (ConfMan.hasKey("start_movie")) {
+		Common::String option = ConfMan.get("start_movie");
+		int atPos = option.findLastOf("@");
+		startMovie.startMovie = option.substr(0, atPos);
+		Common::String tail = option.substr(atPos + 1, option.size());
+		if (tail.size() > 0)
+			startMovie.startFrame = atoi(tail.c_str());
+	}
+	return startMovie;
+}
+
+bool DirectorEngine::hasFeature(EngineFeature f) const {
+	return false;
+		//(f == kSupportsReturnToLauncher);
+}
+
+} // End of Namespace Director
+
+class DirectorMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "director";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool DirectorMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Director::DirectorGameDescription *gd = (const Director::DirectorGameDescription *)desc;
+
+	if (gd)
+		*engine = new Director::DirectorEngine(syst, gd);
+
+	return (gd != 0);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(DIRECTOR)
+	REGISTER_PLUGIN_DYNAMIC(DIRECTOR, PLUGIN_TYPE_ENGINE, DirectorMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(DIRECTOR, PLUGIN_TYPE_ENGINE, DirectorMetaEngineConnect);
+#endif
diff --git a/engines/director/module.mk b/engines/director/module.mk
index 3371974932..508ea8707a 100644
--- a/engines/director/module.mk
+++ b/engines/director/module.mk
@@ -6,12 +6,12 @@ MODULE_OBJS = \
 	castmember.o \
 	channel.o \
 	cursor.o \
-	detection.o \
 	director.o \
 	events.o \
 	frame.o \
 	graphics.o \
 	images.o \
+	metaengine.o \
 	movie.o \
 	resource.o \
 	score.o \
@@ -51,3 +51,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 30794432ab4fa37c5678116d4b3501eab7ae61ec
    https://github.com/scummvm/scummvm/commit/30794432ab4fa37c5678116d4b3501eab7ae61ec
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
FULLPIPE: Split detection features & adapt to new plugins.

Changed paths:
  A engines/fullpipe/metaengine.cpp
    configure
    engines/fullpipe/detection.cpp
    engines/fullpipe/module.mk


diff --git a/configure b/configure
index bc0fbe0180..5113691e1b 100755
--- a/configure
+++ b/configure
@@ -6169,7 +6169,8 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
-								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR")
+								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR"
+								  "FULLPIPE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/fullpipe/detection.cpp b/engines/fullpipe/detection.cpp
index 9fdcd15458..a73cc08cae 100644
--- a/engines/fullpipe/detection.cpp
+++ b/engines/fullpipe/detection.cpp
@@ -25,27 +25,6 @@
 #include "engines/advancedDetector.h"
 #include "common/file.h"
 
-#include "graphics/surface.h"
-
-#include "fullpipe/fullpipe.h"
-#include "fullpipe/gameloader.h"
-
-
-namespace Fullpipe {
-
-uint32 FullpipeEngine::getFeatures() const {
-	return _gameDescription->flags;
-}
-
-bool FullpipeEngine::isDemo() {
-	return _gameDescription->flags & ADGF_DEMO;
-}
-
-Common::Language FullpipeEngine::getLanguage() const {
-	return _gameDescription->language;
-}
-
-}
 
 static const PlainGameDescriptor fullpipeGames[] = {
 	{"fullpipe", "Full Pipe"},
@@ -143,107 +122,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Full Pipe (C) Pipe Studio";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	int getMaximumSaveSlot() const override { return 99; }
-	SaveStateList listSaves(const char *target) const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool FullpipeMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Fullpipe::FullpipeEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-SaveStateList FullpipeMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern("fullpipe.s##");
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot
-		int slotNum = atoi(file->c_str() + file->size() - 2);
-
-		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
-			Common::ScopedPtr<Common::InSaveFile> in(saveFileMan->openForLoading(*file));
-			if (in) {
-				Fullpipe::FullpipeSavegameHeader header;
-				if (!Fullpipe::readSavegameHeader(in.get(), header)) {
-					continue;
-				}
-
-				SaveStateDescriptor desc;
-
-				Fullpipe::parseSavegameHeader(header, desc);
-
-				desc.setSaveSlot(slotNum);
-
-				saveList.push_back(desc);
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-void FullpipeMetaEngine::removeSaveState(const char *target, int slot) const {
-	g_system->getSavefileManager()->removeSavefile(Fullpipe::getSavegameFile(slot));
-}
-
-SaveStateDescriptor FullpipeMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(
-		Fullpipe::getSavegameFile(slot)));
-
-	if (f) {
-		Fullpipe::FullpipeSavegameHeader header;
-		if (!Fullpipe::readSavegameHeader(f.get(), header, false)) {
-			return SaveStateDescriptor();
-		}
-
-		// Create the return descriptor
-		SaveStateDescriptor desc;
-
-		Fullpipe::parseSavegameHeader(header, desc);
-
-		desc.setSaveSlot(slot);
-		desc.setThumbnail(header.thumbnail);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-bool FullpipeMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	if (desc) {
-		*engine = new Fullpipe::FullpipeEngine(syst, desc);
-	}
-	return desc != 0;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(FULLPIPE)
-	REGISTER_PLUGIN_DYNAMIC(FULLPIPE, PLUGIN_TYPE_ENGINE, FullpipeMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(FULLPIPE, PLUGIN_TYPE_ENGINE, FullpipeMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(FULLPIPE_DETECTION, PLUGIN_TYPE_METAENGINE, FullpipeMetaEngine);
diff --git a/engines/fullpipe/metaengine.cpp b/engines/fullpipe/metaengine.cpp
new file mode 100644
index 0000000000..b230912a70
--- /dev/null
+++ b/engines/fullpipe/metaengine.cpp
@@ -0,0 +1,159 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+#include "engines/advancedDetector.h"
+#include "common/file.h"
+
+#include "graphics/surface.h"
+
+#include "fullpipe/fullpipe.h"
+#include "fullpipe/gameloader.h"
+
+namespace Fullpipe {
+
+uint32 FullpipeEngine::getFeatures() const {
+	return _gameDescription->flags;
+}
+
+bool FullpipeEngine::isDemo() {
+	return _gameDescription->flags & ADGF_DEMO;
+}
+
+Common::Language FullpipeEngine::getLanguage() const {
+	return _gameDescription->language;
+}
+
+} // End of namspace Fullpipe
+
+class FullpipeMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "fullpipe";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	int getMaximumSaveSlot() const override { return 99; }
+	SaveStateList listSaves(const char *target) const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+};
+
+bool FullpipeMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Fullpipe::FullpipeEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+SaveStateList FullpipeMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern("fullpipe.s##");
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot
+		int slotNum = atoi(file->c_str() + file->size() - 2);
+
+		if (slotNum >= 0 && slotNum <= getMaximumSaveSlot()) {
+			Common::ScopedPtr<Common::InSaveFile> in(saveFileMan->openForLoading(*file));
+			if (in) {
+				Fullpipe::FullpipeSavegameHeader header;
+				if (!Fullpipe::readSavegameHeader(in.get(), header)) {
+					continue;
+				}
+
+				SaveStateDescriptor desc;
+
+				Fullpipe::parseSavegameHeader(header, desc);
+
+				desc.setSaveSlot(slotNum);
+
+				saveList.push_back(desc);
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+void FullpipeMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	g_system->getSavefileManager()->removeSavefile(Fullpipe::getSavegameFile(slot));
+}
+
+SaveStateDescriptor FullpipeMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(
+		Fullpipe::getSavegameFile(slot)));
+
+	if (f) {
+		Fullpipe::FullpipeSavegameHeader header;
+		if (!Fullpipe::readSavegameHeader(f.get(), header, false)) {
+			return SaveStateDescriptor();
+		}
+
+		// Create the return descriptor
+		SaveStateDescriptor desc;
+
+		Fullpipe::parseSavegameHeader(header, desc);
+
+		desc.setSaveSlot(slot);
+		desc.setThumbnail(header.thumbnail);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+bool FullpipeMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	if (desc) {
+		*engine = new Fullpipe::FullpipeEngine(syst, desc);
+	}
+	return desc != 0;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(FULLPIPE)
+	REGISTER_PLUGIN_DYNAMIC(FULLPIPE, PLUGIN_TYPE_ENGINE, FullpipeMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(FULLPIPE, PLUGIN_TYPE_ENGINE, FullpipeMetaEngineConnect);
+#endif
diff --git a/engines/fullpipe/module.mk b/engines/fullpipe/module.mk
index 5dc6bb82c9..3e59fdcb79 100644
--- a/engines/fullpipe/module.mk
+++ b/engines/fullpipe/module.mk
@@ -4,7 +4,6 @@ MODULE_OBJS = \
 	anihandler.o \
 	behavior.o \
 	console.o \
-	detection.o \
 	floaters.o \
 	fullpipe.o \
 	gameloader.o \
@@ -16,6 +15,7 @@ MODULE_OBJS = \
 	lift.o \
 	messagehandlers.o \
 	messages.o \
+	metaengine.o \
 	modal.o \
 	motion.o \
 	ngiarchive.o \
@@ -75,3 +75,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: a4739197da357b75c1542efe5753bc986ff5faf9
    https://github.com/scummvm/scummvm/commit/a4739197da357b75c1542efe5753bc986ff5faf9
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SAGA: Move some shared defines between engine/game detection to a new header

Changed paths:
  A engines/saga/shared_detection_defines.h
    engines/saga/detection_tables.h
    engines/saga/scene.h


diff --git a/engines/saga/detection_tables.h b/engines/saga/detection_tables.h
index a2b8bf5d72..d9771cd3bd 100644
--- a/engines/saga/detection_tables.h
+++ b/engines/saga/detection_tables.h
@@ -22,6 +22,10 @@
 
 // Game detection information and MD5s
 
+// From sage/scene.h, these are some defines that also
+// help with detection.
+#include "saga/shared_detection_defines.h"
+
 namespace Saga {
 
 static const GameResourceDescription ITE_Resources = {
diff --git a/engines/saga/scene.h b/engines/saga/scene.h
index 1a710cfe9c..a9e1e3fad8 100644
--- a/engines/saga/scene.h
+++ b/engines/saga/scene.h
@@ -31,6 +31,9 @@
 #include "saga/puzzle.h"
 #include "saga/events.h"
 
+// Some defines used for detection.
+#include "saga/shared_detection_defines.h"
+
 namespace Saga {
 
 //#define SCENE_DEBUG // for scene debugging
@@ -45,12 +48,6 @@ namespace Saga {
 #define ITE_SCENE_ENDCREDIT1 295
 #define ITE_SCENE_OVERMAP 226
 
-// Default scenes
-#define ITE_DEFAULT_SCENE 32
-#define IHNM_DEFAULT_SCENE 151
-#define ITEDEMO_DEFAULT_SCENE 68
-#define IHNMDEMO_DEFAULT_SCENE 144
-
 class ObjectMap;
 
 enum SceneFlags {
diff --git a/engines/saga/shared_detection_defines.h b/engines/saga/shared_detection_defines.h
new file mode 100644
index 0000000000..a9c8e42cfd
--- /dev/null
+++ b/engines/saga/shared_detection_defines.h
@@ -0,0 +1,27 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+// Default scenes
+#define ITE_DEFAULT_SCENE 32
+#define IHNM_DEFAULT_SCENE 151
+#define ITEDEMO_DEFAULT_SCENE 68
+#define IHNMDEMO_DEFAULT_SCENE 144


Commit: 95bc4c09947e10145c75129f93a9fa0c5de04c9d
    https://github.com/scummvm/scummvm/commit/95bc4c09947e10145c75129f93a9fa0c5de04c9d
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SAGA: Move common engine/game-detection related enums into a new header.

Changed paths:
  A engines/saga/detection_enums.h
    engines/saga/saga.h


diff --git a/engines/saga/detection_enums.h b/engines/saga/detection_enums.h
new file mode 100644
index 0000000000..fc1a50b668
--- /dev/null
+++ b/engines/saga/detection_enums.h
@@ -0,0 +1,90 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Saga {
+
+struct GameResourceDescription {
+	uint32 sceneLUTResourceId;
+	uint32 moduleLUTResourceId;
+	uint32 mainPanelResourceId;
+	uint32 conversePanelResourceId;
+	uint32 optionPanelResourceId;
+	uint32 mainSpritesResourceId;
+	uint32 mainPanelSpritesResourceId;
+	uint32 mainStringsResourceId;
+	// ITE specific resources
+	uint32 actorsStringsResourceId;
+	uint32 defaultPortraitsResourceId;
+	// IHNM specific resources
+	uint32 optionPanelSpritesResourceId;
+	uint32 warningPanelResourceId;
+	uint32 warningPanelSpritesResourceId;
+	uint32 psychicProfileResourceId;
+};
+
+struct GameFontDescription {
+	uint32 fontResourceId;
+};
+
+struct GamePatchDescription {
+	const char *fileName;
+	uint16 fileType;
+	uint32 resourceId;
+};
+
+enum GameIds {
+	GID_ITE = 0,
+	GID_IHNM = 1,
+	GID_DINO = 2,
+	GID_FTA2 = 3
+};
+
+enum GameFeatures {
+	GF_ITE_FLOPPY        = 1 << 0,
+	GF_ITE_DOS_DEMO      = 1 << 1,
+	GF_EXTRA_ITE_CREDITS = 1 << 2,
+	GF_8BIT_UNSIGNED_PCM = 1 << 3,
+	GF_IHNM_COLOR_FIX    = 1 << 4,
+	GF_SOME_MAC_RESOURCES= 1 << 5
+};
+
+enum GameFileTypes {
+	// Common
+	GAME_RESOURCEFILE     = 1 << 0,    // Game resources
+	GAME_SCRIPTFILE       = 1 << 1,    // Game scripts
+	GAME_SOUNDFILE        = 1 << 2,    // SFX (also contains voices and MIDI music in SAGA 2 games)
+	GAME_VOICEFILE        = 1 << 3,    // Voices (also contains SFX in the ITE floppy version)
+	// ITE specific
+	GAME_DIGITALMUSICFILE = 1 << 4,    // ITE digital music, added by Wyrmkeep
+	GAME_MACBINARY        = 1 << 5,    // ITE Mac CD Guild
+	GAME_DEMOFILE         = 1 << 6,    // Early ITE demo
+	GAME_SWAPENDIAN       = 1 << 7,    // Used to identify the BE voice file in the ITE combined version
+	// IHNM specific
+	GAME_MUSICFILE_FM     = 1 << 8,    // IHNM
+	GAME_MUSICFILE_GM     = 1 << 9,    // IHNM, ITE Mac CD Guild
+	GAME_PATCHFILE        = 1 << 10,   // IHNM patch file (patch.re_/patch.res)
+	// SAGA 2 (Dinotopia, FTA2)
+	GAME_IMAGEFILE        = 1 << 11,   // Game images
+	GAME_OBJRESOURCEFILE  = 1 << 12    // Game object data
+};
+
+} // End of namespace Saga
diff --git a/engines/saga/saga.h b/engines/saga/saga.h
index a76fb00c58..59a8ecf202 100644
--- a/engines/saga/saga.h
+++ b/engines/saga/saga.h
@@ -31,6 +31,7 @@
 #include "common/textconsole.h"
 
 #include "saga/gfx.h"
+#include "saga/detection_enums.h"
 
 struct ADGameFileDescription;
 
@@ -108,42 +109,6 @@ enum ERRORCODE {
 	SUCCESS = 0
 };
 
-enum GameIds {
-	GID_ITE = 0,
-	GID_IHNM = 1,
-	GID_DINO = 2,
-	GID_FTA2 = 3
-};
-
-enum GameFileTypes {
-	// Common
-	GAME_RESOURCEFILE     = 1 << 0,    // Game resources
-	GAME_SCRIPTFILE       = 1 << 1,    // Game scripts
-	GAME_SOUNDFILE        = 1 << 2,    // SFX (also contains voices and MIDI music in SAGA 2 games)
-	GAME_VOICEFILE        = 1 << 3,    // Voices (also contains SFX in the ITE floppy version)
-	// ITE specific
-	GAME_DIGITALMUSICFILE = 1 << 4,    // ITE digital music, added by Wyrmkeep
-	GAME_MACBINARY        = 1 << 5,    // ITE Mac CD Guild
-	GAME_DEMOFILE         = 1 << 6,    // Early ITE demo
-	GAME_SWAPENDIAN       = 1 << 7,    // Used to identify the BE voice file in the ITE combined version
-	// IHNM specific
-	GAME_MUSICFILE_FM     = 1 << 8,    // IHNM
-	GAME_MUSICFILE_GM     = 1 << 9,    // IHNM, ITE Mac CD Guild
-	GAME_PATCHFILE        = 1 << 10,   // IHNM patch file (patch.re_/patch.res)
-	// SAGA 2 (Dinotopia, FTA2)
-	GAME_IMAGEFILE        = 1 << 11,   // Game images
-	GAME_OBJRESOURCEFILE  = 1 << 12    // Game object data
-};
-
-enum GameFeatures {
-	GF_ITE_FLOPPY        = 1 << 0,
-	GF_ITE_DOS_DEMO      = 1 << 1,
-	GF_EXTRA_ITE_CREDITS = 1 << 2,
-	GF_8BIT_UNSIGNED_PCM = 1 << 3,
-	GF_IHNM_COLOR_FIX    = 1 << 4,
-	GF_SOME_MAC_RESOURCES= 1 << 5
-};
-
 enum VerbTypeIds {
 	kVerbITENone = 0,
 	kVerbITEPickUp = 1,
@@ -269,37 +234,8 @@ enum TextStringIds {
 	kTextLoadSavedGame
 };
 
-struct GameResourceDescription {
-	uint32 sceneLUTResourceId;
-	uint32 moduleLUTResourceId;
-	uint32 mainPanelResourceId;
-	uint32 conversePanelResourceId;
-	uint32 optionPanelResourceId;
-	uint32 mainSpritesResourceId;
-	uint32 mainPanelSpritesResourceId;
-	uint32 mainStringsResourceId;
-	// ITE specific resources
-	uint32 actorsStringsResourceId;
-	uint32 defaultPortraitsResourceId;
-	// IHNM specific resources
-	uint32 optionPanelSpritesResourceId;
-	uint32 warningPanelResourceId;
-	uint32 warningPanelSpritesResourceId;
-	uint32 psychicProfileResourceId;
-};
-
-struct GameFontDescription {
-	uint32 fontResourceId;
-};
-
 struct GameDisplayInfo;
 
-struct GamePatchDescription {
-	const char *fileName;
-	uint16 fileType;
-	uint32 resourceId;
-};
-
 struct SAGAGameDescription;
 
 enum GameObjectTypes {


Commit: d8c82faf27493a6db5c55c3862b75c95da53daff
    https://github.com/scummvm/scummvm/commit/d8c82faf27493a6db5c55c3862b75c95da53daff
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SAGA: Split detection features & adapt to new plugins.

Changed paths:
  A engines/saga/detection.h
  A engines/saga/metaengine.cpp
    configure
    engines/saga/detection.cpp
    engines/saga/module.mk


diff --git a/configure b/configure
index 5113691e1b..d1c29ed74e 100755
--- a/configure
+++ b/configure
@@ -6170,7 +6170,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
 								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR"
-								  "FULLPIPE")
+								  "FULLPIPE" "SAGA")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/saga/detection.cpp b/engines/saga/detection.cpp
index e74ecb7483..e58d6689b1 100644
--- a/engines/saga/detection.cpp
+++ b/engines/saga/detection.cpp
@@ -22,62 +22,11 @@
 
 // Game detection, general game parameters
 
-#include "saga/saga.h"
-
 #include "base/plugins.h"
-
-#include "common/config-manager.h"
 #include "engines/advancedDetector.h"
-#include "common/system.h"
-#include "graphics/thumbnail.h"
-
-#include "saga/animation.h"
-#include "saga/displayinfo.h"
-#include "saga/events.h"
-#include "saga/resource.h"
-#include "saga/interface.h"
-#include "saga/scene.h"
-
-namespace Saga {
-struct SAGAGameDescription {
-	ADGameDescription desc;
-
-	int gameId;
-	uint32 features;
-	int startSceneNumber;
-	const GameResourceDescription *resourceDescription;
-	int fontsCount;
-	const GameFontDescription *fontDescriptions;
-	const GamePatchDescription *patchDescriptions;
-};
-
-bool SagaEngine::isBigEndian() const { return isMacResources() && getGameId() == GID_ITE; }
-bool SagaEngine::isMacResources() const { return (getPlatform() == Common::kPlatformMacintosh); }
-const GameResourceDescription *SagaEngine::getResourceDescription() const { return _gameDescription->resourceDescription; }
-
-const GameFontDescription *SagaEngine::getFontDescription(int index) const {
-	assert(index < _gameDescription->fontsCount);
-	return &_gameDescription->fontDescriptions[index];
-}
-int SagaEngine::getFontsCount() const { return _gameDescription->fontsCount; }
-
-int SagaEngine::getGameId() const { return _gameDescription->gameId; }
 
-uint32 SagaEngine::getFeatures() const {
-	uint32 result = _gameDescription->features;
-
-	return result;
-}
-
-Common::Language SagaEngine::getLanguage() const { return _gameDescription->desc.language; }
-Common::Platform SagaEngine::getPlatform() const { return _gameDescription->desc.platform; }
-int SagaEngine::getGameNumber() const { return _gameNumber; }
-int SagaEngine::getStartSceneNumber() const { return _gameDescription->startSceneNumber; }
-
-const GamePatchDescription *SagaEngine::getPatchDescriptions() const { return _gameDescription->patchDescriptions; }
-const ADGameFileDescription *SagaEngine::getFilesDescriptions() const { return _gameDescription->desc.filesDescriptions; }
-
-}
+#include "saga/detection_enums.h"
+#include "saga/detection.h"
 
 static const PlainGameDescriptor sagaGames[] = {
 	{"ite", "Inherit the Earth: Quest for the Orb"},
@@ -123,230 +72,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Inherit the Earth (C) Wyrmkeep Entertainment";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-
-	Common::Error createInstance(OSystem *syst, Engine **engine) const override {
-		return AdvancedMetaEngine::createInstance(syst, engine);
-	}
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool SagaMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Saga::SagaEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool SagaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Saga::SAGAGameDescription *gd = (const Saga::SAGAGameDescription *)desc;
-	if (gd) {
-		*engine = new Saga::SagaEngine(syst, gd);
-	}
-	return gd != 0;
-}
-
-SaveStateList SagaMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	char saveDesc[SAVE_TITLE_SIZE];
-	Common::String pattern = target;
-	pattern += ".s##";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	int slotNum = 0;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 2 digits of the filename, since they correspond to the save slot
-		slotNum = atoi(file->c_str() + file->size() - 2);
-
-		if (slotNum >= 0 && slotNum < MAX_SAVES) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				for (int i = 0; i < 3; i++)
-					in->readUint32BE();
-				in->read(saveDesc, SAVE_TITLE_SIZE);
-				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int SagaMetaEngine::getMaximumSaveSlot() const { return MAX_SAVES - 1; }
-
-void SagaMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = target;
-	filename += Common::String::format(".s%02d", slot);
-
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor SagaMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	static char fileName[MAX_FILE_NAME];
-	sprintf(fileName, "%s.s%02d", target, slot);
-	char title[TITLESIZE];
-
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
-
-	if (in) {
-		uint32 type = in->readUint32BE();
-		in->readUint32LE();		// size
-		uint32 version = in->readUint32LE();
-		char name[SAVE_TITLE_SIZE];
-		in->read(name, sizeof(name));
-
-		SaveStateDescriptor desc(slot, name);
-
-		// Some older saves were not written in an endian safe fashion.
-		// We try to detect this here by checking for extremely high version values.
-		// If found, we retry with the data swapped.
-		if (version > 0xFFFFFF) {
-			warning("This savegame is not endian safe, retrying with the data swapped");
-			version = SWAP_BYTES_32(version);
-		}
-
-		debug(2, "Save version: 0x%X", version);
-
-		if (version < 4)
-			warning("This savegame is not endian-safe. There may be problems");
-
-		if (type != MKTAG('S','A','G','A')) {
-			error("SagaEngine::load wrong save game format");
-		}
-
-		if (version > 4) {
-			in->read(title, TITLESIZE);
-			debug(0, "Save is for: %s", title);
-		}
-
-		if (version >= 6) {
-			Graphics::Surface *thumbnail;
-			if (!Graphics::loadThumbnail(*in, thumbnail)) {
-				delete in;
-				return SaveStateDescriptor();
-			}
-			desc.setThumbnail(thumbnail);
-
-			uint32 saveDate = in->readUint32BE();
-			uint16 saveTime = in->readUint16BE();
-
-			int day = (saveDate >> 24) & 0xFF;
-			int month = (saveDate >> 16) & 0xFF;
-			int year = saveDate & 0xFFFF;
-
-			desc.setSaveDate(year, month, day);
-
-			int hour = (saveTime >> 8) & 0xFF;
-			int minutes = saveTime & 0xFF;
-
-			desc.setSaveTime(hour, minutes);
-
-			if (version >= 8) {
-				uint32 playTime = in->readUint32BE();
-				desc.setPlayTime(playTime * 1000);
-			}
-		}
-
-		delete in;
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(SAGA)
-	REGISTER_PLUGIN_DYNAMIC(SAGA, PLUGIN_TYPE_ENGINE, SagaMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(SAGA, PLUGIN_TYPE_ENGINE, SagaMetaEngine);
-#endif
-
-namespace Saga {
-
-bool SagaEngine::initGame() {
-	_displayClip.right = getDisplayInfo().width;
-	_displayClip.bottom = getDisplayInfo().height;
-
-	return _resource->createContexts();
-}
-
-const GameDisplayInfo &SagaEngine::getDisplayInfo() {
-	switch (_gameDescription->gameId) {
-		case GID_ITE:
-			return ITE_DisplayInfo;
-#ifdef ENABLE_IHNM
-		case GID_IHNM:
-			return IHNM_DisplayInfo;
-#endif
-#ifdef ENABLE_SAGA2
-		case GID_DINO:
-			return FTA2_DisplayInfo;	// TODO
-		case GID_FTA2:
-			return FTA2_DisplayInfo;
-#endif
-		default:
-			error("getDisplayInfo: Unknown game ID");
-			return ITE_DisplayInfo;		// for compilers that don't support NORETURN
-	}
-}
-
-Common::Error SagaEngine::loadGameState(int slot) {
-	// Init the current chapter to 8 (character selection) for IHNM
-	if (getGameId() == GID_IHNM)
-		_scene->changeScene(-2, 0, kTransitionFade, 8);
-
-	// First scene sets up palette
-	_scene->changeScene(getStartSceneNumber(), 0, kTransitionNoFade);
-	_events->handleEvents(0); // Process immediate events
-
-	if (getGameId() == GID_ITE)
-		_interface->setMode(kPanelMain);
-	else
-		_interface->setMode(kPanelChapterSelection);
-
-	load(calcSaveFileName((uint)slot));
-	syncSoundSettings();
-
-	return Common::kNoError;	// TODO: return success/failure
-}
-
-Common::Error SagaEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
-	save(calcSaveFileName((uint)slot), desc.c_str());
-	return Common::kNoError;	// TODO: return success/failure
-}
-
-bool SagaEngine::canLoadGameStateCurrently() {
-	return !_scene->isInIntro() &&
-		(_interface->getMode() == kPanelMain || _interface->getMode() == kPanelChapterSelection);
-}
-
-bool SagaEngine::canSaveGameStateCurrently() {
-	return !_scene->isInIntro() &&
-		(_interface->getMode() == kPanelMain || _interface->getMode() == kPanelChapterSelection);
-}
-
-} // End of namespace Saga
+REGISTER_PLUGIN_STATIC(SAGA_DETECTION, PLUGIN_TYPE_METAENGINE, SagaMetaEngine);
diff --git a/engines/saga/detection.h b/engines/saga/detection.h
new file mode 100644
index 0000000000..29034f70a4
--- /dev/null
+++ b/engines/saga/detection.h
@@ -0,0 +1,37 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Saga {
+
+struct SAGAGameDescription {
+	ADGameDescription desc;
+
+	int gameId;
+	uint32 features;
+	int startSceneNumber;
+	const GameResourceDescription *resourceDescription;
+	int fontsCount;
+	const GameFontDescription *fontDescriptions;
+	const GamePatchDescription *patchDescriptions;
+};
+
+} // End of namespace Saga
diff --git a/engines/saga/metaengine.cpp b/engines/saga/metaengine.cpp
new file mode 100644
index 0000000000..43d8b6bceb
--- /dev/null
+++ b/engines/saga/metaengine.cpp
@@ -0,0 +1,303 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+// Game detection, general game parameters
+
+#include "saga/saga.h"
+
+#include "base/plugins.h"
+
+#include "common/config-manager.h"
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+#include "graphics/thumbnail.h"
+
+#include "saga/animation.h"
+#include "saga/displayinfo.h"
+#include "saga/events.h"
+#include "saga/resource.h"
+#include "saga/interface.h"
+#include "saga/scene.h"
+#include "saga/detection.h"
+
+namespace Saga {
+
+bool SagaEngine::isBigEndian() const { return isMacResources() && getGameId() == GID_ITE; }
+bool SagaEngine::isMacResources() const { return (getPlatform() == Common::kPlatformMacintosh); }
+const GameResourceDescription *SagaEngine::getResourceDescription() const { return _gameDescription->resourceDescription; }
+
+const GameFontDescription *SagaEngine::getFontDescription(int index) const {
+	assert(index < _gameDescription->fontsCount);
+	return &_gameDescription->fontDescriptions[index];
+}
+int SagaEngine::getFontsCount() const { return _gameDescription->fontsCount; }
+
+int SagaEngine::getGameId() const { return _gameDescription->gameId; }
+
+uint32 SagaEngine::getFeatures() const {
+	uint32 result = _gameDescription->features;
+
+	return result;
+}
+
+Common::Language SagaEngine::getLanguage() const { return _gameDescription->desc.language; }
+Common::Platform SagaEngine::getPlatform() const { return _gameDescription->desc.platform; }
+int SagaEngine::getGameNumber() const { return _gameNumber; }
+int SagaEngine::getStartSceneNumber() const { return _gameDescription->startSceneNumber; }
+
+const GamePatchDescription *SagaEngine::getPatchDescriptions() const { return _gameDescription->patchDescriptions; }
+const ADGameFileDescription *SagaEngine::getFilesDescriptions() const { return _gameDescription->desc.filesDescriptions; }
+
+} // End of namespace Saga
+
+class SagaMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "saga";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+
+	Common::Error createInstance(OSystem *syst, Engine **engine) const override {
+		return AdvancedMetaEngineConnect::createInstance(syst, engine);
+	}
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool SagaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Saga::SagaEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool SagaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Saga::SAGAGameDescription *gd = (const Saga::SAGAGameDescription *)desc;
+	if (gd) {
+		*engine = new Saga::SagaEngine(syst, gd);
+	}
+	return gd != 0;
+}
+
+SaveStateList SagaMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	char saveDesc[SAVE_TITLE_SIZE];
+	Common::String pattern = target;
+	pattern += ".s##";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	int slotNum = 0;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 2 digits of the filename, since they correspond to the save slot
+		slotNum = atoi(file->c_str() + file->size() - 2);
+
+		if (slotNum >= 0 && slotNum < MAX_SAVES) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				for (int i = 0; i < 3; i++)
+					in->readUint32BE();
+				in->read(saveDesc, SAVE_TITLE_SIZE);
+				saveList.push_back(SaveStateDescriptor(slotNum, saveDesc));
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int SagaMetaEngineConnect::getMaximumSaveSlot() const { return MAX_SAVES - 1; }
+
+void SagaMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = target;
+	filename += Common::String::format(".s%02d", slot);
+
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor SagaMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	static char fileName[MAX_FILE_NAME];
+	sprintf(fileName, "%s.s%02d", target, slot);
+	char title[TITLESIZE];
+
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
+
+	if (in) {
+		uint32 type = in->readUint32BE();
+		in->readUint32LE();		// size
+		uint32 version = in->readUint32LE();
+		char name[SAVE_TITLE_SIZE];
+		in->read(name, sizeof(name));
+
+		SaveStateDescriptor desc(slot, name);
+
+		// Some older saves were not written in an endian safe fashion.
+		// We try to detect this here by checking for extremely high version values.
+		// If found, we retry with the data swapped.
+		if (version > 0xFFFFFF) {
+			warning("This savegame is not endian safe, retrying with the data swapped");
+			version = SWAP_BYTES_32(version);
+		}
+
+		debug(2, "Save version: 0x%X", version);
+
+		if (version < 4)
+			warning("This savegame is not endian-safe. There may be problems");
+
+		if (type != MKTAG('S','A','G','A')) {
+			error("SagaEngine::load wrong save game format");
+		}
+
+		if (version > 4) {
+			in->read(title, TITLESIZE);
+			debug(0, "Save is for: %s", title);
+		}
+
+		if (version >= 6) {
+			Graphics::Surface *thumbnail;
+			if (!Graphics::loadThumbnail(*in, thumbnail)) {
+				delete in;
+				return SaveStateDescriptor();
+			}
+			desc.setThumbnail(thumbnail);
+
+			uint32 saveDate = in->readUint32BE();
+			uint16 saveTime = in->readUint16BE();
+
+			int day = (saveDate >> 24) & 0xFF;
+			int month = (saveDate >> 16) & 0xFF;
+			int year = saveDate & 0xFFFF;
+
+			desc.setSaveDate(year, month, day);
+
+			int hour = (saveTime >> 8) & 0xFF;
+			int minutes = saveTime & 0xFF;
+
+			desc.setSaveTime(hour, minutes);
+
+			if (version >= 8) {
+				uint32 playTime = in->readUint32BE();
+				desc.setPlayTime(playTime * 1000);
+			}
+		}
+
+		delete in;
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(SAGA)
+	REGISTER_PLUGIN_DYNAMIC(SAGA, PLUGIN_TYPE_ENGINE, SagaMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(SAGA, PLUGIN_TYPE_ENGINE, SagaMetaEngineConnect);
+#endif
+
+namespace Saga {
+
+bool SagaEngine::initGame() {
+	_displayClip.right = getDisplayInfo().width;
+	_displayClip.bottom = getDisplayInfo().height;
+
+	return _resource->createContexts();
+}
+
+const GameDisplayInfo &SagaEngine::getDisplayInfo() {
+	switch (_gameDescription->gameId) {
+		case GID_ITE:
+			return ITE_DisplayInfo;
+#ifdef ENABLE_IHNM
+		case GID_IHNM:
+			return IHNM_DisplayInfo;
+#endif
+#ifdef ENABLE_SAGA2
+		case GID_DINO:
+			return FTA2_DisplayInfo;	// TODO
+		case GID_FTA2:
+			return FTA2_DisplayInfo;
+#endif
+		default:
+			error("getDisplayInfo: Unknown game ID");
+			return ITE_DisplayInfo;		// for compilers that don't support NORETURN
+	}
+}
+
+Common::Error SagaEngine::loadGameState(int slot) {
+	// Init the current chapter to 8 (character selection) for IHNM
+	if (getGameId() == GID_IHNM)
+		_scene->changeScene(-2, 0, kTransitionFade, 8);
+
+	// First scene sets up palette
+	_scene->changeScene(getStartSceneNumber(), 0, kTransitionNoFade);
+	_events->handleEvents(0); // Process immediate events
+
+	if (getGameId() == GID_ITE)
+		_interface->setMode(kPanelMain);
+	else
+		_interface->setMode(kPanelChapterSelection);
+
+	load(calcSaveFileName((uint)slot));
+	syncSoundSettings();
+
+	return Common::kNoError;	// TODO: return success/failure
+}
+
+Common::Error SagaEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
+	save(calcSaveFileName((uint)slot), desc.c_str());
+	return Common::kNoError;	// TODO: return success/failure
+}
+
+bool SagaEngine::canLoadGameStateCurrently() {
+	return !_scene->isInIntro() &&
+		(_interface->getMode() == kPanelMain || _interface->getMode() == kPanelChapterSelection);
+}
+
+bool SagaEngine::canSaveGameStateCurrently() {
+	return !_scene->isInIntro() &&
+		(_interface->getMode() == kPanelMain || _interface->getMode() == kPanelChapterSelection);
+}
+
+} // End of namespace Saga
diff --git a/engines/saga/module.mk b/engines/saga/module.mk
index 9c10fa5bda..07af31efc0 100644
--- a/engines/saga/module.mk
+++ b/engines/saga/module.mk
@@ -6,7 +6,6 @@ MODULE_OBJS := \
 	actor_walk.o \
 	animation.o \
 	console.o \
-	detection.o \
 	events.o \
 	font.o \
 	font_map.o \
@@ -17,6 +16,7 @@ MODULE_OBJS := \
 	introproc_ite.o \
 	isomap.o \
 	itedata.o \
+	metaengine.o \
 	music.o \
 	objectmap.o \
 	palanim.o \
@@ -55,3 +55,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: cd87a9150e293ce4ed74657b9b597e48eeee14b6
    https://github.com/scummvm/scummvm/commit/cd87a9150e293ce4ed74657b9b597e48eeee14b6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
XEEN: Split detection features & adapt to new plugins.

Changed paths:
  A engines/xeen/detection.h
  A engines/xeen/detection_enums.h
  A engines/xeen/metaengine.cpp
    configure
    engines/xeen/detection.cpp
    engines/xeen/module.mk
    engines/xeen/xeen.h


diff --git a/configure b/configure
index d1c29ed74e..c7b56b9d16 100755
--- a/configure
+++ b/configure
@@ -6170,7 +6170,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
 								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR"
-								  "FULLPIPE" "SAGA")
+								  "FULLPIPE" "SAGA" "XEEN")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/xeen/detection.cpp b/engines/xeen/detection.cpp
index 77258beb33..79343db575 100644
--- a/engines/xeen/detection.cpp
+++ b/engines/xeen/detection.cpp
@@ -20,60 +20,12 @@
  *
  */
 
-#include "xeen/xeen.h"
-#include "xeen/worldofxeen/worldofxeen.h"
-#include "xeen/swordsofxeen/swordsofxeen.h"
-
 #include "base/plugins.h"
-#include "common/savefile.h"
 #include "engines/advancedDetector.h"
-#include "common/system.h"
 #include "common/translation.h"
 
-#define MAX_SAVES 99
-
-namespace Xeen {
-
-struct XeenGameDescription {
-	ADGameDescription desc;
-
-	int gameID;
-	uint32 features;
-};
-
-uint32 XeenEngine::getGameID() const {
-	return _gameDescription->gameID;
-}
-
-uint32 XeenEngine::getSpecificGameId() const {
-	uint gameId = g_vm->getGameID();
-	if (gameId == GType_WorldOfXeen)
-		gameId = _files->_ccNum ? GType_DarkSide : GType_Clouds;
-
-	return gameId;
-}
-
-uint32 XeenEngine::getGameFeatures() const {
-	return _gameDescription->features;
-}
-
-uint32 XeenEngine::getFeatures() const {
-	return _gameDescription->desc.flags;
-}
-
-Common::Language XeenEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-Common::Platform XeenEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-bool XeenEngine::getIsCD() const {
-	return getFeatures() & ADGF_CD;
-}
-
-} // End of namespace Xeen
+#include "xeen/detection.h"
+#include "xeen/detection_enums.h"
 
 static const PlainGameDescriptor XeenGames[] = {
 	{ "cloudsofxeen", "Might and Magic IV: Clouds of Xeen" },
@@ -131,121 +83,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Xeen (C) 1992-1993 New World Computing, Inc.";
 	}
-
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool XeenMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSimpleSavesNames);
-}
-
-bool Xeen::XeenEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime) ||
-		(f == kSupportsSavingDuringRuntime);
-}
-
-bool XeenMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Xeen::XeenGameDescription *gd = (const Xeen::XeenGameDescription *)desc;
-
-	switch (gd->gameID) {
-	case Xeen::GType_Clouds:
-	case Xeen::GType_DarkSide:
-	case Xeen::GType_WorldOfXeen:
-		*engine = new Xeen::WorldOfXeen::WorldOfXeenEngine(syst, gd);
-		break;
-	case Xeen::GType_Swords:
-		*engine = new Xeen::SwordsOfXeen::SwordsOfXeenEngine(syst, gd);
-		break;
-	default:
-		error("Invalid game");
-	}
-
-	return true;
-}
-
-SaveStateList XeenMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.###", target);
-	Xeen::XeenSavegameHeader header;
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		const char *ext = strrchr(file->c_str(), '.');
-		int slot = ext ? atoi(ext + 1) : -1;
-
-		if (slot >= 0 && slot <= MAX_SAVES) {
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-			if (in) {
-				if (Xeen::SavesManager::readSavegameHeader(in, header))
-					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
-
-				delete in;
-			}
-		}
-	}
-
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int XeenMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVES;
-}
-
-void XeenMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor XeenMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
-
-	if (f) {
-		Xeen::XeenSavegameHeader header;
-		if (!Xeen::SavesManager::readSavegameHeader(f, header, false)) {
-			delete f;
-			return SaveStateDescriptor();
-		}
-
-		delete f;
-
-		// Create the return descriptor
-		SaveStateDescriptor desc(slot, header._saveName);
-		desc.setThumbnail(header._thumbnail);
-		desc.setSaveDate(header._year, header._month, header._day);
-		desc.setSaveTime(header._hour, header._minute);
-		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
-
-		return desc;
-	}
-
-	return SaveStateDescriptor();
-}
-
-
-#if PLUGIN_ENABLED_DYNAMIC(XEEN)
-	REGISTER_PLUGIN_DYNAMIC(XEEN, PLUGIN_TYPE_ENGINE, XeenMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(XEEN, PLUGIN_TYPE_ENGINE, XeenMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(XEEN_DETECTION, PLUGIN_TYPE_METAENGINE, XeenMetaEngine);
diff --git a/engines/xeen/detection.h b/engines/xeen/detection.h
new file mode 100644
index 0000000000..0c7a014966
--- /dev/null
+++ b/engines/xeen/detection.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Xeen {
+
+struct XeenGameDescription {
+	ADGameDescription desc;
+
+	int gameID;
+	uint32 features;
+};
+
+} // End of namespace Xeen
diff --git a/engines/xeen/detection_enums.h b/engines/xeen/detection_enums.h
new file mode 100644
index 0000000000..90076adaa6
--- /dev/null
+++ b/engines/xeen/detection_enums.h
@@ -0,0 +1,32 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Xeen {
+
+enum {
+	GType_Clouds = 1,
+	GType_DarkSide = 2,
+	GType_WorldOfXeen = 3,
+	GType_Swords = 4
+};
+
+} // End of namespace Xeen
diff --git a/engines/xeen/metaengine.cpp b/engines/xeen/metaengine.cpp
new file mode 100644
index 0000000000..bbeca61390
--- /dev/null
+++ b/engines/xeen/metaengine.cpp
@@ -0,0 +1,193 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "xeen/xeen.h"
+#include "xeen/worldofxeen/worldofxeen.h"
+#include "xeen/swordsofxeen/swordsofxeen.h"
+
+#include "base/plugins.h"
+#include "common/savefile.h"
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+#include "common/translation.h"
+#include "xeen/detection.h"
+
+#define MAX_SAVES 99
+
+namespace Xeen {
+
+uint32 XeenEngine::getGameID() const {
+	return _gameDescription->gameID;
+}
+
+uint32 XeenEngine::getSpecificGameId() const {
+	uint gameId = g_vm->getGameID();
+	if (gameId == GType_WorldOfXeen)
+		gameId = _files->_ccNum ? GType_DarkSide : GType_Clouds;
+
+	return gameId;
+}
+
+uint32 XeenEngine::getGameFeatures() const {
+	return _gameDescription->features;
+}
+
+uint32 XeenEngine::getFeatures() const {
+	return _gameDescription->desc.flags;
+}
+
+Common::Language XeenEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+Common::Platform XeenEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+bool XeenEngine::getIsCD() const {
+	return getFeatures() & ADGF_CD;
+}
+
+} // End of namespace Xeen
+
+class XeenMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+	const char *getName() const override {
+		return "xeen";
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool XeenMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSimpleSavesNames);
+}
+
+bool Xeen::XeenEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime) ||
+		(f == kSupportsSavingDuringRuntime);
+}
+
+bool XeenMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Xeen::XeenGameDescription *gd = (const Xeen::XeenGameDescription *)desc;
+
+	switch (gd->gameID) {
+	case Xeen::GType_Clouds:
+	case Xeen::GType_DarkSide:
+	case Xeen::GType_WorldOfXeen:
+		*engine = new Xeen::WorldOfXeen::WorldOfXeenEngine(syst, gd);
+		break;
+	case Xeen::GType_Swords:
+		*engine = new Xeen::SwordsOfXeen::SwordsOfXeenEngine(syst, gd);
+		break;
+	default:
+		error("Invalid game");
+	}
+
+	return true;
+}
+
+SaveStateList XeenMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.###", target);
+	Xeen::XeenSavegameHeader header;
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		const char *ext = strrchr(file->c_str(), '.');
+		int slot = ext ? atoi(ext + 1) : -1;
+
+		if (slot >= 0 && slot <= MAX_SAVES) {
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+			if (in) {
+				if (Xeen::SavesManager::readSavegameHeader(in, header))
+					saveList.push_back(SaveStateDescriptor(slot, header._saveName));
+
+				delete in;
+			}
+		}
+	}
+
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int XeenMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVES;
+}
+
+void XeenMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor XeenMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
+
+	if (f) {
+		Xeen::XeenSavegameHeader header;
+		if (!Xeen::SavesManager::readSavegameHeader(f, header, false)) {
+			delete f;
+			return SaveStateDescriptor();
+		}
+
+		delete f;
+
+		// Create the return descriptor
+		SaveStateDescriptor desc(slot, header._saveName);
+		desc.setThumbnail(header._thumbnail);
+		desc.setSaveDate(header._year, header._month, header._day);
+		desc.setSaveTime(header._hour, header._minute);
+		desc.setPlayTime(header._totalFrames * GAME_FRAME_TIME);
+
+		return desc;
+	}
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(XEEN)
+	REGISTER_PLUGIN_DYNAMIC(XEEN, PLUGIN_TYPE_ENGINE, XeenMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(XEEN, PLUGIN_TYPE_ENGINE, XeenMetaEngineConnect);
+#endif
diff --git a/engines/xeen/module.mk b/engines/xeen/module.mk
index 4b8272df3c..71afe7762d 100644
--- a/engines/xeen/module.mk
+++ b/engines/xeen/module.mk
@@ -35,7 +35,6 @@ MODULE_OBJS := \
 	combat.o \
 	cutscenes.o \
 	debugger.o \
-	detection.o \
 	events.o \
 	files.o \
 	font.o \
@@ -45,6 +44,7 @@ MODULE_OBJS := \
 	item.o \
 	locations.o \
 	map.o \
+	metaengine.o \
 	party.o \
 	patcher.o \
 	resources.o \
@@ -68,3 +68,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/xeen/xeen.h b/engines/xeen/xeen.h
index be2310eaa3..503d6a5a99 100644
--- a/engines/xeen/xeen.h
+++ b/engines/xeen/xeen.h
@@ -47,6 +47,7 @@
 #include "xeen/sound.h"
 #include "xeen/spells.h"
 #include "xeen/window.h"
+#include "xeen/detection_enums.h"
 
 /**
  * This is the namespace of the Xeen engine.
@@ -61,13 +62,6 @@
  */
 namespace Xeen {
 
-enum {
-	GType_Clouds = 1,
-	GType_DarkSide = 2,
-	GType_WorldOfXeen = 3,
-	GType_Swords = 4
-};
-
 enum XeenDebugChannels {
 	kDebugPath      = 1 << 0,
 	kDebugScripts	= 1 << 1,


Commit: 30d2d9167e599c49a7027a6beb1d019a0ee3931b
    https://github.com/scummvm/scummvm/commit/30d2d9167e599c49a7027a6beb1d019a0ee3931b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: ME: Mark destructor as virtual

Changed paths:
    engines/metaengine.h


diff --git a/engines/metaengine.h b/engines/metaengine.h
index 376e3448bd..9ed6fd5abc 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -185,6 +185,8 @@ private:
 	 */
 	static void saveScreenThumbnail(Common::OutSaveFile *saveFile);
 public:
+	virtual ~MetaEngineConnect() {}
+
 	/**
 	 * Name of the engine plugin.
 	 * Classes inheriting a MetaEngineConnect must provide a engineID here,


Commit: 395f59055442d84765aabf990cab191cc98f4f37
    https://github.com/scummvm/scummvm/commit/395f59055442d84765aabf990cab191cc98f4f37
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: AMEC: Add some fallback detection-related functionality.

- Add fallbackDetectExtern, meant to be overriden by child classes, if fallbackdetection heavily depends on Engine code.
- Add getFileProperties helper.
- End function names with "extern" to distinguish from normal.

Changed paths:
    engines/advancedDetector.cpp
    engines/advancedDetector.h


diff --git a/engines/advancedDetector.cpp b/engines/advancedDetector.cpp
index d48ff83da4..52f2724a55 100644
--- a/engines/advancedDetector.cpp
+++ b/engines/advancedDetector.cpp
@@ -439,6 +439,36 @@ bool AdvancedMetaEngine::getFileProperties(const FileMap &allFiles, const ADGame
 	return true;
 }
 
+bool AdvancedMetaEngineConnect::getFilePropertiesExtern(uint md5Bytes, const Common::FSNode &parent, const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const {
+	// FIXME/TODO: We don't handle the case that a file is listed as a regular
+	// file and as one with resource fork.
+
+	if (game.flags & ADGF_MACRESFORK) {
+		Common::MacResManager macResMan;
+
+		if (!macResMan.open(parent, fname))
+			return false;
+
+		fileProps.md5 = macResMan.computeResForkMD5AsString(md5Bytes);
+		fileProps.size = macResMan.getResForkDataSize();
+
+		if (fileProps.size != 0)
+			return true;
+	}
+
+	if (!allFiles.contains(fname))
+		return false;
+
+	Common::File testFile;
+
+	if (!testFile.open(allFiles[fname]))
+		return false;
+
+	fileProps.size = (int32)testFile.size();
+	fileProps.md5 = Common::computeStreamMD5AsString(testFile, md5Bytes);
+	return true;
+}
+
 ADDetectedGames AdvancedMetaEngine::detectGame(const Common::FSNode &parent, const FileMap &allFiles, Common::Language language, Common::Platform platform, const Common::String &extra) const {
 	FilePropertiesMap filesProps;
 	ADDetectedGames matched;
diff --git a/engines/advancedDetector.h b/engines/advancedDetector.h
index d4fd4f686c..390716bb08 100644
--- a/engines/advancedDetector.h
+++ b/engines/advancedDetector.h
@@ -350,6 +350,31 @@ public:
 	 * @see MetaEngineConnect::getName().
 	 */
 	virtual const char *getName() const = 0;
+
+public:
+	typedef Common::HashMap<Common::String, Common::FSNode, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> FileMap;
+
+	/**
+	 * An (optional) generic fallback detect function which is invoked
+	 * if the regular MD5 based detection failed to detect anything.
+	 * NOTE: This is only meant to be used if fallback detection is heavily dependant on engine resources.
+	 *
+	 * To use this, implement the intended fallbackDetectExtern inside the relevant MetaEngineConnect class.
+	 * Then, override the method "fallbackDetect" inside your MetaEngine class.
+	 * Finally, provide a "hook" to fetch the relevant MetaEngineConnect class and then use the orignal detection
+	 * method.
+	 *
+	 * An example for the way this is used can be found in the Wintermute Engine.
+	 */
+	virtual ADDetectedGame fallbackDetectExtern(uint md5Bytes, const FileMap &allFiles, const Common::FSList &fslist) const {
+		return ADDetectedGame();
+	}
+
+	/**
+	 * Get the properties (size and MD5) of this file.
+	 * Based on MetaEngine::getFileProperties.
+	 */
+	bool getFilePropertiesExtern(uint md5Bytes, const Common::FSNode &parent, const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const;
 };
 
 #endif


Commit: 57b5a93f47c5e5a7ad96ccd86b4a4ad1058c87e9
    https://github.com/scummvm/scummvm/commit/57b5a93f47c5e5a7ad96ccd86b4a4ad1058c87e9
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
WINTERMUTE: Move engine/game-detection common enum to new header

Changed paths:
  A engines/wintermute/detection_enums.h
    engines/wintermute/wintermute.h


diff --git a/engines/wintermute/detection_enums.h b/engines/wintermute/detection_enums.h
new file mode 100644
index 0000000000..0781988426
--- /dev/null
+++ b/engines/wintermute/detection_enums.h
@@ -0,0 +1,33 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Wintermute {
+
+enum WintermuteGameFeatures {
+	/** A game with low-spec resources. */
+	GF_LOWSPEC_ASSETS       = 1 << 0,
+	GF_IGNORE_SD_FILES      = 1 << 1,
+	GF_IGNORE_HD_FILES      = 1 << 2,
+	GF_3D                   = 1 << 3
+};
+
+} // End of namespace Wintermute
diff --git a/engines/wintermute/wintermute.h b/engines/wintermute/wintermute.h
index 21befc2f34..08bfa4f6e8 100644
--- a/engines/wintermute/wintermute.h
+++ b/engines/wintermute/wintermute.h
@@ -26,6 +26,7 @@
 #include "engines/engine.h"
 #include "gui/debugger.h"
 #include "common/fs.h"
+#include "wintermute/detection_enums.h"
 
 namespace Wintermute {
 
@@ -47,14 +48,6 @@ enum {
 	kWintermuteDebugGeneral = 1 << 5
 };
 
-enum WintermuteGameFeatures {
- 	/** A game with low-spec resources. */
- 	GF_LOWSPEC_ASSETS       = 1 << 0,
- 	GF_IGNORE_SD_FILES      = 1 << 1,
- 	GF_IGNORE_HD_FILES      = 1 << 2,
- 	GF_3D                   = 1 << 3
-};
-
 class WintermuteEngine : public Engine {
 public:
 	WintermuteEngine(OSystem *syst, const WMEGameDescription *desc);


Commit: b4044c87e74074fe67fb911b4d9f6db8cf75ff21
    https://github.com/scummvm/scummvm/commit/b4044c87e74074fe67fb911b4d9f6db8cf75ff21
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
WINTERMUTE: Move game/engine common enums from /base to a common enum

Changed paths:
  A engines/wintermute/base/base_detection_enums.h
    engines/wintermute/base/base_engine.h


diff --git a/engines/wintermute/base/base_detection_enums.h b/engines/wintermute/base/base_detection_enums.h
new file mode 100644
index 0000000000..f0c903aca3
--- /dev/null
+++ b/engines/wintermute/base/base_detection_enums.h
@@ -0,0 +1,114 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace Wintermute {
+
+enum WMETargetExecutable {
+	OLDEST_VERSION,
+	WME_1_0_12, // DEAD:CODE 2003
+	WME_1_0_19, // DEAD:CODE 2003
+	WME_1_0_20, // DEAD:CODE 2003
+	WME_1_0_22, // DEAD:CODE 2003
+	WME_1_0_24, // DEAD:CODE 2003
+	WME_1_0_25, // DEAD:CODE 2003
+	WME_1_0_28, // DEAD:CODE 2003
+	WME_1_0_30, // DEAD:CODE 2003
+	WME_1_0_31, // DEAD:CODE 2003
+	WME_1_1_33, // DEAD:CODE 2003
+	WME_1_1_35, // DEAD:CODE 2003
+	WME_1_1_37, // DEAD:CODE 2003
+	WME_1_1_39, // DEAD:CODE 2004
+	WME_1_2_43, // DEAD:CODE 2004
+	WME_1_2_44, // DEAD:CODE 2004
+	WME_1_3_0,  // DEAD:CODE 2004
+	WME_1_3_2,  // DEAD:CODE 2004
+	WME_1_3_3,  // DEAD:CODE 2004
+	WME_1_4_0,  // DEAD:CODE 2005
+	WME_1_4_1,  // DEAD:CODE 2005
+	WME_1_5_0,  // DEAD:CODE 2005
+	WME_1_5_2,  // DEAD:CODE 2005
+	WME_1_6_0,  // DEAD:CODE 2006
+	WME_1_6_1,  // DEAD:CODE 2006
+	WME_1_7_0,  // DEAD:CODE 2007
+	WME_1_7_1,  // DEAD:CODE 2007
+	WME_1_7_2,  // DEAD:CODE 2007
+	WME_1_7_3,  // DEAD:CODE 2007
+	WME_1_7_93, // DEAD:CODE 2007
+	WME_1_7_94, // DEAD:CODE 2007
+	WME_1_8_0,  // DEAD:CODE 2007
+	WME_1_8_1,  // DEAD:CODE 2007
+	WME_1_8_2,  // DEAD:CODE 2008
+	WME_1_8_3,  // DEAD:CODE 2008
+	WME_1_8_4,  // DEAD:CODE 2008
+	WME_1_8_5,  // DEAD:CODE 2008
+	WME_1_8_6,  // DEAD:CODE 2008
+	WME_1_8_7,  // DEAD:CODE 2008, released as "1.8.7 beta"
+	WME_1_8_8,  // DEAD:CODE 2008, released as "1.8.8 beta"
+	WME_1_8_9,  // DEAD:CODE 2008, released as "1.8.9 beta"
+	WME_1_8_10, // DEAD:CODE 2009
+
+	// fork of WME_1_8_10
+	WME_ANDISHE_VARAN, // Andishe Varan Engine 1.0.0.0
+
+	WME_1_8_11, // DEAD:CODE 2009
+	WME_1_9_0,  // DEAD:CODE 2009, released as "1.9.0 beta"
+
+	// fork of WME_1_9_0
+	WME_KINJAL_1_0,
+	WME_KINJAL_1_1,
+	WME_KINJAL_1_2,
+	WME_KINJAL_1_3,
+	WME_KINJAL_1_4,
+
+	// fork of WME_KINJAL_1_4
+	WME_HEROCRAFT,
+
+	WME_1_9_1,  // DEAD:CODE 2010
+
+	// fork of WME_1_9_1
+	WME_KINJAL_1_5,
+	WME_KINJAL_1_6,
+	WME_KINJAL_1_7,
+	WME_KINJAL_1_7a,
+	WME_KINJAL_1_7b,
+	WME_KINJAL_1_8,
+	WME_KINJAL_1_9,
+	WME_KINJAL_2_0,
+
+	WME_1_9_2,  // DEAD:CODE 2010
+	WME_1_9_3,  // DEAD:CODE 2012, released as "1.10.1 beta"
+	WME_LITE,
+	LATEST_VERSION,
+
+	// fork of WME_LITE
+	FOXTAIL_OLDEST_VERSION,
+	FOXTAIL_1_2_227,
+	FOXTAIL_1_2_230,
+	FOXTAIL_1_2_304,
+	FOXTAIL_1_2_362,
+	FOXTAIL_1_2_527,
+	FOXTAIL_1_2_896,
+	FOXTAIL_1_2_902,
+	FOXTAIL_LATEST_VERSION
+};
+
+} // End of namespace Wintermute
diff --git a/engines/wintermute/base/base_engine.h b/engines/wintermute/base/base_engine.h
index 5888b84a5e..0691240bd1 100644
--- a/engines/wintermute/base/base_engine.h
+++ b/engines/wintermute/base/base_engine.h
@@ -34,96 +34,9 @@
 #include "common/random.h"
 #include "common/language.h"
 
-namespace Wintermute {
-
-enum WMETargetExecutable {
-	OLDEST_VERSION,
-	WME_1_0_12, // DEAD:CODE 2003
-	WME_1_0_19, // DEAD:CODE 2003
-	WME_1_0_20, // DEAD:CODE 2003
-	WME_1_0_22, // DEAD:CODE 2003
-	WME_1_0_24, // DEAD:CODE 2003
-	WME_1_0_25, // DEAD:CODE 2003
-	WME_1_0_28, // DEAD:CODE 2003
-	WME_1_0_30, // DEAD:CODE 2003
-	WME_1_0_31, // DEAD:CODE 2003
-	WME_1_1_33, // DEAD:CODE 2003
-	WME_1_1_35, // DEAD:CODE 2003
-	WME_1_1_37, // DEAD:CODE 2003
-	WME_1_1_39, // DEAD:CODE 2004
-	WME_1_2_43, // DEAD:CODE 2004
-	WME_1_2_44, // DEAD:CODE 2004
-	WME_1_3_0,  // DEAD:CODE 2004
-	WME_1_3_2,  // DEAD:CODE 2004
-	WME_1_3_3,  // DEAD:CODE 2004
-	WME_1_4_0,  // DEAD:CODE 2005
-	WME_1_4_1,  // DEAD:CODE 2005
-	WME_1_5_0,  // DEAD:CODE 2005
-	WME_1_5_2,  // DEAD:CODE 2005
-	WME_1_6_0,  // DEAD:CODE 2006
-	WME_1_6_1,  // DEAD:CODE 2006
-	WME_1_7_0,  // DEAD:CODE 2007
-	WME_1_7_1,  // DEAD:CODE 2007
-	WME_1_7_2,  // DEAD:CODE 2007
-	WME_1_7_3,  // DEAD:CODE 2007
-	WME_1_7_93, // DEAD:CODE 2007
-	WME_1_7_94, // DEAD:CODE 2007
-	WME_1_8_0,  // DEAD:CODE 2007
-	WME_1_8_1,  // DEAD:CODE 2007
-	WME_1_8_2,  // DEAD:CODE 2008
-	WME_1_8_3,  // DEAD:CODE 2008
-	WME_1_8_4,  // DEAD:CODE 2008
-	WME_1_8_5,  // DEAD:CODE 2008
-	WME_1_8_6,  // DEAD:CODE 2008
-	WME_1_8_7,  // DEAD:CODE 2008, released as "1.8.7 beta"
-	WME_1_8_8,  // DEAD:CODE 2008, released as "1.8.8 beta"
-	WME_1_8_9,  // DEAD:CODE 2008, released as "1.8.9 beta"
-	WME_1_8_10, // DEAD:CODE 2009
-
-	// fork of WME_1_8_10
-	WME_ANDISHE_VARAN, // Andishe Varan Engine 1.0.0.0
-
-	WME_1_8_11, // DEAD:CODE 2009
-	WME_1_9_0,  // DEAD:CODE 2009, released as "1.9.0 beta"
-
-	// fork of WME_1_9_0
-	WME_KINJAL_1_0,
-	WME_KINJAL_1_1,
-	WME_KINJAL_1_2,
-	WME_KINJAL_1_3,
-	WME_KINJAL_1_4,
-
-	// fork of WME_KINJAL_1_4
-	WME_HEROCRAFT,
+#include "engines/wintermute/base/base_detection_enums.h"
 
-	WME_1_9_1,  // DEAD:CODE 2010
-
-	// fork of WME_1_9_1
-	WME_KINJAL_1_5,
-	WME_KINJAL_1_6,
-	WME_KINJAL_1_7,
-	WME_KINJAL_1_7a,
-	WME_KINJAL_1_7b,
-	WME_KINJAL_1_8,
-	WME_KINJAL_1_9,
-	WME_KINJAL_2_0,
-
-	WME_1_9_2,  // DEAD:CODE 2010
-	WME_1_9_3,  // DEAD:CODE 2012, released as "1.10.1 beta"
-	WME_LITE,
-	LATEST_VERSION,
-
-	// fork of WME_LITE
-	FOXTAIL_OLDEST_VERSION,
-	FOXTAIL_1_2_227,
-	FOXTAIL_1_2_230,
-	FOXTAIL_1_2_304,
-	FOXTAIL_1_2_362,
-	FOXTAIL_1_2_527,
-	FOXTAIL_1_2_896,
-	FOXTAIL_1_2_902,
-	FOXTAIL_LATEST_VERSION
-};
+namespace Wintermute {
 
 class BaseFileManager;
 class BaseRegistry;


Commit: 0b9df0411259fe9c90e5f66c183fc8317805eff9
    https://github.com/scummvm/scummvm/commit/0b9df0411259fe9c90e5f66c183fc8317805eff9
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
WINTERMUTE: Rename game_description.h -> detection.h

- Done to match consistency with other engines.
- Remove external header file.
- Match namecalling of header where needed.

Changed paths:
  A engines/wintermute/detection.h
  R engines/wintermute/game_description.h
    engines/wintermute/base/base_sprite.cpp
    engines/wintermute/wintermute.cpp


diff --git a/engines/wintermute/base/base_sprite.cpp b/engines/wintermute/base/base_sprite.cpp
index cde1225ead..eb88e3de09 100644
--- a/engines/wintermute/base/base_sprite.cpp
+++ b/engines/wintermute/base/base_sprite.cpp
@@ -41,7 +41,7 @@
 #include "engines/wintermute/base/scriptables/script_value.h"
 #include "engines/wintermute/base/scriptables/script.h"
 #include "engines/wintermute/base/scriptables/script_stack.h"
-#include "engines/wintermute/game_description.h"
+#include "engines/wintermute/detection.h"
 
 namespace Wintermute {
 
diff --git a/engines/wintermute/game_description.h b/engines/wintermute/detection.h
similarity index 96%
rename from engines/wintermute/game_description.h
rename to engines/wintermute/detection.h
index 92f62dd7f6..0d75a58f27 100644
--- a/engines/wintermute/game_description.h
+++ b/engines/wintermute/detection.h
@@ -24,7 +24,6 @@
 #define WINTERMUTE_GAME_DESCRIPTION_H
 
 #include "engines/advancedDetector.h"
-#include "engines/wintermute/base/base_engine.h"
 
 namespace Wintermute {
 
@@ -33,6 +32,6 @@ struct WMEGameDescription {
 	WMETargetExecutable targetExecutable;
 };
 
-}
+} // End of namespace Wintermute
 
 #endif  /* WINTERMUTE_GAME_DESCRIPTION_H_ */
diff --git a/engines/wintermute/wintermute.cpp b/engines/wintermute/wintermute.cpp
index 2ca21495fb..579fd54bfc 100644
--- a/engines/wintermute/wintermute.cpp
+++ b/engines/wintermute/wintermute.cpp
@@ -35,9 +35,9 @@
 #include "engines/wintermute/ad/ad_game.h"
 #include "engines/wintermute/wintermute.h"
 #include "engines/wintermute/debugger.h"
-#include "engines/wintermute/game_description.h"
 #include "engines/wintermute/platform_osystem.h"
 #include "engines/wintermute/base/base_engine.h"
+#include "engines/wintermute/detection.h"
 
 #include "engines/wintermute/base/sound/base_sound_manager.h"
 #include "engines/wintermute/base/base_file_manager.h"


Commit: c9f2c50380547326a5312d0db6abe61c2fc6104e
    https://github.com/scummvm/scummvm/commit/c9f2c50380547326a5312d0db6abe61c2fc6104e
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
WINTERMUTE: Split detection features & adapt to new plugins.

- Update AMEC's getFileProps (changes related to MacResMan)
- This commit also includes a change from other engines.
- Fallback detection here depends upon many Engine resources.
- As such, it might not be suitable to add all of them to executable.
- Thus, shift fallback detection to the dynamic part.
- The static part gets the relevant Engine plugin & then tries to call it.
- This way, fallback detection for Wintermute will depend on the engine plugin.
- Normal detection will still work fine.

Changed paths:
  A engines/wintermute/metaengine.cpp
    configure
    engines/advancedDetector.cpp
    engines/advancedDetector.h
    engines/wintermute/detection.cpp
    engines/wintermute/ext/wme_galaxy.cpp
    engines/wintermute/ext/wme_steam.cpp
    engines/wintermute/module.mk


diff --git a/configure b/configure
index c7b56b9d16..b26ca3a614 100755
--- a/configure
+++ b/configure
@@ -6170,7 +6170,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
 								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR"
-								  "FULLPIPE" "SAGA" "XEEN")
+								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/advancedDetector.cpp b/engines/advancedDetector.cpp
index 52f2724a55..8ffdc55dc8 100644
--- a/engines/advancedDetector.cpp
+++ b/engines/advancedDetector.cpp
@@ -439,14 +439,16 @@ bool AdvancedMetaEngine::getFileProperties(const FileMap &allFiles, const ADGame
 	return true;
 }
 
-bool AdvancedMetaEngineConnect::getFilePropertiesExtern(uint md5Bytes, const Common::FSNode &parent, const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const {
+bool AdvancedMetaEngineConnect::getFilePropertiesExtern(uint md5Bytes, const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const {
 	// FIXME/TODO: We don't handle the case that a file is listed as a regular
 	// file and as one with resource fork.
 
 	if (game.flags & ADGF_MACRESFORK) {
+		FileMapArchive fileMapArchive(allFiles);
+
 		Common::MacResManager macResMan;
 
-		if (!macResMan.open(parent, fname))
+		if (!macResMan.open(fname, fileMapArchive))
 			return false;
 
 		fileProps.md5 = macResMan.computeResForkMD5AsString(md5Bytes);
diff --git a/engines/advancedDetector.h b/engines/advancedDetector.h
index 390716bb08..972b214644 100644
--- a/engines/advancedDetector.h
+++ b/engines/advancedDetector.h
@@ -374,7 +374,7 @@ public:
 	 * Get the properties (size and MD5) of this file.
 	 * Based on MetaEngine::getFileProperties.
 	 */
-	bool getFilePropertiesExtern(uint md5Bytes, const Common::FSNode &parent, const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const;
+	bool getFilePropertiesExtern(uint md5Bytes, const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const;
 };
 
 #endif
diff --git a/engines/wintermute/detection.cpp b/engines/wintermute/detection.cpp
index 1ad248c192..a02ed8038f 100644
--- a/engines/wintermute/detection.cpp
+++ b/engines/wintermute/detection.cpp
@@ -21,11 +21,7 @@
  */
 
 #include "engines/advancedDetector.h"
-#include "engines/wintermute/wintermute.h"
-#include "engines/wintermute/game_description.h"
-#include "engines/wintermute/base/base_persistence_manager.h"
 
-#include "common/achievements.h"
 #include "common/config-manager.h"
 #include "common/error.h"
 #include "common/fs.h"
@@ -34,27 +30,13 @@
 
 #include "engines/metaengine.h"
 
-#include "engines/wintermute/achievements_tables.h"
+#include "wintermute/base/base_detection_enums.h"
+#include "wintermute/detection_enums.h"
+#include "engines/wintermute/detection.h"
 #include "engines/wintermute/detection_tables.h"
-#include "engines/wintermute/keymapper_tables.h"
 
 namespace Wintermute {
 
-/**
- * The fallback game descriptor used by the Wintermute engine's fallbackDetector.
- * Contents of this struct are overwritten by the fallbackDetector. (logic copied partially
- * from the SCI-engine).
- */
-static ADGameDescription s_fallbackDesc = {
-	"",
-	"",
-	AD_ENTRY1(0, 0), // This should always be AD_ENTRY1(0, 0) in the fallback descriptor
-	Common::UNK_LANG,
-	Common::kPlatformWindows,
-	ADGF_UNSTABLE,
-	GUIO0()
-};
-
 static const ADExtraGuiOptionsMap gameGuiOptions[] = {
 	{
 		GAMEOPTION_SHOW_FPS,
@@ -79,8 +61,6 @@ static const ADExtraGuiOptionsMap gameGuiOptions[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-static char s_fallbackExtraBuf[256];
-
 static const char *directoryGlobs[] = {
 	"language", // To detect the various languages
 	"languages", // To detect the various languages
@@ -112,153 +92,29 @@ public:
 	}
 
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override {
-		// Set some defaults
-		s_fallbackDesc.extra = "";
-		s_fallbackDesc.language = Common::UNK_LANG;
-		s_fallbackDesc.flags = ADGF_UNSTABLE;
-		s_fallbackDesc.platform = Common::kPlatformWindows; // default to Windows
-		s_fallbackDesc.gameId = "wintermute";
-		s_fallbackDesc.guiOptions = GUIO0();
-
-		if (!allFiles.contains("data.dcp")) {
-			return ADDetectedGame();
-		}
-
-		Common::String name, caption;
-		if (!WintermuteEngine::getGameInfo(fslist, name, caption)) {
-			return ADDetectedGame();
-		}
-
-		Common::String extra = caption;
-		if (extra.empty()) {
-			extra = name;
-		}
-
-		if (!extra.empty()) {
-			Common::strlcpy(s_fallbackExtraBuf, extra.c_str(), sizeof(s_fallbackExtraBuf) - 1);
-			s_fallbackDesc.extra = s_fallbackExtraBuf;
-			s_fallbackDesc.flags |= ADGF_USEEXTRAASTITLE;
-			s_fallbackDesc.flags |= ADGF_AUTOGENTARGET;
-		}
-
-		ADDetectedGame game(&s_fallbackDesc);
-
-		for (Common::FSList::const_iterator file = fslist.begin(); file != fslist.end(); ++file) {
-			if (file->isDirectory()) continue;
-			if (!file->getName().hasSuffixIgnoreCase(".dcp")) continue;
-
-			FileProperties tmp;
-			if (getFileProperties(allFiles, s_fallbackDesc, file->getName(), tmp)) {
-				game.hasUnknownFiles = true;
-				game.matchedFiles[file->getName()] = tmp;
-			}
-		}
-
-		return game;
-	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
-		assert(syst);
-		assert(engine);
-		const WMEGameDescription *gd = (const WMEGameDescription *)desc;
-		*engine = new Wintermute::WintermuteEngine(syst, gd);
-		return true;
-	}
-
-	bool hasFeature(MetaEngineFeature f) const override {
-		switch (f) {
-		case MetaEngine::kSupportsListSaves:
-			return true;
-		case MetaEngine::kSupportsLoadingDuringStartup:
-			return true;
-		case MetaEngine::kSupportsDeleteSave:
-			return true;
-		case MetaEngine::kSavesSupportCreationDate:
-			return true;
-		case MetaEngine::kSavesSupportMetaInfo:
-			return true;
-		case MetaEngine::kSavesSupportThumbnail:
-			return true;
-		default:
-			return false;
-		}
-	}
-
-	SaveStateList listSaves(const char *target) const override {
-		SaveStateList saves;
-		Wintermute::BasePersistenceManager pm(target, true);
-		for (int i = 0; i < getMaximumSaveSlot(); i++) {
-			if (pm.getSaveExists(i)) {
-				SaveStateDescriptor desc;
-				pm.getSaveStateDesc(i, desc);
-				saves.push_back(desc);
-			}
-		}
-		return saves;
-	}
-
-	int getMaximumSaveSlot() const override {
-		return 100;
-	}
-
-	void removeSaveState(const char *target, int slot) const override {
-		Wintermute::BasePersistenceManager pm(target, true);
-		pm.deleteSaveSlot(slot);
-	}
-
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
-		Wintermute::BasePersistenceManager pm(target, true);
-		SaveStateDescriptor retVal;
-		retVal.setDescription("Invalid savegame");
-		pm.getSaveStateDesc(slot, retVal);
-		return retVal;
-	}
-
-	const Common::AchievementsInfo getAchievementsInfo(const Common::String &target) const override {
-		Common::String gameId = ConfMan.get("gameid", target);
-
-		// HACK: "juliauntold" is a DLC of "juliastars", they share the same achievements list
-		if (gameId == "juliauntold") {
-			gameId = "juliastars";
-		}
-
-		Common::AchievementsPlatform platform = Common::STEAM_ACHIEVEMENTS;
-		if (ConfMan.get("extra", target).contains("GOG")) {
-			platform = Common::GALAXY_ACHIEVEMENTS;
-		}
-
-		// "(gameId, platform) -> result" search
-		Common::AchievementsInfo result;
-		for (const AchievementDescriptionList *i = achievementDescriptionList; i->gameId; i++) {
-			if (i->gameId == gameId && i->platform == platform) {
-				result.platform = i->platform;
-				result.appId = i->appId;
-				for (const Common::AchievementDescription *it = i->descriptions; it->id; it++) {
-					result.descriptions.push_back(*it);
+		/**
+		 * Fallback detection for Wintermute heavily depends on engine resources, so it's not possible
+		 * to use them without the engine present in a clean way.
+		 */
+		static const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
+
+		if (metaEnginePlugin) {
+			static const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+			if (enginePlugin) {
+				return enginePlugin->get<AdvancedMetaEngineConnect>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
+			} else {
+				static bool warn = true;
+				if (warn) {
+					warning("Engine plugin for Wintermute not found. Some games will fail to be detected until an engine plugin is present.");
+					warn = false;
 				}
-				break;
-			}
-		}
-		return result;
-	}
-	
-	Common::KeymapArray initKeymaps(const char *target) const override {
-		Common::String gameId = ConfMan.get("gameid", target);
-		const char *gameDescr = "Unknown WME game";
-		for (const PlainGameDescriptor *it = Wintermute::wintermuteGames; it->gameId ; it++ ) {
-			if (gameId == it->gameId) {
-				gameDescr = it->description;
 			}
 		}
-		return getWintermuteKeymaps(target, gameId, gameDescr);
+		return ADDetectedGame();
 	}
 
 };
 
 } // End of namespace Wintermute
 
-#if PLUGIN_ENABLED_DYNAMIC(WINTERMUTE)
-	REGISTER_PLUGIN_DYNAMIC(WINTERMUTE, PLUGIN_TYPE_ENGINE, Wintermute::WintermuteMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(WINTERMUTE, PLUGIN_TYPE_ENGINE, Wintermute::WintermuteMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(WINTERMUTE_DETECTION, PLUGIN_TYPE_METAENGINE, Wintermute::WintermuteMetaEngine);
diff --git a/engines/wintermute/ext/wme_galaxy.cpp b/engines/wintermute/ext/wme_galaxy.cpp
index 949839a046..cd70a484c5 100644
--- a/engines/wintermute/ext/wme_galaxy.cpp
+++ b/engines/wintermute/ext/wme_galaxy.cpp
@@ -50,7 +50,7 @@ SXWMEGalaxyAPI::SXWMEGalaxyAPI(BaseGame *inGame, ScStack *stack) : BaseScriptabl
 
 //////////////////////////////////////////////////////////////////////////
 void SXWMEGalaxyAPI::init() {
-	MetaEngine &meta = ((WintermuteEngine *)g_engine)->getMetaEngine();
+	const MetaEngineConnect &meta = ((WintermuteEngine *)g_engine)->getMetaEngineConnect();
 	const Common::String target = BaseEngine::instance().getGameTargetName();
 	_achievementsInfo = meta.getAchievementsInfo(target);
 
diff --git a/engines/wintermute/ext/wme_steam.cpp b/engines/wintermute/ext/wme_steam.cpp
index 47812abc32..62bc171869 100644
--- a/engines/wintermute/ext/wme_steam.cpp
+++ b/engines/wintermute/ext/wme_steam.cpp
@@ -50,7 +50,7 @@ SXSteamAPI::SXSteamAPI(BaseGame *inGame, ScStack *stack) : BaseScriptable(inGame
 
 //////////////////////////////////////////////////////////////////////////
 void SXSteamAPI::init() {
-	MetaEngine &meta = ((WintermuteEngine *)g_engine)->getMetaEngine();
+	const MetaEngineConnect &meta = ((WintermuteEngine *)g_engine)->getMetaEngineConnect();
 	const Common::String target = BaseEngine::instance().getGameTargetName();
 	_achievementsInfo = meta.getAchievementsInfo(target);
 
diff --git a/engines/wintermute/metaengine.cpp b/engines/wintermute/metaengine.cpp
new file mode 100644
index 0000000000..03c717dc5d
--- /dev/null
+++ b/engines/wintermute/metaengine.cpp
@@ -0,0 +1,210 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "common/achievements.h"
+
+#include "engines/wintermute/wintermute.h"
+#include "engines/wintermute/base/base_persistence_manager.h"
+
+#include "engines/wintermute/keymapper_tables.h"
+#include "engines/wintermute/achievements_tables.h"
+
+// Detection related files.
+#include "wintermute/base/base_detection_enums.h"
+#include "wintermute/detection.h"
+#include "engines/wintermute/detection_tables.h"
+
+namespace Wintermute {
+
+/**
+ * The fallback game descriptor used by the Wintermute engine's fallbackDetector.
+ * Contents of this struct are overwritten by the fallbackDetector. (logic copied partially
+ * from the SCI-engine).
+ */
+static ADGameDescription s_fallbackDesc = {
+	"",
+	"",
+	AD_ENTRY1(0, 0), // This should always be AD_ENTRY1(0, 0) in the fallback descriptor
+	Common::UNK_LANG,
+	Common::kPlatformWindows,
+	ADGF_UNSTABLE,
+	GUIO0()
+};
+
+static char s_fallbackExtraBuf[256];
+
+class WintermuteMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "wintermute";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override {
+		assert(syst);
+		assert(engine);
+		const WMEGameDescription *gd = (const WMEGameDescription *)desc;
+		*engine = new Wintermute::WintermuteEngine(syst, gd);
+		return true;
+	}
+
+	bool hasFeature(MetaEngineFeature f) const override {
+		switch (f) {
+		case MetaEngineConnect::kSupportsListSaves:
+			return true;
+		case MetaEngineConnect::kSupportsLoadingDuringStartup:
+			return true;
+		case MetaEngineConnect::kSupportsDeleteSave:
+			return true;
+		case MetaEngineConnect::kSavesSupportCreationDate:
+			return true;
+		case MetaEngineConnect::kSavesSupportMetaInfo:
+			return true;
+		case MetaEngineConnect::kSavesSupportThumbnail:
+			return true;
+		default:
+			return false;
+		}
+	}
+
+	SaveStateList listSaves(const char *target) const override {
+		SaveStateList saves;
+		Wintermute::BasePersistenceManager pm(target, true);
+		for (int i = 0; i < getMaximumSaveSlot(); i++) {
+			if (pm.getSaveExists(i)) {
+				SaveStateDescriptor desc;
+				pm.getSaveStateDesc(i, desc);
+				saves.push_back(desc);
+			}
+		}
+		return saves;
+	}
+
+	int getMaximumSaveSlot() const override {
+		return 100;
+	}
+
+	void removeSaveState(const char *target, int slot) const override {
+		Wintermute::BasePersistenceManager pm(target, true);
+		pm.deleteSaveSlot(slot);
+	}
+
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override {
+		Wintermute::BasePersistenceManager pm(target, true);
+		SaveStateDescriptor retVal;
+		retVal.setDescription("Invalid savegame");
+		pm.getSaveStateDesc(slot, retVal);
+		return retVal;
+	}
+
+    const Common::AchievementsInfo getAchievementsInfo(const Common::String &target) const override {
+		Common::String gameId = ConfMan.get("gameid", target);
+
+		// HACK: "juliauntold" is a DLC of "juliastars", they share the same achievements list
+		if (gameId == "juliauntold") {
+			gameId = "juliastars";
+		}
+
+		Common::AchievementsPlatform platform = Common::STEAM_ACHIEVEMENTS;
+		if (ConfMan.get("extra", target).contains("GOG")) {
+			platform = Common::GALAXY_ACHIEVEMENTS;
+		}
+
+		// "(gameId, platform) -> result" search
+		Common::AchievementsInfo result;
+		for (const AchievementDescriptionList *i = achievementDescriptionList; i->gameId; i++) {
+			if (i->gameId == gameId && i->platform == platform) {
+				result.platform = i->platform;
+				result.appId = i->appId;
+				for (const Common::AchievementDescription *it = i->descriptions; it->id; it++) {
+					result.descriptions.push_back(*it);
+				}
+				break;
+			}
+		}
+		return result;
+	}
+
+	Common::KeymapArray initKeymaps(const char *target) const override {
+		Common::String gameId = ConfMan.get("gameid", target);
+		const char *gameDescr = "Unknown WME game";
+		for (const PlainGameDescriptor *it = Wintermute::wintermuteGames; it->gameId ; it++ ) {
+			if (gameId == it->gameId) {
+				gameDescr = it->description;
+			}
+		}
+		return getWintermuteKeymaps(target, gameId, gameDescr);
+	}
+
+	ADDetectedGame fallbackDetectExtern(uint md5Bytes, const FileMap &allFiles, const Common::FSList &fslist) const override {
+		// Set some defaults
+		s_fallbackDesc.extra = "";
+		s_fallbackDesc.language = Common::UNK_LANG;
+		s_fallbackDesc.flags = ADGF_UNSTABLE;
+		s_fallbackDesc.platform = Common::kPlatformWindows; // default to Windows
+		s_fallbackDesc.gameId = "wintermute";
+		s_fallbackDesc.guiOptions = GUIO0();
+
+		if (!allFiles.contains("data.dcp")) {
+			return ADDetectedGame();
+		}
+
+		Common::String name, caption;
+		if (!WintermuteEngine::getGameInfo(fslist, name, caption)) {
+			return ADDetectedGame();
+		}
+
+		Common::String extra = caption;
+		if (extra.empty()) {
+			extra = name;
+		}
+
+		if (!extra.empty()) {
+			Common::strlcpy(s_fallbackExtraBuf, extra.c_str(), sizeof(s_fallbackExtraBuf) - 1);
+			s_fallbackDesc.extra = s_fallbackExtraBuf;
+			s_fallbackDesc.flags |= ADGF_USEEXTRAASTITLE;
+			s_fallbackDesc.flags |= ADGF_AUTOGENTARGET;
+		}
+
+		ADDetectedGame game(&s_fallbackDesc);
+
+		for (Common::FSList::const_iterator file = fslist.begin(); file != fslist.end(); ++file) {
+			if (file->isDirectory()) continue;
+			if (!file->getName().hasSuffixIgnoreCase(".dcp")) continue;
+
+			FileProperties tmp;
+			if (AdvancedMetaEngineConnect::getFilePropertiesExtern(md5Bytes, allFiles, s_fallbackDesc, file->getName(), tmp)) {
+				game.hasUnknownFiles = true;
+				game.matchedFiles[file->getName()] = tmp;
+			}
+		}
+
+		return game;
+	}
+};
+
+} // End of namespace Wintermute
+
+#if PLUGIN_ENABLED_DYNAMIC(WINTERMUTE)
+	REGISTER_PLUGIN_DYNAMIC(WINTERMUTE, PLUGIN_TYPE_ENGINE, Wintermute::WintermuteMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(WINTERMUTE, PLUGIN_TYPE_ENGINE, Wintermute::WintermuteMetaEngineConnect);
+#endif
diff --git a/engines/wintermute/module.mk b/engines/wintermute/module.mk
index 7d6045dd60..9a701fbd12 100644
--- a/engines/wintermute/module.mk
+++ b/engines/wintermute/module.mk
@@ -116,10 +116,10 @@ MODULE_OBJS := \
 	debugger/script_monitor.o \
 	debugger/watch.o \
 	debugger/watch_instance.o \
-	detection.o \
 	math/math_util.o \
 	math/matrix4.o \
 	math/vector2.o \
+	metaengine.o \
 	platform_osystem.o \
 	system/sys_class.o \
 	system/sys_class_registry.o \
@@ -154,3 +154,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: e6447822948a3a75c34e93c141005062ef8355f3
    https://github.com/scummvm/scummvm/commit/e6447822948a3a75c34e93c141005062ef8355f3
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCI: Move graphics helpers/detection related enums into a new header

Changed paths:
  A engines/sci/graphics/helpers_detection_enums.h
    engines/sci/graphics/helpers.h


diff --git a/engines/sci/graphics/helpers.h b/engines/sci/graphics/helpers.h
index 8b59dee21a..68b99828e7 100644
--- a/engines/sci/graphics/helpers.h
+++ b/engines/sci/graphics/helpers.h
@@ -32,6 +32,7 @@
 #include "graphics/surface.h"
 #endif
 #include "sci/engine/vm_types.h"
+#include "sci/graphics/helpers_detection_enums.h" // for enum ViewType
 
 namespace Sci {
 
@@ -269,16 +270,6 @@ struct PalSchedule {
 	uint32 schedule;
 };
 
-// Game view types, sorted by the number of colors
-enum ViewType {
-	kViewUnknown,   // uninitialized, or non-SCI
-	kViewEga,       // EGA SCI0/SCI1 and Amiga SCI0/SCI1 ECS 16 colors
-	kViewAmiga,     // Amiga SCI1 ECS 32 colors
-	kViewAmiga64,   // Amiga SCI1 AGA 64 colors (i.e. Longbow)
-	kViewVga,       // VGA SCI1 256 colors
-	kViewVga11      // VGA SCI1.1 and newer 256 colors
-};
-
 } // End of namespace Sci
 
 #endif
diff --git a/engines/sci/graphics/helpers_detection_enums.h b/engines/sci/graphics/helpers_detection_enums.h
new file mode 100644
index 0000000000..cdd9b51777
--- /dev/null
+++ b/engines/sci/graphics/helpers_detection_enums.h
@@ -0,0 +1,39 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef SCI_HELPERES_DETECTION_ENUMS_H
+#define SCI_HELPERES_DETECTION_ENUMS_H
+
+namespace Sci {
+// Game view types, sorted by the number of colors
+enum ViewType {
+	kViewUnknown,   // uninitialized, or non-SCI
+	kViewEga,       // EGA SCI0/SCI1 and Amiga SCI0/SCI1 ECS 16 colors
+	kViewAmiga,     // Amiga SCI1 ECS 32 colors
+	kViewAmiga64,   // Amiga SCI1 AGA 64 colors (i.e. Longbow)
+	kViewVga,       // VGA SCI1 256 colors
+	kViewVga11      // VGA SCI1.1 and newer 256 colors
+};
+
+} // End of namespace Sci
+
+#endif


Commit: aa353cc4fbf99ec4000d0dc9d1fc1c9b982c3dfb
    https://github.com/scummvm/scummvm/commit/aa353cc4fbf99ec4000d0dc9d1fc1c9b982c3dfb
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCI: Move engine/detection common enums to new header.

Changed paths:
  A engines/sci/detection_defines.h
  A engines/sci/detection_enums.h
    engines/sci/sci.h


diff --git a/engines/sci/detection_defines.h b/engines/sci/detection_defines.h
new file mode 100644
index 0000000000..143b7b203e
--- /dev/null
+++ b/engines/sci/detection_defines.h
@@ -0,0 +1,46 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef SCI_DETECTION_DEFINES_H
+#define SCI_DETECTION_DEFINES_H
+
+namespace Sci {
+
+// GUI-options, primarily used by detection_tables.h
+#define GAMEOPTION_PREFER_DIGITAL_SFX       GUIO_GAMEOPTIONS1
+#define GAMEOPTION_ORIGINAL_SAVELOAD        GUIO_GAMEOPTIONS2
+#define GAMEOPTION_MIDI_MODE                GUIO_GAMEOPTIONS3
+#define GAMEOPTION_JONES_CDAUDIO            GUIO_GAMEOPTIONS4
+#define GAMEOPTION_KQ6_WINDOWS_CURSORS      GUIO_GAMEOPTIONS5
+#define GAMEOPTION_SQ4_SILVER_CURSORS       GUIO_GAMEOPTIONS6
+#define GAMEOPTION_EGA_UNDITHER             GUIO_GAMEOPTIONS7
+// HIGH_RESOLUTION_GRAPHICS availability is checked for in SciEngine::run()
+#define GAMEOPTION_HIGH_RESOLUTION_GRAPHICS GUIO_GAMEOPTIONS8
+#define GAMEOPTION_ENABLE_BLACK_LINED_VIDEO GUIO_GAMEOPTIONS9
+#define GAMEOPTION_HQ_VIDEO                 GUIO_GAMEOPTIONS10
+#define GAMEOPTION_ENABLE_CENSORING         GUIO_GAMEOPTIONS11
+#define GAMEOPTION_LARRYSCALE               GUIO_GAMEOPTIONS12
+#define GAMEOPTION_UPSCALE_VIDEOS           GUIO_GAMEOPTIONS13
+
+} // End of namespace Sci
+
+#endif
diff --git a/engines/sci/detection_enums.h b/engines/sci/detection_enums.h
new file mode 100644
index 0000000000..6da06e5e0b
--- /dev/null
+++ b/engines/sci/detection_enums.h
@@ -0,0 +1,131 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef SCI_DETECTION_ENUMS_H
+#define SCI_DETECTION_ENUMS_H
+
+namespace Sci {
+
+enum SciGameId {
+	GID_ASTROCHICKEN,
+	GID_CAMELOT,
+	GID_CASTLEBRAIN,
+	GID_CHEST,
+	GID_CHRISTMAS1988,
+	GID_CHRISTMAS1990,
+	GID_CHRISTMAS1992,
+	GID_CNICK_KQ,
+	GID_CNICK_LAURABOW,
+	GID_CNICK_LONGBOW,
+	GID_CNICK_LSL,
+	GID_CNICK_SQ,
+	GID_ECOQUEST,
+	GID_ECOQUEST2,
+	GID_FAIRYTALES,
+	GID_FREDDYPHARKAS,
+	GID_FUNSEEKER,
+	GID_GK1DEMO,	// We have a separate ID for GK1 demo, because it's actually a completely different game (SCI1.1 vs SCI2/SCI2.1)
+	GID_GK1,
+	GID_GK2,
+	GID_HOYLE1,
+	GID_HOYLE2,
+	GID_HOYLE3,
+	GID_HOYLE4,
+	GID_HOYLE5,
+	GID_ICEMAN,
+	GID_INNDEMO,
+	GID_ISLANDBRAIN,
+	GID_JONES,
+	GID_KQ1,
+	GID_KQ4,
+	GID_KQ5,
+	GID_KQ6,
+	GID_KQ7,
+	GID_KQUESTIONS,
+	GID_LAURABOW,
+	GID_LAURABOW2,
+	GID_LIGHTHOUSE,
+	GID_LONGBOW,
+	GID_LSL1,
+	GID_LSL2,
+	GID_LSL3,
+	GID_LSL5,
+	GID_LSL6,
+	GID_LSL6HIRES, // We have a separate ID for LSL6 SCI32, because it's actually a completely different game
+	GID_LSL7,
+	GID_MOTHERGOOSE, // this one is the SCI0 version
+	GID_MOTHERGOOSE256, // this one handles SCI1 and SCI1.1 variants, at least those 2 share a bit in common
+	GID_MOTHERGOOSEHIRES, // this one is the SCI2.1 hires version, completely different from the other ones
+	GID_MSASTROCHICKEN,
+	GID_PEPPER,
+	GID_PHANTASMAGORIA,
+	GID_PHANTASMAGORIA2,
+	GID_PQ1,
+	GID_PQ2,
+	GID_PQ3,
+	GID_PQ4,
+	GID_PQ4DEMO,	// We have a separate ID for PQ4 demo, because it's actually a completely different game (SCI1.1 vs SCI2/SCI2.1)
+	GID_PQSWAT,
+	GID_QFG1,
+	GID_QFG1VGA,
+	GID_QFG2,
+	GID_QFG3,
+	GID_QFG4,
+	GID_QFG4DEMO,	// We have a separate ID for QFG4 demo, because it's actually a completely different game (SCI1.1 vs SCI2/SCI2.1)
+	GID_RAMA,
+	GID_SHIVERS,
+	//GID_SHIVERS2,	// Not SCI
+	GID_SLATER,
+	GID_SQ1,
+	GID_SQ3,
+	GID_SQ4,
+	GID_SQ5,
+	GID_SQ6,
+	GID_TORIN,
+	GID_FANMADE
+};
+
+/**
+ * SCI versions
+ * For more information, check here:
+ * https://wiki.scummvm.org/index.php/Sierra_Game_Versions#SCI_Games
+ */
+enum SciVersion {
+	SCI_VERSION_NONE,
+	SCI_VERSION_0_EARLY, // KQ4 early, LSL2 early, XMAS card 1988
+	SCI_VERSION_0_LATE, // KQ4, LSL2, LSL3, SQ3 etc
+	SCI_VERSION_01, // KQ1 and multilingual games (S.old.*)
+	SCI_VERSION_1_EGA_ONLY, // SCI 1 EGA with parser (i.e. QFG2 only)
+	SCI_VERSION_1_EARLY, // KQ5 floppy, SQ4 floppy, XMAS card 1990, Fairy tales, Jones floppy
+	SCI_VERSION_1_MIDDLE, // LSL1, Jones CD, LSL3 & SQ3 multilingual Amiga
+	SCI_VERSION_1_LATE, // Dr. Brain 1, EcoQuest 1, Longbow, PQ3, SQ1, LSL5, KQ5 CD
+	SCI_VERSION_1_1, // Dr. Brain 2, EcoQuest 1 CD, EcoQuest 2, KQ6, QFG3, SQ4CD, XMAS 1992 and many more
+	SCI_VERSION_2, // GK1, PQ4 floppy, QFG4 floppy
+	SCI_VERSION_2_1_EARLY, // GK2 demo, KQ7 1.4/1.51, LSL6 hires, PQ4CD, QFG4CD
+	SCI_VERSION_2_1_MIDDLE, // GK2, Hoyle 5, KQ7 2.00b, MUMG Deluxe, Phantasmagoria 1, PQ:SWAT, Shivers 1, SQ6, Torin
+	SCI_VERSION_2_1_LATE, // demos and Mac versions of LSL7, Lighthouse, RAMA
+	SCI_VERSION_3 // LSL7, Lighthouse, RAMA, Phantasmagoria 2
+};
+
+} // End of namespace Sci
+
+#endif
diff --git a/engines/sci/sci.h b/engines/sci/sci.h
index 135abbff8f..7ea28b38f7 100644
--- a/engines/sci/sci.h
+++ b/engines/sci/sci.h
@@ -29,6 +29,8 @@
 #include "common/random.h"
 #include "sci/engine/vm_types.h"	// for Selector
 #include "sci/debug.h"	// for DebugState
+#include "sci/detection_enums.h" // for shared enums between detection/engine
+#include "sci/detection_defines.h" // for shared defines between detection/engine
 
 struct ADGameDescription;
 
@@ -45,22 +47,6 @@ struct ADGameDescription;
  */
 namespace Sci {
 
-// GUI-options, primarily used by detection_tables.h
-#define GAMEOPTION_PREFER_DIGITAL_SFX       GUIO_GAMEOPTIONS1
-#define GAMEOPTION_ORIGINAL_SAVELOAD        GUIO_GAMEOPTIONS2
-#define GAMEOPTION_MIDI_MODE                GUIO_GAMEOPTIONS3
-#define GAMEOPTION_JONES_CDAUDIO            GUIO_GAMEOPTIONS4
-#define GAMEOPTION_KQ6_WINDOWS_CURSORS      GUIO_GAMEOPTIONS5
-#define GAMEOPTION_SQ4_SILVER_CURSORS       GUIO_GAMEOPTIONS6
-#define GAMEOPTION_EGA_UNDITHER             GUIO_GAMEOPTIONS7
-// HIGH_RESOLUTION_GRAPHICS availability is checked for in SciEngine::run()
-#define GAMEOPTION_HIGH_RESOLUTION_GRAPHICS GUIO_GAMEOPTIONS8
-#define GAMEOPTION_ENABLE_BLACK_LINED_VIDEO GUIO_GAMEOPTIONS9
-#define GAMEOPTION_HQ_VIDEO                 GUIO_GAMEOPTIONS10
-#define GAMEOPTION_ENABLE_CENSORING         GUIO_GAMEOPTIONS11
-#define GAMEOPTION_LARRYSCALE               GUIO_GAMEOPTIONS12
-#define GAMEOPTION_UPSCALE_VIDEOS           GUIO_GAMEOPTIONS13
-
 struct EngineState;
 class Vocabulary;
 class ResourceManager;
@@ -134,106 +120,6 @@ enum kDebugLevels {
 	kDebugLevelGame          = 1 << 25
 };
 
-enum SciGameId {
-	GID_ASTROCHICKEN,
-	GID_CAMELOT,
-	GID_CASTLEBRAIN,
-	GID_CHEST,
-	GID_CHRISTMAS1988,
-	GID_CHRISTMAS1990,
-	GID_CHRISTMAS1992,
-	GID_CNICK_KQ,
-	GID_CNICK_LAURABOW,
-	GID_CNICK_LONGBOW,
-	GID_CNICK_LSL,
-	GID_CNICK_SQ,
-	GID_ECOQUEST,
-	GID_ECOQUEST2,
-	GID_FAIRYTALES,
-	GID_FREDDYPHARKAS,
-	GID_FUNSEEKER,
-	GID_GK1DEMO,	// We have a separate ID for GK1 demo, because it's actually a completely different game (SCI1.1 vs SCI2/SCI2.1)
-	GID_GK1,
-	GID_GK2,
-	GID_HOYLE1,
-	GID_HOYLE2,
-	GID_HOYLE3,
-	GID_HOYLE4,
-	GID_HOYLE5,
-	GID_ICEMAN,
-	GID_INNDEMO,
-	GID_ISLANDBRAIN,
-	GID_JONES,
-	GID_KQ1,
-	GID_KQ4,
-	GID_KQ5,
-	GID_KQ6,
-	GID_KQ7,
-	GID_KQUESTIONS,
-	GID_LAURABOW,
-	GID_LAURABOW2,
-	GID_LIGHTHOUSE,
-	GID_LONGBOW,
-	GID_LSL1,
-	GID_LSL2,
-	GID_LSL3,
-	GID_LSL5,
-	GID_LSL6,
-	GID_LSL6HIRES, // We have a separate ID for LSL6 SCI32, because it's actually a completely different game
-	GID_LSL7,
-	GID_MOTHERGOOSE, // this one is the SCI0 version
-	GID_MOTHERGOOSE256, // this one handles SCI1 and SCI1.1 variants, at least those 2 share a bit in common
-	GID_MOTHERGOOSEHIRES, // this one is the SCI2.1 hires version, completely different from the other ones
-	GID_MSASTROCHICKEN,
-	GID_PEPPER,
-	GID_PHANTASMAGORIA,
-	GID_PHANTASMAGORIA2,
-	GID_PQ1,
-	GID_PQ2,
-	GID_PQ3,
-	GID_PQ4,
-	GID_PQ4DEMO,	// We have a separate ID for PQ4 demo, because it's actually a completely different game (SCI1.1 vs SCI2/SCI2.1)
-	GID_PQSWAT,
-	GID_QFG1,
-	GID_QFG1VGA,
-	GID_QFG2,
-	GID_QFG3,
-	GID_QFG4,
-	GID_QFG4DEMO,	// We have a separate ID for QFG4 demo, because it's actually a completely different game (SCI1.1 vs SCI2/SCI2.1)
-	GID_RAMA,
-	GID_SHIVERS,
-	//GID_SHIVERS2,	// Not SCI
-	GID_SLATER,
-	GID_SQ1,
-	GID_SQ3,
-	GID_SQ4,
-	GID_SQ5,
-	GID_SQ6,
-	GID_TORIN,
-	GID_FANMADE
-};
-
-/**
- * SCI versions
- * For more information, check here:
- * https://wiki.scummvm.org/index.php/Sierra_Game_Versions#SCI_Games
- */
-enum SciVersion {
-	SCI_VERSION_NONE,
-	SCI_VERSION_0_EARLY, // KQ4 early, LSL2 early, XMAS card 1988
-	SCI_VERSION_0_LATE, // KQ4, LSL2, LSL3, SQ3 etc
-	SCI_VERSION_01, // KQ1 and multilingual games (S.old.*)
-	SCI_VERSION_1_EGA_ONLY, // SCI 1 EGA with parser (i.e. QFG2 only)
-	SCI_VERSION_1_EARLY, // KQ5 floppy, SQ4 floppy, XMAS card 1990, Fairy tales, Jones floppy
-	SCI_VERSION_1_MIDDLE, // LSL1, Jones CD, LSL3 & SQ3 multilingual Amiga
-	SCI_VERSION_1_LATE, // Dr. Brain 1, EcoQuest 1, Longbow, PQ3, SQ1, LSL5, KQ5 CD
-	SCI_VERSION_1_1, // Dr. Brain 2, EcoQuest 1 CD, EcoQuest 2, KQ6, QFG3, SQ4CD, XMAS 1992 and many more
-	SCI_VERSION_2, // GK1, PQ4 floppy, QFG4 floppy
-	SCI_VERSION_2_1_EARLY, // GK2 demo, KQ7 1.4/1.51, LSL6 hires, PQ4CD, QFG4CD
-	SCI_VERSION_2_1_MIDDLE, // GK2, Hoyle 5, KQ7 2.00b, MUMG Deluxe, Phantasmagoria 1, PQ:SWAT, Shivers 1, SQ6, Torin
-	SCI_VERSION_2_1_LATE, // demos and Mac versions of LSL7, Lighthouse, RAMA
-	SCI_VERSION_3 // LSL7, Lighthouse, RAMA, Phantasmagoria 2
-};
 
 /** Supported languages */
 enum kLanguage {


Commit: 255af8a0eb89c835cd9228c7e579128136e96568
    https://github.com/scummvm/scummvm/commit/255af8a0eb89c835cd9228c7e579128136e96568
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCI: Split detection features & adapt to new plugins.

Changed paths:
  A engines/sci/metaengine.cpp
    configure
    engines/sci/detection.cpp
    engines/sci/detection_tables.h
    engines/sci/module.mk


diff --git a/configure b/configure
index b26ca3a614..d7caff69b0 100755
--- a/configure
+++ b/configure
@@ -6170,7 +6170,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
 								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR"
-								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE")
+								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE" "SCI")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/sci/detection.cpp b/engines/sci/detection.cpp
index cbce01a8f5..667c2d3176 100644
--- a/engines/sci/detection.cpp
+++ b/engines/sci/detection.cpp
@@ -22,25 +22,18 @@
 
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
-#include "common/config-manager.h"
 #include "common/file.h"
 #include "common/hashmap.h"
 #include "common/ptr.h"
-#include "common/savefile.h"
-#include "common/system.h"
 #include "common/translation.h"
-#include "graphics/thumbnail.h"
-#include "graphics/surface.h"
+
 #include "gui/ThemeEval.h"
 #include "gui/widget.h"
 #include "gui/widgets/popup.h"
 
-#include "sci/sci.h"
-#include "sci/engine/kernel.h"
-#include "sci/engine/savegame.h"
-#include "sci/engine/script.h"
-#include "sci/engine/seg_manager.h"
-#include "sci/engine/state.h"
+#include "sci/detection_enums.h"
+#include "sci/detection_defines.h"
+#include "sci/graphics/helpers_detection_enums.h"
 
 namespace Sci {
 
@@ -138,260 +131,12 @@ static const PlainGameDescriptor s_sciGameTitles[] = {
 	{0, 0}
 };
 
-struct GameIdStrToEnum {
-	const char *gameidStr;
-	SciGameId gameidEnum;
-};
-
-static const GameIdStrToEnum s_gameIdStrToEnum[] = {
-	{ "astrochicken",    GID_ASTROCHICKEN },
-	{ "camelot",         GID_CAMELOT },
-	{ "castlebrain",     GID_CASTLEBRAIN },
-	{ "chest",           GID_CHEST },
-	{ "christmas1988",   GID_CHRISTMAS1988 },
-	{ "christmas1990",   GID_CHRISTMAS1990 },
-	{ "christmas1992",   GID_CHRISTMAS1992 },
-	{ "cnick-kq",        GID_CNICK_KQ },
-	{ "cnick-laurabow",  GID_CNICK_LAURABOW },
-	{ "cnick-longbow",   GID_CNICK_LONGBOW },
-	{ "cnick-lsl",       GID_CNICK_LSL },
-	{ "cnick-sq",        GID_CNICK_SQ },
-	{ "ecoquest",        GID_ECOQUEST },
-	{ "ecoquest2",       GID_ECOQUEST2 },
-	{ "fairytales",      GID_FAIRYTALES },
-	{ "freddypharkas",   GID_FREDDYPHARKAS },
-	{ "funseeker",       GID_FUNSEEKER },
-	{ "gk1demo",         GID_GK1DEMO },
-	{ "gk1",             GID_GK1 },
-	{ "gk2",             GID_GK2 },
-	{ "hoyle1",          GID_HOYLE1 },
-	{ "hoyle2",          GID_HOYLE2 },
-	{ "hoyle3",          GID_HOYLE3 },
-	{ "hoyle4",          GID_HOYLE4 },
-	{ "hoyle5",          GID_HOYLE5 },
-	{ "hoyle5bridge",    GID_HOYLE5 },
-	{ "hoyle5children",  GID_HOYLE5 },
-	{ "hoyle5solitaire", GID_HOYLE5 },
-	{ "iceman",          GID_ICEMAN },
-	{ "inndemo",         GID_INNDEMO },
-	{ "islandbrain",     GID_ISLANDBRAIN },
-	{ "jones",           GID_JONES },
-	{ "kq1sci",          GID_KQ1 },
-	{ "kq4sci",          GID_KQ4 },
-	{ "kq5",             GID_KQ5 },
-	{ "kq6",             GID_KQ6 },
-	{ "kq7",             GID_KQ7 },
-	{ "kquestions",      GID_KQUESTIONS },
-	{ "laurabow",        GID_LAURABOW },
-	{ "laurabow2",       GID_LAURABOW2 },
-	{ "lighthouse",      GID_LIGHTHOUSE },
-	{ "longbow",         GID_LONGBOW },
-	{ "lsl1sci",         GID_LSL1 },
-	{ "lsl2",            GID_LSL2 },
-	{ "lsl3",            GID_LSL3 },
-	{ "lsl5",            GID_LSL5 },
-	{ "lsl6",            GID_LSL6 },
-	{ "lsl6hires",       GID_LSL6HIRES },
-	{ "lsl7",            GID_LSL7 },
-	{ "mothergoose",     GID_MOTHERGOOSE },
-	{ "mothergoose256",  GID_MOTHERGOOSE256 },
-	{ "mothergoosehires",GID_MOTHERGOOSEHIRES },
-	{ "msastrochicken",  GID_MSASTROCHICKEN },
-	{ "pepper",          GID_PEPPER },
-	{ "phantasmagoria",  GID_PHANTASMAGORIA },
-	{ "phantasmagoria2", GID_PHANTASMAGORIA2 },
-	{ "pq1sci",          GID_PQ1 },
-	{ "pq2",             GID_PQ2 },
-	{ "pq3",             GID_PQ3 },
-	{ "pq4",             GID_PQ4 },
-	{ "pq4demo",         GID_PQ4DEMO },
-	{ "pqswat",          GID_PQSWAT },
-	{ "qfg1",            GID_QFG1 },
-	{ "qfg1vga",         GID_QFG1VGA },
-	{ "qfg2",            GID_QFG2 },
-	{ "qfg3",            GID_QFG3 },
-	{ "qfg4",            GID_QFG4 },
-	{ "qfg4demo",        GID_QFG4DEMO },
-	{ "rama",            GID_RAMA },
-	{ "sci-fanmade",     GID_FANMADE },
-	{ "shivers",         GID_SHIVERS },
-	//{ "shivers2",        GID_SHIVERS2 },	// Not SCI
-	{ "slater",          GID_SLATER },
-	{ "sq1sci",          GID_SQ1 },
-	{ "sq3",             GID_SQ3 },
-	{ "sq4",             GID_SQ4 },
-	{ "sq5",             GID_SQ5 },
-	{ "sq6",             GID_SQ6 },
-	{ "torin",           GID_TORIN },
-	{ NULL, (SciGameId)-1 }
-};
-
-struct OldNewIdTableEntry {
-	const char *oldId;
-	const char *newId;
-	SciVersion version;
-};
-
-static const OldNewIdTableEntry s_oldNewTable[] = {
-	{ "archive",    "chest",            SCI_VERSION_NONE       },
-	{ "arthur",		"camelot",			SCI_VERSION_NONE       },
-	{ "brain",      "castlebrain",      SCI_VERSION_1_MIDDLE   },	// Amiga
-	{ "brain",      "castlebrain",      SCI_VERSION_1_LATE     },
-	{ "demo",		"christmas1988",	SCI_VERSION_NONE       },
-	{ "card",       "christmas1990",    SCI_VERSION_1_EARLY,   },
-	{ "card",       "christmas1992",    SCI_VERSION_1_1        },
-	{ "RH Budget",	"cnick-longbow",	SCI_VERSION_NONE       },
-	// iceman is the same
-	{ "icedemo",	"iceman",			SCI_VERSION_NONE       },
-	// longbow is the same
-	{ "eco",		"ecoquest",			SCI_VERSION_NONE       },
-	{ "eco2",		"ecoquest2",		SCI_VERSION_NONE       },	// EcoQuest 2 demo
-	{ "rain",		"ecoquest2",		SCI_VERSION_NONE       },	// EcoQuest 2 full
-	{ "tales",		"fairytales",		SCI_VERSION_NONE       },
-	{ "fp",			"freddypharkas",	SCI_VERSION_NONE       },
-	{ "emc",		"funseeker",		SCI_VERSION_NONE       },
-	{ "gk",			"gk1",				SCI_VERSION_NONE       },
-	// gk2 is the same
-	{ "gk2demo",	"gk2",				SCI_VERSION_NONE       },
-	{ "hoyledemo",	"hoyle1",			SCI_VERSION_NONE       },
-	{ "cardgames",	"hoyle1",			SCI_VERSION_NONE       },
-	{ "solitare",	"hoyle2",			SCI_VERSION_NONE       },
-	{ "hoyle3",	    "hoyle3",			SCI_VERSION_NONE       },
-	{ "hoyle4",	    "hoyle4",			SCI_VERSION_1_1        },
-	{ "hoyle4",	    "hoyle5",			SCI_VERSION_2_1_MIDDLE },
-	{ "brain",      "islandbrain",      SCI_VERSION_1_1        },
-	{ "demo000",	"kq1sci",			SCI_VERSION_NONE       },
-	{ "kq1",		"kq1sci",			SCI_VERSION_NONE       },
-	{ "kq4",		"kq4sci",			SCI_VERSION_NONE       },
-	// kq5 is the same
-	// kq6 is the same
-	{ "kq7cd",		"kq7",				SCI_VERSION_NONE       },
-	{ "quizgame-demo", "kquestions",    SCI_VERSION_NONE       },
-	{ "mm1",		"laurabow",			SCI_VERSION_NONE       },
-	{ "cb1",		"laurabow",			SCI_VERSION_NONE       },
-	{ "lb2",		"laurabow2",		SCI_VERSION_NONE       },
-	{ "rh",			"longbow",			SCI_VERSION_NONE       },
-	{ "ll1",		"lsl1sci",			SCI_VERSION_NONE       },
-	{ "lsl1",		"lsl1sci",			SCI_VERSION_NONE       },
-	// lsl2 is the same
-	{ "lsl3",		"lsl3",				SCI_VERSION_NONE       },
-	{ "ll5",		"lsl5",				SCI_VERSION_NONE       },
-	// lsl5 is the same
-	// lsl6 is the same
-	{ "mg",			"mothergoose",		SCI_VERSION_NONE       },
-	{ "twisty",		"pepper",			SCI_VERSION_NONE       },
-	{ "scary",      "phantasmagoria",   SCI_VERSION_NONE       },
-	// TODO: distinguish the full version of Phantasmagoria from the demo
-	{ "pq1",		"pq1sci",			SCI_VERSION_NONE       },
-	{ "pq",			"pq2",				SCI_VERSION_NONE       },
-	// pq3 is the same
-	// pq4 is the same
-	{ "hq",			"qfg1",				SCI_VERSION_NONE       },	// QFG1 SCI0/EGA
-	{ "glory",      "qfg1",             SCI_VERSION_0_LATE     },	// QFG1 SCI0/EGA
-	{ "trial",		"qfg2",				SCI_VERSION_NONE       },
-	{ "hq2demo",	"qfg2",				SCI_VERSION_NONE       },
-	// rama is the same
-	// TODO: distinguish the full version of rama from the demo
-	{ "thegame",	"slater",			SCI_VERSION_NONE       },
-	{ "sq1demo",	"sq1sci",			SCI_VERSION_NONE       },
-	{ "sq1",		"sq1sci",			SCI_VERSION_NONE       },
-	// sq3 is the same
-	// sq4 is the same
-	// sq5 is the same
-	// sq6 is the same
-	// TODO: distinguish the full version of SQ6 from the demo
-	// torin is the same
-	{ "l7",			"lsl7",				SCI_VERSION_NONE       },
-	{ "p2",			"phantasmagoria2",	SCI_VERSION_NONE       },
-	{ "lite",		"lighthouse",		SCI_VERSION_NONE       },
-
-	{ "", "", SCI_VERSION_NONE }
-};
-
-/**
- * Converts the builtin Sierra game IDs to the ones we use in ScummVM
- * @param[in] gameId		The internal game ID
- * @param[in] gameFlags     The game's flags, which are adjusted accordingly for demos
- * @return					The equivalent ScummVM game id
- */
-Common::String convertSierraGameId(Common::String sierraId, uint32 *gameFlags, ResourceManager &resMan) {
-	// Convert the id to lower case, so that we match all upper/lower case variants.
-	sierraId.toLowercase();
-
-	// If the game has less than the expected scripts, it's a demo
-	uint32 demoThreshold = 100;
-	// ...but there are some exceptions
-	if (sierraId == "brain" || sierraId == "lsl1" ||
-		sierraId == "mg" || sierraId == "pq" ||
-		sierraId == "jones" ||
-		sierraId == "cardgames" || sierraId == "solitare" ||
-		sierraId == "catdate" ||
-		sierraId == "hoyle4")
-		demoThreshold = 40;
-	if (sierraId == "hoyle3")
-		demoThreshold = 45;	// cnick-kq has 42 scripts. The actual hoyle 3 demo has 27.
-	if (sierraId == "fp" || sierraId == "gk" || sierraId == "pq4")
-		demoThreshold = 150;
-
-	Common::List<ResourceId> resources = resMan.listResources(kResourceTypeScript, -1);
-	if (resources.size() < demoThreshold) {
-		*gameFlags |= ADGF_DEMO;
-
-		// Crazy Nick's Picks
-		if (sierraId == "lsl1" && resources.size() == 34)
-			return "cnick-lsl";
-		if (sierraId == "sq4" && resources.size() == 34)
-			return "cnick-sq";
-		if (sierraId == "hoyle3" && resources.size() == 42)
-			return "cnick-kq";
-		if (sierraId == "rh budget" && resources.size() == 39)
-			return "cnick-longbow";
-		// TODO: cnick-laurabow (the name of the game object contains junk)
-
-		// Handle Astrochicken 1 (SQ3) and 2 (SQ4)
-		if (sierraId == "sq3" && resources.size() == 20)
-			return "astrochicken";
-		if (sierraId == "sq4")
-			return "msastrochicken";
-	}
-
-	if (sierraId == "torin" && resources.size() == 226)	// Torin's Passage demo
-		*gameFlags |= ADGF_DEMO;
-
-	for (const OldNewIdTableEntry *cur = s_oldNewTable; cur->oldId[0]; ++cur) {
-		if (sierraId == cur->oldId) {
-			// Distinguish same IDs via the SCI version
-			if (cur->version != SCI_VERSION_NONE && cur->version != getSciVersion())
-				continue;
-
-			return cur->newId;
-		}
-	}
-
-	if (sierraId == "glory") {
-		// This could either be qfg1 VGA, qfg3 or qfg4 demo (all SCI1.1),
-		// or qfg4 full (SCI2)
-		// qfg1 VGA doesn't have view 1
-		if (!resMan.testResource(ResourceId(kResourceTypeView, 1)))
-			return "qfg1vga";
-
-		// qfg4 full is SCI2
-		if (getSciVersion() == SCI_VERSION_2)
-			return "qfg4";
-
-		// qfg4 demo has less than 50 scripts
-		if (resources.size() < 50)
-			return "qfg4demo";
-
-		// Otherwise it's qfg3
-		return "qfg3";
-	}
-
-	return sierraId;
-}
+} // End of namespace Sci
 
 #include "sci/detection_tables.h"
 
+namespace Sci {
+
 static const ADExtraGuiOptionsMap optionsList[] = {
 	{
 		GAMEOPTION_EGA_UNDITHER,
@@ -565,22 +310,6 @@ static const PopUpOptionsMap popUpOptionsList[] = {
 	POPUP_OPTIONS_TERMINATOR
 };
 
-/**
- * The fallback game descriptor used by the SCI engine's fallbackDetector.
- * Contents of this struct are overwritten by the fallbackDetector.
- */
-static ADGameDescription s_fallbackDesc = {
-	"",
-	"",
-	AD_ENTRY1(0, 0), // This should always be AD_ENTRY1(0, 0) in the fallback descriptor
-	Common::UNK_LANG,
-	Common::kPlatformDOS,
-	ADGF_NO_FLAGS,
-	GUIO3(GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE)
-};
-
-static char s_fallbackGameIdBuf[256];
-
 static const char *directoryGlobs[] = {
 	"avi",
 	"english",
@@ -701,13 +430,7 @@ public:
 		return "Sierra's Creative Interpreter (C) Sierra Online";
 	}
 
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
-	bool hasFeature(MetaEngineFeature f) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 	void registerDefaultSettings(const Common::String &target) const override;
 	GUI::OptionsContainerWidget *buildEngineOptionsWidget(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const override;
 };
@@ -723,385 +446,29 @@ GUI::OptionsContainerWidget *SciMetaEngine::buildEngineOptionsWidget(GUI::GuiObj
 	return new OptionsWidget(boss, name, target);
 }
 
-Common::Language charToScummVMLanguage(const char c) {
-	switch (c) {
-	case 'F':
-		return Common::FR_FRA;
-	case 'S':
-		return Common::ES_ESP;
-	case 'I':
-		return Common::IT_ITA;
-	case 'G':
-		return Common::DE_DEU;
-	case 'J':
-	case 'j':
-		return Common::JA_JPN;
-	case 'P':
-		return Common::PT_BRA;
-	default:
-		return Common::UNK_LANG;
-	}
-}
-
 ADDetectedGame SciMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
-	bool foundResMap = false;
-	bool foundRes000 = false;
-
-	// Set some defaults
-	s_fallbackDesc.extra = "";
-	s_fallbackDesc.language = Common::EN_ANY;
-	s_fallbackDesc.flags = ADGF_NO_FLAGS;
-	s_fallbackDesc.platform = Common::kPlatformDOS;	// default to PC platform
-	s_fallbackDesc.gameId = "sci";
-	s_fallbackDesc.guiOptions = GUIO3(GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE);
-
-	if (allFiles.contains("resource.map") || allFiles.contains("Data1")
-	    || allFiles.contains("resmap.000") || allFiles.contains("resmap.001")) {
-		foundResMap = true;
-	}
-
-	// Determine if we got a CD version and set the CD flag accordingly, by checking for
-	// resource.aud for SCI1.1 CD games, or audio001.002 for SCI1 CD games. We assume that
-	// the file should be over 10MB, as it contains all the game speech and is usually
-	// around 450MB+. The size check is for some floppy game versions like KQ6 floppy, which
-	// also have a small resource.aud file
-	if (allFiles.contains("resource.aud") || allFiles.contains("resaud.001") || allFiles.contains("audio001.002")) {
-		Common::FSNode file = allFiles.contains("resource.aud") ? allFiles["resource.aud"] : (allFiles.contains("resaud.001") ? allFiles["resaud.001"] : allFiles["audio001.002"]);
-		Common::SeekableReadStream *tmpStream = file.createReadStream();
-		if (tmpStream->size() > 10 * 1024 * 1024) {
-			// We got a CD version, so set the CD flag accordingly
-			s_fallbackDesc.flags |= ADGF_CD;
-		}
-		delete tmpStream;
-	}
-
-	if (allFiles.contains("resource.000") || allFiles.contains("resource.001")
-		|| allFiles.contains("ressci.000") || allFiles.contains("ressci.001"))
-		foundRes000 = true;
-
-	// Data1 contains both map and volume for SCI1.1+ Mac games
-	if (allFiles.contains("Data1")) {
-		foundResMap = foundRes000 = true;
-		 s_fallbackDesc.platform = Common::kPlatformMacintosh;
-	}
-
-	// Determine the game platform
-	// The existence of any of these files indicates an Amiga game
-	if (allFiles.contains("9.pat") || allFiles.contains("spal") ||
-		allFiles.contains("patch.005") || allFiles.contains("bank.001"))
-			s_fallbackDesc.platform = Common::kPlatformAmiga;
-
-	// The existence of 7.pat or patch.200 indicates a Mac game
-	if (allFiles.contains("7.pat") || allFiles.contains("patch.200"))
-		s_fallbackDesc.platform = Common::kPlatformMacintosh;
-
-	// The data files for Atari ST versions are the same as their DOS counterparts
-
-
-	// If these files aren't found, it can't be SCI
-	if (!foundResMap && !foundRes000)
-		return ADDetectedGame();
-
-	ResourceManager resMan(true);
-	resMan.addAppropriateSourcesForDetection(fslist);
-	resMan.init();
-	// TODO: Add error handling.
-
-#ifndef ENABLE_SCI32
-	// Is SCI32 compiled in? If not, and this is a SCI32 game,
-	// stop here
-	if (getSciVersionForDetection() >= SCI_VERSION_2)
-		return ADDetectedGame();
-#endif
-
-	ViewType gameViews = resMan.getViewType();
-
-	// Have we identified the game views? If not, stop here
-	// Can't be SCI (or unsupported SCI views). Pinball Creep by Sierra also uses resource.map/resource.000 files
-	// but doesn't share SCI format at all
-	if (gameViews == kViewUnknown)
-		return ADDetectedGame();
-
-	// Set the platform to Amiga if the game is using Amiga views
-	if (gameViews == kViewAmiga)
-		s_fallbackDesc.platform = Common::kPlatformAmiga;
-
-	// Determine the game id
-	Common::String sierraGameId = resMan.findSierraGameId(s_fallbackDesc.platform == Common::kPlatformMacintosh);
-
-	// If we don't have a game id, the game is not SCI
-	if (sierraGameId.empty())
-		return ADDetectedGame();
-
-	Common::String gameId = convertSierraGameId(sierraGameId, &s_fallbackDesc.flags, resMan);
-	Common::strlcpy(s_fallbackGameIdBuf, gameId.c_str(), sizeof(s_fallbackGameIdBuf));
-	s_fallbackDesc.gameId = s_fallbackGameIdBuf;
-
-	// Try to determine the game language
-	// Load up text 0 and start looking for "#" characters
-	// Non-English versions contain strings like XXXX#YZZZZ
-	// Where XXXX is the English string, #Y a separator indicating the language
-	// (e.g. #G for German) and ZZZZ is the translated text
-	// NOTE: This doesn't work for games which use message instead of text resources
-	// (like, for example, Eco Quest 1 and all SCI1.1 games and newer, e.g. Freddy Pharkas).
-	// As far as we know, these games store the messages of each language in separate
-	// resources, and it's not possible to detect that easily
-	// Also look for "%J" which is used in japanese games
-	Resource *text = resMan.findResource(ResourceId(kResourceTypeText, 0), false);
-	uint seeker = 0;
-	if (text) {
-		while (seeker < text->size()) {
-			if (text->getUint8At(seeker) == '#')  {
-				if (seeker + 1 < text->size())
-					s_fallbackDesc.language = charToScummVMLanguage(text->getUint8At(seeker + 1));
-				break;
-			}
-			if (text->getUint8At(seeker) == '%') {
-				if ((seeker + 1 < text->size()) && (text->getUint8At(seeker + 1) == 'J')) {
-					s_fallbackDesc.language = charToScummVMLanguage(text->getUint8At(seeker + 1));
-					break;
-				}
-			}
-			seeker++;
-		}
-	}
-
-
-	// Fill in "extra" field
-
-	// Is this an EGA version that might have a VGA pendant? Then we want
-	// to mark it as such in the "extra" field.
-	const bool markAsEGA = (gameViews == kViewEga && s_fallbackDesc.platform != Common::kPlatformAmiga
-			&& getSciVersion() > SCI_VERSION_1_EGA_ONLY);
-
-	const bool isDemo = (s_fallbackDesc.flags & ADGF_DEMO);
-	const bool isCD = (s_fallbackDesc.flags & ADGF_CD);
-
-	if (!isCD)
-		s_fallbackDesc.guiOptions = GUIO4(GUIO_NOSPEECH, GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE);
-
-	if (gameId.hasSuffix("sci")) {
-		s_fallbackDesc.extra = "SCI";
-
-		// Differentiate EGA versions from the VGA ones, where needed
-		if (markAsEGA)
-			s_fallbackDesc.extra = "SCI/EGA";
-
-		// Mark as demo.
-		// Note: This overwrites the 'EGA' info, if it was previously set.
-		if (isDemo)
-			s_fallbackDesc.extra = "SCI/Demo";
-	} else {
-		if (markAsEGA)
-			s_fallbackDesc.extra = "EGA";
-
-		// Set "CD" and "Demo" as appropriate.
-		// Note: This overwrites the 'EGA' info, if it was previously set.
-		if (isDemo && isCD)
-			s_fallbackDesc.extra = "CD Demo";
-		else if (isDemo)
-			s_fallbackDesc.extra = "Demo";
-		else if (isCD)
-			s_fallbackDesc.extra = "CD";
-	}
-
-	return ADDetectedGame(&s_fallbackDesc);
-}
-
-bool SciMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const GameIdStrToEnum *g = s_gameIdStrToEnum;
-	for (; g->gameidStr; ++g) {
-		if (0 == strcmp(desc->gameId, g->gameidStr)) {
-			*engine = new SciEngine(syst, desc, g->gameidEnum);
-			return true;
-		}
-	}
-
-	return false;
-}
-
-bool SciMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves) ||
-		(f == kSupportsLoadingDuringStartup) ||
-		(f == kSupportsDeleteSave) ||
-		(f == kSavesSupportMetaInfo) ||
-		(f == kSavesSupportThumbnail) ||
-		(f == kSavesSupportCreationDate) ||
-		(f == kSavesSupportPlayTime);
-}
-
-bool SciEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher) ||
-		(f == kSupportsLoadingDuringRuntime); // ||
-		//(f == kSupportsSavingDuringRuntime);
-		// We can't allow saving through ScummVM menu, because
-		//  a) lots of games don't like saving everywhere (e.g. castle of dr. brain)
-		//  b) some games even dont allow saving in certain rooms (e.g. lsl6)
-		//  c) somehow some games even get mad when doing this (execstackbase was 1 all of a sudden in lsl3)
-		//  d) for sci0/sci01 games we should at least wait till status bar got drawn, although this may not be enough
-		// we can't make sure that the scripts are fine with us saving at a specific location, doing so may work sometimes
-		//  and some other times it won't work.
-}
-
-SaveStateList SciMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String pattern = target;
-	pattern += ".###";
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	bool hasAutosave = false;
-	int slotNr = 0;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		// Obtain the last 3 digits of the filename, since they correspond to the save slot
-		slotNr = atoi(file->c_str() + file->size() - 3);
-
-		if (slotNr >= 0 && slotNr <= 99) {
-			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
-			if (in) {
-				SavegameMetadata meta;
-				if (!get_savegame_metadata(in, meta)) {
-					// invalid
-					delete in;
-					continue;
-				}
-				SaveStateDescriptor descriptor(slotNr, meta.name);
-
-				if (slotNr == 0) {
-					// ScummVM auto-save slot
-					descriptor.setWriteProtectedFlag(true);
-					hasAutosave = true;
-				} else {
-					descriptor.setWriteProtectedFlag(false);
-				}
-
-				saveList.push_back(descriptor);
-				delete in;
-			}
-		}
-	}
-
-	if (!hasAutosave) {
-		SaveStateDescriptor descriptor(0, _("(Autosave)"));
-		descriptor.setLocked(true);
-		saveList.push_back(descriptor);
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-SaveStateDescriptor SciMetaEngine::querySaveMetaInfos(const char *target, int slotNr) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slotNr);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
-	SaveStateDescriptor descriptor(slotNr, "");
-
-	if (slotNr == 0) {
-		// ScummVM auto-save slot
-		descriptor.setWriteProtectedFlag(true);
-		descriptor.setDeletableFlag(false);
-	} else {
-		descriptor.setWriteProtectedFlag(false);
-		descriptor.setDeletableFlag(true);
-	}
-
-	if (in) {
-		SavegameMetadata meta;
-
-		if (!get_savegame_metadata(in, meta)) {
-			// invalid
-			delete in;
-
-			descriptor.setDescription("*Invalid*");
-			return descriptor;
-		}
-
-		descriptor.setDescription(meta.name);
-
-		Graphics::Surface *thumbnail;
-		if (!Graphics::loadThumbnail(*in, thumbnail)) {
-			// invalid
-			delete in;
-
-			descriptor.setDescription("*Invalid*");
-			return descriptor;
-		}
-		descriptor.setThumbnail(thumbnail);
-
-		int day = (meta.saveDate >> 24) & 0xFF;
-		int month = (meta.saveDate >> 16) & 0xFF;
-		int year = meta.saveDate & 0xFFFF;
-
-		descriptor.setSaveDate(year, month, day);
-
-		int hour = (meta.saveTime >> 16) & 0xFF;
-		int minutes = (meta.saveTime >> 8) & 0xFF;
-
-		descriptor.setSaveTime(hour, minutes);
-
-		if (meta.version >= 34) {
-			descriptor.setPlayTime(meta.playTime * 1000 / 60);
+	/**
+	 * Fallback detection for Sci heavily depends on engine resources, so it's not possible
+	 * to use them without the engine present in a clean way.
+	 */
+	static const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
+
+	if (metaEnginePlugin) {
+		static const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+		if (enginePlugin) {
+			return enginePlugin->get<AdvancedMetaEngineConnect>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
 		} else {
-			descriptor.setPlayTime(meta.playTime * 1000);
-		}
-
-		delete in;
-
-		return descriptor;
-	}
-	// Return empty descriptor
-	return descriptor;
-}
-
-int SciMetaEngine::getMaximumSaveSlot() const { return 99; }
-
-void SciMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String fileName = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(fileName);
-}
-
-Common::Error SciEngine::loadGameState(int slot) {
-	_gamestate->_delayedRestoreGameId = slot;
-	return Common::kNoError;
-}
-
-Common::Error SciEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
-	const char *version = "";
-	if (gamestate_save(_gamestate, slot, desc, version)) {
-		return Common::kNoError;
-	}
-	return Common::kWritingFailed;
-}
-
-bool SciEngine::canLoadGameStateCurrently() {
-#ifdef ENABLE_SCI32
-	const Common::String &guiOptions = ConfMan.get("guioptions");
-	if (getSciVersion() >= SCI_VERSION_2) {
-		if (ConfMan.getBool("originalsaveload") ||
-			Common::checkGameGUIOption(GUIO_NOLAUNCHLOAD, guiOptions)) {
-
-			return false;
+			static bool warn = true;
+			if (warn) {
+				warning("Engine plugin for Sci not found. Some games will fail to be detected until an engine plugin is present.");
+				warn = false;
+			}
 		}
 	}
-#endif
 
-	return !_gamestate->executionStackBase;
-}
-
-bool SciEngine::canSaveGameStateCurrently() {
-	// see comment about kSupportsSavingDuringRuntime in SciEngine::hasFeature
-	return false;
+	return ADDetectedGame();
 }
 
 } // End of namespace Sci
 
-#if PLUGIN_ENABLED_DYNAMIC(SCI)
-	REGISTER_PLUGIN_DYNAMIC(SCI, PLUGIN_TYPE_ENGINE, Sci::SciMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(SCI, PLUGIN_TYPE_ENGINE, Sci::SciMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(SCI_DETECTION, PLUGIN_TYPE_METAENGINE, Sci::SciMetaEngine);
diff --git a/engines/sci/detection_tables.h b/engines/sci/detection_tables.h
index cda28eaea5..13a07ec741 100644
--- a/engines/sci/detection_tables.h
+++ b/engines/sci/detection_tables.h
@@ -22,8 +22,6 @@
 
 namespace Sci {
 
-#include "sci/sci.h"
-
 #define GUIO_STD16 GUIO4(GUIO_NOSPEECH, GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE)
 #define GUIO_STD16_UNDITHER GUIO5(GUIO_NOSPEECH, GAMEOPTION_EGA_UNDITHER, GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE)
 #define GUIO_STD16_SPEECH GUIO3(GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE)
diff --git a/engines/sci/metaengine.cpp b/engines/sci/metaengine.cpp
new file mode 100644
index 0000000000..2596211318
--- /dev/null
+++ b/engines/sci/metaengine.cpp
@@ -0,0 +1,722 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "engines/advancedDetector.h"
+#include "base/plugins.h"
+#include "common/config-manager.h"
+#include "common/file.h"
+#include "common/ptr.h"
+#include "common/savefile.h"
+#include "common/system.h"
+#include "common/translation.h"
+#include "graphics/thumbnail.h"
+#include "graphics/surface.h"
+
+#include "sci/sci.h"
+#include "sci/engine/kernel.h"
+#include "sci/engine/savegame.h"
+#include "sci/engine/script.h"
+#include "sci/engine/seg_manager.h"
+#include "sci/engine/state.h"
+
+namespace Sci {
+
+struct GameIdStrToEnum {
+	const char *gameidStr;
+	SciGameId gameidEnum;
+};
+
+static const GameIdStrToEnum s_gameIdStrToEnum[] = {
+	{ "astrochicken",    GID_ASTROCHICKEN },
+	{ "camelot",         GID_CAMELOT },
+	{ "castlebrain",     GID_CASTLEBRAIN },
+	{ "chest",           GID_CHEST },
+	{ "christmas1988",   GID_CHRISTMAS1988 },
+	{ "christmas1990",   GID_CHRISTMAS1990 },
+	{ "christmas1992",   GID_CHRISTMAS1992 },
+	{ "cnick-kq",        GID_CNICK_KQ },
+	{ "cnick-laurabow",  GID_CNICK_LAURABOW },
+	{ "cnick-longbow",   GID_CNICK_LONGBOW },
+	{ "cnick-lsl",       GID_CNICK_LSL },
+	{ "cnick-sq",        GID_CNICK_SQ },
+	{ "ecoquest",        GID_ECOQUEST },
+	{ "ecoquest2",       GID_ECOQUEST2 },
+	{ "fairytales",      GID_FAIRYTALES },
+	{ "freddypharkas",   GID_FREDDYPHARKAS },
+	{ "funseeker",       GID_FUNSEEKER },
+	{ "gk1demo",         GID_GK1DEMO },
+	{ "gk1",             GID_GK1 },
+	{ "gk2",             GID_GK2 },
+	{ "hoyle1",          GID_HOYLE1 },
+	{ "hoyle2",          GID_HOYLE2 },
+	{ "hoyle3",          GID_HOYLE3 },
+	{ "hoyle4",          GID_HOYLE4 },
+	{ "hoyle5",          GID_HOYLE5 },
+	{ "hoyle5bridge",    GID_HOYLE5 },
+	{ "hoyle5children",  GID_HOYLE5 },
+	{ "hoyle5solitaire", GID_HOYLE5 },
+	{ "iceman",          GID_ICEMAN },
+	{ "inndemo",         GID_INNDEMO },
+	{ "islandbrain",     GID_ISLANDBRAIN },
+	{ "jones",           GID_JONES },
+	{ "kq1sci",          GID_KQ1 },
+	{ "kq4sci",          GID_KQ4 },
+	{ "kq5",             GID_KQ5 },
+	{ "kq6",             GID_KQ6 },
+	{ "kq7",             GID_KQ7 },
+	{ "kquestions",      GID_KQUESTIONS },
+	{ "laurabow",        GID_LAURABOW },
+	{ "laurabow2",       GID_LAURABOW2 },
+	{ "lighthouse",      GID_LIGHTHOUSE },
+	{ "longbow",         GID_LONGBOW },
+	{ "lsl1sci",         GID_LSL1 },
+	{ "lsl2",            GID_LSL2 },
+	{ "lsl3",            GID_LSL3 },
+	{ "lsl5",            GID_LSL5 },
+	{ "lsl6",            GID_LSL6 },
+	{ "lsl6hires",       GID_LSL6HIRES },
+	{ "lsl7",            GID_LSL7 },
+	{ "mothergoose",     GID_MOTHERGOOSE },
+	{ "mothergoose256",  GID_MOTHERGOOSE256 },
+	{ "mothergoosehires",GID_MOTHERGOOSEHIRES },
+	{ "msastrochicken",  GID_MSASTROCHICKEN },
+	{ "pepper",          GID_PEPPER },
+	{ "phantasmagoria",  GID_PHANTASMAGORIA },
+	{ "phantasmagoria2", GID_PHANTASMAGORIA2 },
+	{ "pq1sci",          GID_PQ1 },
+	{ "pq2",             GID_PQ2 },
+	{ "pq3",             GID_PQ3 },
+	{ "pq4",             GID_PQ4 },
+	{ "pq4demo",         GID_PQ4DEMO },
+	{ "pqswat",          GID_PQSWAT },
+	{ "qfg1",            GID_QFG1 },
+	{ "qfg1vga",         GID_QFG1VGA },
+	{ "qfg2",            GID_QFG2 },
+	{ "qfg3",            GID_QFG3 },
+	{ "qfg4",            GID_QFG4 },
+	{ "qfg4demo",        GID_QFG4DEMO },
+	{ "rama",            GID_RAMA },
+	{ "sci-fanmade",     GID_FANMADE },
+	{ "shivers",         GID_SHIVERS },
+	//{ "shivers2",        GID_SHIVERS2 },	// Not SCI
+	{ "slater",          GID_SLATER },
+	{ "sq1sci",          GID_SQ1 },
+	{ "sq3",             GID_SQ3 },
+	{ "sq4",             GID_SQ4 },
+	{ "sq5",             GID_SQ5 },
+	{ "sq6",             GID_SQ6 },
+	{ "torin",           GID_TORIN },
+	{ NULL, (SciGameId)-1 }
+};
+
+struct OldNewIdTableEntry {
+	const char *oldId;
+	const char *newId;
+	SciVersion version;
+};
+
+static const OldNewIdTableEntry s_oldNewTable[] = {
+	{ "archive",    "chest",            SCI_VERSION_NONE       },
+	{ "arthur",		"camelot",			SCI_VERSION_NONE       },
+	{ "brain",      "castlebrain",      SCI_VERSION_1_MIDDLE   },	// Amiga
+	{ "brain",      "castlebrain",      SCI_VERSION_1_LATE     },
+	{ "demo",		"christmas1988",	SCI_VERSION_NONE       },
+	{ "card",       "christmas1990",    SCI_VERSION_1_EARLY,   },
+	{ "card",       "christmas1992",    SCI_VERSION_1_1        },
+	{ "RH Budget",	"cnick-longbow",	SCI_VERSION_NONE       },
+	// iceman is the same
+	{ "icedemo",	"iceman",			SCI_VERSION_NONE       },
+	// longbow is the same
+	{ "eco",		"ecoquest",			SCI_VERSION_NONE       },
+	{ "eco2",		"ecoquest2",		SCI_VERSION_NONE       },	// EcoQuest 2 demo
+	{ "rain",		"ecoquest2",		SCI_VERSION_NONE       },	// EcoQuest 2 full
+	{ "tales",		"fairytales",		SCI_VERSION_NONE       },
+	{ "fp",			"freddypharkas",	SCI_VERSION_NONE       },
+	{ "emc",		"funseeker",		SCI_VERSION_NONE       },
+	{ "gk",			"gk1",				SCI_VERSION_NONE       },
+	// gk2 is the same
+	{ "gk2demo",	"gk2",				SCI_VERSION_NONE       },
+	{ "hoyledemo",	"hoyle1",			SCI_VERSION_NONE       },
+	{ "cardgames",	"hoyle1",			SCI_VERSION_NONE       },
+	{ "solitare",	"hoyle2",			SCI_VERSION_NONE       },
+	{ "hoyle3",	    "hoyle3",			SCI_VERSION_NONE       },
+	{ "hoyle4",	    "hoyle4",			SCI_VERSION_1_1        },
+	{ "hoyle4",	    "hoyle5",			SCI_VERSION_2_1_MIDDLE },
+	{ "brain",      "islandbrain",      SCI_VERSION_1_1        },
+	{ "demo000",	"kq1sci",			SCI_VERSION_NONE       },
+	{ "kq1",		"kq1sci",			SCI_VERSION_NONE       },
+	{ "kq4",		"kq4sci",			SCI_VERSION_NONE       },
+	// kq5 is the same
+	// kq6 is the same
+	{ "kq7cd",		"kq7",				SCI_VERSION_NONE       },
+	{ "quizgame-demo", "kquestions",    SCI_VERSION_NONE       },
+	{ "mm1",		"laurabow",			SCI_VERSION_NONE       },
+	{ "cb1",		"laurabow",			SCI_VERSION_NONE       },
+	{ "lb2",		"laurabow2",		SCI_VERSION_NONE       },
+	{ "rh",			"longbow",			SCI_VERSION_NONE       },
+	{ "ll1",		"lsl1sci",			SCI_VERSION_NONE       },
+	{ "lsl1",		"lsl1sci",			SCI_VERSION_NONE       },
+	// lsl2 is the same
+	{ "lsl3",		"lsl3",				SCI_VERSION_NONE       },
+	{ "ll5",		"lsl5",				SCI_VERSION_NONE       },
+	// lsl5 is the same
+	// lsl6 is the same
+	{ "mg",			"mothergoose",		SCI_VERSION_NONE       },
+	{ "twisty",		"pepper",			SCI_VERSION_NONE       },
+	{ "scary",      "phantasmagoria",   SCI_VERSION_NONE       },
+	// TODO: distinguish the full version of Phantasmagoria from the demo
+	{ "pq1",		"pq1sci",			SCI_VERSION_NONE       },
+	{ "pq",			"pq2",				SCI_VERSION_NONE       },
+	// pq3 is the same
+	// pq4 is the same
+	{ "hq",			"qfg1",				SCI_VERSION_NONE       },	// QFG1 SCI0/EGA
+	{ "glory",      "qfg1",             SCI_VERSION_0_LATE     },	// QFG1 SCI0/EGA
+	{ "trial",		"qfg2",				SCI_VERSION_NONE       },
+	{ "hq2demo",	"qfg2",				SCI_VERSION_NONE       },
+	// rama is the same
+	// TODO: distinguish the full version of rama from the demo
+	{ "thegame",	"slater",			SCI_VERSION_NONE       },
+	{ "sq1demo",	"sq1sci",			SCI_VERSION_NONE       },
+	{ "sq1",		"sq1sci",			SCI_VERSION_NONE       },
+	// sq3 is the same
+	// sq4 is the same
+	// sq5 is the same
+	// sq6 is the same
+	// TODO: distinguish the full version of SQ6 from the demo
+	// torin is the same
+	{ "l7",			"lsl7",				SCI_VERSION_NONE       },
+	{ "p2",			"phantasmagoria2",	SCI_VERSION_NONE       },
+	{ "lite",		"lighthouse",		SCI_VERSION_NONE       },
+
+	{ "", "", SCI_VERSION_NONE }
+};
+
+/**
+ * Converts the builtin Sierra game IDs to the ones we use in ScummVM
+ * @param[in] gameId		The internal game ID
+ * @param[in] gameFlags     The game's flags, which are adjusted accordingly for demos
+ * @return					The equivalent ScummVM game id
+ */
+static Common::String convertSierraGameId(Common::String sierraId, uint32 *gameFlags, ResourceManager &resMan) {
+	// Convert the id to lower case, so that we match all upper/lower case variants.
+	sierraId.toLowercase();
+
+	// If the game has less than the expected scripts, it's a demo
+	uint32 demoThreshold = 100;
+	// ...but there are some exceptions
+	if (sierraId == "brain" || sierraId == "lsl1" ||
+		sierraId == "mg" || sierraId == "pq" ||
+		sierraId == "jones" ||
+		sierraId == "cardgames" || sierraId == "solitare" ||
+		sierraId == "catdate" ||
+		sierraId == "hoyle4")
+		demoThreshold = 40;
+	if (sierraId == "hoyle3")
+		demoThreshold = 45;	// cnick-kq has 42 scripts. The actual hoyle 3 demo has 27.
+	if (sierraId == "fp" || sierraId == "gk" || sierraId == "pq4")
+		demoThreshold = 150;
+
+	Common::List<ResourceId> resources = resMan.listResources(kResourceTypeScript, -1);
+	if (resources.size() < demoThreshold) {
+		*gameFlags |= ADGF_DEMO;
+
+		// Crazy Nick's Picks
+		if (sierraId == "lsl1" && resources.size() == 34)
+			return "cnick-lsl";
+		if (sierraId == "sq4" && resources.size() == 34)
+			return "cnick-sq";
+		if (sierraId == "hoyle3" && resources.size() == 42)
+			return "cnick-kq";
+		if (sierraId == "rh budget" && resources.size() == 39)
+			return "cnick-longbow";
+		// TODO: cnick-laurabow (the name of the game object contains junk)
+
+		// Handle Astrochicken 1 (SQ3) and 2 (SQ4)
+		if (sierraId == "sq3" && resources.size() == 20)
+			return "astrochicken";
+		if (sierraId == "sq4")
+			return "msastrochicken";
+	}
+
+	if (sierraId == "torin" && resources.size() == 226)	// Torin's Passage demo
+		*gameFlags |= ADGF_DEMO;
+
+	for (const OldNewIdTableEntry *cur = s_oldNewTable; cur->oldId[0]; ++cur) {
+		if (sierraId == cur->oldId) {
+			// Distinguish same IDs via the SCI version
+			if (cur->version != SCI_VERSION_NONE && cur->version != getSciVersion())
+				continue;
+
+			return cur->newId;
+		}
+	}
+
+	if (sierraId == "glory") {
+		// This could either be qfg1 VGA, qfg3 or qfg4 demo (all SCI1.1),
+		// or qfg4 full (SCI2)
+		// qfg1 VGA doesn't have view 1
+		if (!resMan.testResource(ResourceId(kResourceTypeView, 1)))
+			return "qfg1vga";
+
+		// qfg4 full is SCI2
+		if (getSciVersion() == SCI_VERSION_2)
+			return "qfg4";
+
+		// qfg4 demo has less than 50 scripts
+		if (resources.size() < 50)
+			return "qfg4demo";
+
+		// Otherwise it's qfg3
+		return "qfg3";
+	}
+
+	return sierraId;
+}
+
+} // End of namespace Sci
+
+namespace Sci {
+
+class SciMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "sci";
+	}
+
+    bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
+	bool hasFeature(MetaEngineFeature f) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+
+	// A fallback detection method. This is not ideal as all detection lives in MetaEngine, but
+	// here fb detection has many engine dependencies.
+	virtual ADDetectedGame fallbackDetectExtern(uint md5Bytes, const FileMap &allFiles, const Common::FSList &fslist) const override;
+};
+
+bool SciMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const GameIdStrToEnum *g = s_gameIdStrToEnum;
+	for (; g->gameidStr; ++g) {
+		if (0 == strcmp(desc->gameId, g->gameidStr)) {
+			*engine = new SciEngine(syst, desc, g->gameidEnum);
+			return true;
+		}
+	}
+
+	return false;
+}
+
+bool SciMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves) ||
+		(f == kSupportsLoadingDuringStartup) ||
+		(f == kSupportsDeleteSave) ||
+		(f == kSavesSupportMetaInfo) ||
+		(f == kSavesSupportThumbnail) ||
+		(f == kSavesSupportCreationDate) ||
+		(f == kSavesSupportPlayTime);
+}
+
+bool SciEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher) ||
+		(f == kSupportsLoadingDuringRuntime); // ||
+		//(f == kSupportsSavingDuringRuntime);
+		// We can't allow saving through ScummVM menu, because
+		//  a) lots of games don't like saving everywhere (e.g. castle of dr. brain)
+		//  b) some games even dont allow saving in certain rooms (e.g. lsl6)
+		//  c) somehow some games even get mad when doing this (execstackbase was 1 all of a sudden in lsl3)
+		//  d) for sci0/sci01 games we should at least wait till status bar got drawn, although this may not be enough
+		// we can't make sure that the scripts are fine with us saving at a specific location, doing so may work sometimes
+		//  and some other times it won't work.
+}
+
+SaveStateList SciMetaEngine::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String pattern = target;
+	pattern += ".###";
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	bool hasAutosave = false;
+	int slotNr = 0;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		// Obtain the last 3 digits of the filename, since they correspond to the save slot
+		slotNr = atoi(file->c_str() + file->size() - 3);
+
+		if (slotNr >= 0 && slotNr <= 99) {
+			Common::InSaveFile *in = saveFileMan->openForLoading(*file);
+			if (in) {
+				SavegameMetadata meta;
+				if (!get_savegame_metadata(in, meta)) {
+					// invalid
+					delete in;
+					continue;
+				}
+				SaveStateDescriptor descriptor(slotNr, meta.name);
+
+				if (slotNr == 0) {
+					// ScummVM auto-save slot
+					descriptor.setWriteProtectedFlag(true);
+					hasAutosave = true;
+				} else {
+					descriptor.setWriteProtectedFlag(false);
+				}
+
+				saveList.push_back(descriptor);
+				delete in;
+			}
+		}
+	}
+
+	if (!hasAutosave) {
+		SaveStateDescriptor descriptor(0, _("(Autosave)"));
+		descriptor.setLocked(true);
+		saveList.push_back(descriptor);
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+SaveStateDescriptor SciMetaEngineConnect::querySaveMetaInfos(const char *target, int slotNr) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slotNr);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
+	SaveStateDescriptor descriptor(slotNr, "");
+
+	if (slotNr == 0) {
+		// ScummVM auto-save slot
+		descriptor.setWriteProtectedFlag(true);
+		descriptor.setDeletableFlag(false);
+	} else {
+		descriptor.setWriteProtectedFlag(false);
+		descriptor.setDeletableFlag(true);
+	}
+
+	if (in) {
+		SavegameMetadata meta;
+
+		if (!get_savegame_metadata(in, meta)) {
+			// invalid
+			delete in;
+
+			descriptor.setDescription("*Invalid*");
+			return descriptor;
+		}
+
+		descriptor.setDescription(meta.name);
+
+		Graphics::Surface *thumbnail;
+		if (!Graphics::loadThumbnail(*in, thumbnail)) {
+			// invalid
+			delete in;
+
+			descriptor.setDescription("*Invalid*");
+			return descriptor;
+		}
+		descriptor.setThumbnail(thumbnail);
+
+		int day = (meta.saveDate >> 24) & 0xFF;
+		int month = (meta.saveDate >> 16) & 0xFF;
+		int year = meta.saveDate & 0xFFFF;
+
+		descriptor.setSaveDate(year, month, day);
+
+		int hour = (meta.saveTime >> 16) & 0xFF;
+		int minutes = (meta.saveTime >> 8) & 0xFF;
+
+		descriptor.setSaveTime(hour, minutes);
+
+		if (meta.version >= 34) {
+			descriptor.setPlayTime(meta.playTime * 1000 / 60);
+		} else {
+			descriptor.setPlayTime(meta.playTime * 1000);
+		}
+
+		delete in;
+
+		return descriptor;
+	}
+	// Return empty descriptor
+	return descriptor;
+}
+
+int SciMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+
+void SciMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String fileName = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(fileName);
+}
+
+Common::Error SciEngine::loadGameState(int slot) {
+	_gamestate->_delayedRestoreGameId = slot;
+	return Common::kNoError;
+}
+
+Common::Error SciEngine::saveGameState(int slot, const Common::String &desc, bool isAutosave) {
+	const char *version = "";
+	if (gamestate_save(_gamestate, slot, desc, version)) {
+		return Common::kNoError;
+	}
+	return Common::kWritingFailed;
+}
+
+bool SciEngine::canLoadGameStateCurrently() {
+#ifdef ENABLE_SCI32
+	const Common::String &guiOptions = ConfMan.get("guioptions");
+	if (getSciVersion() >= SCI_VERSION_2) {
+		if (ConfMan.getBool("originalsaveload") ||
+			Common::checkGameGUIOption(GUIO_NOLAUNCHLOAD, guiOptions)) {
+
+			return false;
+		}
+	}
+#endif
+
+	return !_gamestate->executionStackBase;
+}
+
+bool SciEngine::canSaveGameStateCurrently() {
+	// see comment about kSupportsSavingDuringRuntime in SciEngine::hasFeature
+	return false;
+}
+
+} // End of namespace Sci
+
+/**
+ * External fallback detection-related code.
+ */
+namespace Sci {
+
+Common::Language charToScummVMLanguage(const char c) {
+	switch (c) {
+	case 'F':
+		return Common::FR_FRA;
+	case 'S':
+		return Common::ES_ESP;
+	case 'I':
+		return Common::IT_ITA;
+	case 'G':
+		return Common::DE_DEU;
+	case 'J':
+	case 'j':
+		return Common::JA_JPN;
+	case 'P':
+		return Common::PT_BRA;
+	default:
+		return Common::UNK_LANG;
+	}
+}
+
+static char s_fallbackGameIdBuf[256];
+
+/**
+ * The fallback game descriptor used by the SCI engine's fallbackDetector.
+ * Contents of this struct are overwritten by the fallbackDetector.
+ */
+static ADGameDescription s_fallbackDesc = {
+	"",
+	"",
+	AD_ENTRY1(0, 0), // This should always be AD_ENTRY1(0, 0) in the fallback descriptor
+	Common::UNK_LANG,
+	Common::kPlatformDOS,
+	ADGF_NO_FLAGS,
+	GUIO3(GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE)
+};
+
+ADDetectedGame SciMetaEngineConnect::fallbackDetectExtern(uint md5Bytes, const FileMap &allFiles, const Common::FSList &fslist) const {
+	bool foundResMap = false;
+	bool foundRes000 = false;
+
+	// Set some defaults
+	s_fallbackDesc.extra = "";
+	s_fallbackDesc.language = Common::EN_ANY;
+	s_fallbackDesc.flags = ADGF_NO_FLAGS;
+	s_fallbackDesc.platform = Common::kPlatformDOS;	// default to PC platform
+	s_fallbackDesc.gameId = "sci";
+	s_fallbackDesc.guiOptions = GUIO3(GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE);
+
+	if (allFiles.contains("resource.map") || allFiles.contains("Data1")
+	    || allFiles.contains("resmap.000") || allFiles.contains("resmap.001")) {
+		foundResMap = true;
+	}
+
+	// Determine if we got a CD version and set the CD flag accordingly, by checking for
+	// resource.aud for SCI1.1 CD games, or audio001.002 for SCI1 CD games. We assume that
+	// the file should be over 10MB, as it contains all the game speech and is usually
+	// around 450MB+. The size check is for some floppy game versions like KQ6 floppy, which
+	// also have a small resource.aud file
+	if (allFiles.contains("resource.aud") || allFiles.contains("resaud.001") || allFiles.contains("audio001.002")) {
+		Common::FSNode file = allFiles.contains("resource.aud") ? allFiles["resource.aud"] : (allFiles.contains("resaud.001") ? allFiles["resaud.001"] : allFiles["audio001.002"]);
+		Common::SeekableReadStream *tmpStream = file.createReadStream();
+		if (tmpStream->size() > 10 * 1024 * 1024) {
+			// We got a CD version, so set the CD flag accordingly
+			s_fallbackDesc.flags |= ADGF_CD;
+		}
+		delete tmpStream;
+	}
+
+	if (allFiles.contains("resource.000") || allFiles.contains("resource.001")
+		|| allFiles.contains("ressci.000") || allFiles.contains("ressci.001"))
+		foundRes000 = true;
+
+	// Data1 contains both map and volume for SCI1.1+ Mac games
+	if (allFiles.contains("Data1")) {
+		foundResMap = foundRes000 = true;
+		 s_fallbackDesc.platform = Common::kPlatformMacintosh;
+	}
+
+	// Determine the game platform
+	// The existence of any of these files indicates an Amiga game
+	if (allFiles.contains("9.pat") || allFiles.contains("spal") ||
+		allFiles.contains("patch.005") || allFiles.contains("bank.001"))
+			s_fallbackDesc.platform = Common::kPlatformAmiga;
+
+	// The existence of 7.pat or patch.200 indicates a Mac game
+	if (allFiles.contains("7.pat") || allFiles.contains("patch.200"))
+		s_fallbackDesc.platform = Common::kPlatformMacintosh;
+
+	// The data files for Atari ST versions are the same as their DOS counterparts
+
+
+	// If these files aren't found, it can't be SCI
+	if (!foundResMap && !foundRes000)
+		return ADDetectedGame();
+
+	ResourceManager resMan(true);
+	resMan.addAppropriateSourcesForDetection(fslist);
+	resMan.init();
+	// TODO: Add error handling.
+
+#ifndef ENABLE_SCI32
+	// Is SCI32 compiled in? If not, and this is a SCI32 game,
+	// stop here
+	if (getSciVersionForDetection() >= SCI_VERSION_2)
+		return ADDetectedGame();
+#endif
+
+	ViewType gameViews = resMan.getViewType();
+
+	// Have we identified the game views? If not, stop here
+	// Can't be SCI (or unsupported SCI views). Pinball Creep by Sierra also uses resource.map/resource.000 files
+	// but doesn't share SCI format at all
+	if (gameViews == kViewUnknown)
+		return ADDetectedGame();
+
+	// Set the platform to Amiga if the game is using Amiga views
+	if (gameViews == kViewAmiga)
+		s_fallbackDesc.platform = Common::kPlatformAmiga;
+
+	// Determine the game id
+	Common::String sierraGameId = resMan.findSierraGameId(s_fallbackDesc.platform == Common::kPlatformMacintosh);
+
+	// If we don't have a game id, the game is not SCI
+	if (sierraGameId.empty())
+		return ADDetectedGame();
+
+	Common::String gameId = convertSierraGameId(sierraGameId, &s_fallbackDesc.flags, resMan);
+	Common::strlcpy(s_fallbackGameIdBuf, gameId.c_str(), sizeof(s_fallbackGameIdBuf));
+	s_fallbackDesc.gameId = s_fallbackGameIdBuf;
+
+	// Try to determine the game language
+	// Load up text 0 and start looking for "#" characters
+	// Non-English versions contain strings like XXXX#YZZZZ
+	// Where XXXX is the English string, #Y a separator indicating the language
+	// (e.g. #G for German) and ZZZZ is the translated text
+	// NOTE: This doesn't work for games which use message instead of text resources
+	// (like, for example, Eco Quest 1 and all SCI1.1 games and newer, e.g. Freddy Pharkas).
+	// As far as we know, these games store the messages of each language in separate
+	// resources, and it's not possible to detect that easily
+	// Also look for "%J" which is used in japanese games
+	Resource *text = resMan.findResource(ResourceId(kResourceTypeText, 0), false);
+	uint seeker = 0;
+	if (text) {
+		while (seeker < text->size()) {
+			if (text->getUint8At(seeker) == '#')  {
+				if (seeker + 1 < text->size())
+					s_fallbackDesc.language = charToScummVMLanguage(text->getUint8At(seeker + 1));
+				break;
+			}
+			if (text->getUint8At(seeker) == '%') {
+				if ((seeker + 1 < text->size()) && (text->getUint8At(seeker + 1) == 'J')) {
+					s_fallbackDesc.language = charToScummVMLanguage(text->getUint8At(seeker + 1));
+					break;
+				}
+			}
+			seeker++;
+		}
+	}
+
+
+	// Fill in "extra" field
+
+	// Is this an EGA version that might have a VGA pendant? Then we want
+	// to mark it as such in the "extra" field.
+	const bool markAsEGA = (gameViews == kViewEga && s_fallbackDesc.platform != Common::kPlatformAmiga
+			&& getSciVersion() > SCI_VERSION_1_EGA_ONLY);
+
+	const bool isDemo = (s_fallbackDesc.flags & ADGF_DEMO);
+	const bool isCD = (s_fallbackDesc.flags & ADGF_CD);
+
+	if (!isCD)
+		s_fallbackDesc.guiOptions = GUIO4(GUIO_NOSPEECH, GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE);
+
+	if (gameId.hasSuffix("sci")) {
+		s_fallbackDesc.extra = "SCI";
+
+		// Differentiate EGA versions from the VGA ones, where needed
+		if (markAsEGA)
+			s_fallbackDesc.extra = "SCI/EGA";
+
+		// Mark as demo.
+		// Note: This overwrites the 'EGA' info, if it was previously set.
+		if (isDemo)
+			s_fallbackDesc.extra = "SCI/Demo";
+	} else {
+		if (markAsEGA)
+			s_fallbackDesc.extra = "EGA";
+
+		// Set "CD" and "Demo" as appropriate.
+		// Note: This overwrites the 'EGA' info, if it was previously set.
+		if (isDemo && isCD)
+			s_fallbackDesc.extra = "CD Demo";
+		else if (isDemo)
+			s_fallbackDesc.extra = "Demo";
+		else if (isCD)
+			s_fallbackDesc.extra = "CD";
+	}
+
+	return ADDetectedGame(&s_fallbackDesc);
+}
+
+} // End of namespace Sci
+
+#if PLUGIN_ENABLED_DYNAMIC(SCI)
+	REGISTER_PLUGIN_DYNAMIC(SCI, PLUGIN_TYPE_ENGINE, Sci::SciMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(SCI, PLUGIN_TYPE_ENGINE, Sci::SciMetaEngineConnect);
+#endif
diff --git a/engines/sci/module.mk b/engines/sci/module.mk
index f2fa5b762a..4e2724cede 100644
--- a/engines/sci/module.mk
+++ b/engines/sci/module.mk
@@ -3,8 +3,8 @@ MODULE := engines/sci
 MODULE_OBJS := \
 	console.o \
 	decompressor.o \
-	detection.o \
 	event.o \
+	metaengine.o \
 	resource.o \
 	resource_audio.o \
 	resource_patcher.o \
@@ -113,3 +113,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o


Commit: 81ba5d5627208f409b9fafdb23e907883c0deee8
    https://github.com/scummvm/scummvm/commit/81ba5d5627208f409b9fafdb23e907883c0deee8
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: ME & MEC: Allow MEC to build engine options widget.

- Rename the one in ME to avoid ambiguity.
- ME is named *static & MEC is named *dynamic.
- This change means that engines  can build 2 types of option widgets.
- The "Engine" tab is created statically regardless if an engine plugin is present or not.
- The in-game options are built using the MEC.
- With this commit, engines/dialogs is no longer dependant on MetaEngine, and instead used MEC all over.

Changed paths:
    engines/dialogs.cpp
    engines/metaengine.cpp
    engines/metaengine.h
    gui/editgamedialog.cpp


diff --git a/engines/dialogs.cpp b/engines/dialogs.cpp
index 4bcecad4b7..b47be56ca6 100644
--- a/engines/dialogs.cpp
+++ b/engines/dialogs.cpp
@@ -273,7 +273,6 @@ ConfigDialog::ConfigDialog() :
 	assert(g_engine);
 
 	const Common::String &gameDomain = ConfMan.getActiveDomainName();
-	const MetaEngine &metaEngine = g_engine->getMetaEngine();
 	const MetaEngineConnect &metaEngineConnect = g_engine->getMetaEngineConnect();
 
 	// GUI:  Add tab widget
@@ -286,7 +285,7 @@ ConfigDialog::ConfigDialog() :
 	int tabId = tab->addTab(_("Game"), "GlobalConfig_Engine");
 
 	if (g_engine->hasFeature(Engine::kSupportsChangingOptionsDuringRuntime)) {
-		_engineOptions = metaEngine.buildEngineOptionsWidget(tab, "GlobalConfig_Engine.Container", gameDomain);
+		_engineOptions = metaEngineConnect.buildEngineOptionsWidgetDynamic(tab, "GlobalConfig_Engine.Container", gameDomain);
 	}
 
 	if (_engineOptions) {
diff --git a/engines/metaengine.cpp b/engines/metaengine.cpp
index aff0df47a0..a77a787110 100644
--- a/engines/metaengine.cpp
+++ b/engines/metaengine.cpp
@@ -345,7 +345,16 @@ void MetaEngine::registerDefaultSettings(const Common::String &) const {
 	}
 }
 
-GUI::OptionsContainerWidget *MetaEngine::buildEngineOptionsWidget(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
+GUI::OptionsContainerWidget *MetaEngine::buildEngineOptionsWidgetStatic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
+	const ExtraGuiOptions engineOptions = getExtraGuiOptions(target);
+	if (engineOptions.empty()) {
+		return nullptr;
+	}
+
+	return new GUI::ExtraGuiOptionsWidget(boss, name, target, engineOptions);
+}
+
+GUI::OptionsContainerWidget *MetaEngineConnect::buildEngineOptionsWidgetDynamic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
 	const ExtraGuiOptions engineOptions = getExtraGuiOptions(target);
 	if (engineOptions.empty()) {
 		return nullptr;
diff --git a/engines/metaengine.h b/engines/metaengine.h
index 9ed6fd5abc..cb9ade66f2 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -164,7 +164,7 @@ public:
 	 * @param name     the name the returned widget must use
 	 * @param target   name of a config manager target
 	 */
-	virtual GUI::OptionsContainerWidget *buildEngineOptionsWidget(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const;
+	virtual GUI::OptionsContainerWidget *buildEngineOptionsWidgetStatic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const;
 };
 
 /**
@@ -313,6 +313,28 @@ public:
 	 */
 	virtual Common::Array<Common::Keymap *> initKeymaps(const char *target) const;
 
+	virtual const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const {
+		return ExtraGuiOptions();
+	}
+
+	/**
+	 * Return a GUI widget container for configuring the specified target options.
+	 *
+	 * Engines can build custom options dialogs from here, but by default a simple widget
+	 * allowing to configure the extra GUI options is used.
+	 *
+	 * A engine that builds the "Engines" tab in "Edit Game" uses a MetaEngine.
+	 * A engine that specifies a custom dialog, when a game is running, uses a MetaEngineConnect.
+	 *
+	 * Engines that don't want to have an Engine tab in the edit game dialog
+	 * can return nullptr.
+	 *
+	 * @param boss     the widget / dialog the returned widget is a child of
+	 * @param name     the name the returned widget must use
+	 * @param target   name of a config manager target
+	 */
+	virtual GUI::OptionsContainerWidget *buildEngineOptionsWidgetDynamic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const;
+
 	/** @name MetaEngineFeature flags */
 	//@{
 
diff --git a/gui/editgamedialog.cpp b/gui/editgamedialog.cpp
index 606c4c305c..65fe06dfdb 100644
--- a/gui/editgamedialog.cpp
+++ b/gui/editgamedialog.cpp
@@ -187,7 +187,7 @@ EditGameDialog::EditGameDialog(const String &domain)
 
 		const MetaEngine &metaEngine = metaEnginePlugin->get<MetaEngine>();
 		metaEngine.registerDefaultSettings(_domain);
-		_engineOptions = metaEngine.buildEngineOptionsWidget(tab, "GameOptions_Engine.Container", _domain);
+		_engineOptions = metaEngine.buildEngineOptionsWidgetStatic(tab, "GameOptions_Engine.Container", _domain);
 
 		if (_engineOptions) {
 			_engineOptions->setParentDialog(this);


Commit: 8c324fab423b43d49ff03d12decb4fa0e51a8702
    https://github.com/scummvm/scummvm/commit/8c324fab423b43d49ff03d12decb4fa0e51a8702
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MOHAWK: RIVEN: Move shared graphics/detection enum to new header.

Changed paths:
  A engines/mohawk/riven_metaengine/graphics_detection_enums.h
    engines/mohawk/riven_graphics.h


diff --git a/engines/mohawk/riven_graphics.h b/engines/mohawk/riven_graphics.h
index 2da51da79d..25d7921290 100644
--- a/engines/mohawk/riven_graphics.h
+++ b/engines/mohawk/riven_graphics.h
@@ -24,6 +24,7 @@
 #define MOHAWK_RIVEN_GRAPHICS_H
 
 #include "mohawk/graphics.h"
+#include "mohawk/riven_metaengine/graphics_detection_enums.h"
 
 #include "common/ustr.h"
 
@@ -51,13 +52,6 @@ enum RivenTransition {
 	kRivenTransitionBlend2    = 17
 };
 
-enum RivenTransitionMode {
-	kRivenTransitionModeDisabled = 5000,
-	kRivenTransitionModeFastest  = 5001,
-	kRivenTransitionModeNormal   = 5002,
-	kRivenTransitionModeBest     = 5003
-};
-
 enum RivenCreditsImageNumber {
 	kRivenCreditsZeroImage   = 302,
 	kRivenCreditsFirstImage  = 303,
diff --git a/engines/mohawk/riven_metaengine/graphics_detection_enums.h b/engines/mohawk/riven_metaengine/graphics_detection_enums.h
new file mode 100644
index 0000000000..afddeb41ad
--- /dev/null
+++ b/engines/mohawk/riven_metaengine/graphics_detection_enums.h
@@ -0,0 +1,33 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef MOHAWK_RIVEN_GRAPHICS_DETECTION_ENUMS_H
+#define MOHAWK_RIVEN_GRAPHICS_DETECTION_ENUMS_H
+
+enum RivenTransitionMode {
+	kRivenTransitionModeDisabled = 5000,
+	kRivenTransitionModeFastest  = 5001,
+	kRivenTransitionModeNormal   = 5002,
+	kRivenTransitionModeBest     = 5003
+};
+
+#endif


Commit: 2113bbcd9c72f036c346111570fc07e26b9a3718
    https://github.com/scummvm/scummvm/commit/2113bbcd9c72f036c346111570fc07e26b9a3718
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MOHAWK: RIVEN: Move shared detection/riven code from engine to a new MetaEngine class.

- This new class will help detection work properly.

Changed paths:
  A engines/mohawk/riven_metaengine/metaengine.cpp
  A engines/mohawk/riven_metaengine/metaengine.h
    engines/mohawk/riven.cpp
    engines/mohawk/riven.h


diff --git a/engines/mohawk/riven.cpp b/engines/mohawk/riven.cpp
index 8afef9c273..a3c2b669fc 100644
--- a/engines/mohawk/riven.cpp
+++ b/engines/mohawk/riven.cpp
@@ -57,6 +57,9 @@
 #include "mohawk/dialogs.h"
 #include "mohawk/console.h"
 
+// Shared code between detection/engine.
+#include "mohawk/riven_metaengine/metaengine.h"
+
 namespace Mohawk {
 
 MohawkEngine_Riven::MohawkEngine_Riven(OSystem *syst, const MohawkGameDescription *gamedesc) :
@@ -509,23 +512,8 @@ bool MohawkEngine_Riven::checkDatafiles() {
 	return false;
 }
 
-const RivenLanguage *MohawkEngine_Riven::listLanguages() {
-	static const RivenLanguage languages[] = {
-	    { Common::EN_ANY,   "english"  },
-	    { Common::FR_FRA,   "french"   },
-	    { Common::DE_DEU,   "german"   },
-	    { Common::IT_ITA,   "italian"  },
-	    { Common::JA_JPN,   "japanese" },
-	    { Common::PL_POL,   "polish"   },
-	    { Common::RU_RUS,   "russian"  },
-	    { Common::ES_ESP,   "spanish"  },
-	    { Common::UNK_LANG, nullptr    }
-	};
-	return languages;
-}
-
 const RivenLanguage *MohawkEngine_Riven::getLanguageDesc(Common::Language language) {
-	const RivenLanguage *languages = listLanguages();
+	const RivenLanguage *languages = MohawkMetaEngine_Riven::listLanguages();
 
 	while (languages->language != Common::UNK_LANG) {
 		if (languages->language == language) {
@@ -820,12 +808,6 @@ bool MohawkEngine_Riven::isInteractive() const {
 	return !_scriptMan->hasQueuedScripts() && !hasGameEnded();
 }
 
-void MohawkEngine_Riven::registerDefaultSettings() {
-	ConfMan.registerDefault("zip_mode", false);
-	ConfMan.registerDefault("water_effects", true);
-	ConfMan.registerDefault("transition_mode", kRivenTransitionModeFastest);
-}
-
 Common::KeymapArray MohawkEngine_Riven::initKeymaps(const char *target) {
 	using namespace Common;
 
diff --git a/engines/mohawk/riven.h b/engines/mohawk/riven.h
index f916465f4a..6b78852bcf 100644
--- a/engines/mohawk/riven.h
+++ b/engines/mohawk/riven.h
@@ -115,12 +115,11 @@ public:
 		return Common::String::format("riven-%03d.rvn", slot);
 	}
 
-	static const RivenLanguage *listLanguages();
 	static const RivenLanguage *getLanguageDesc(Common::Language language);
 	Common::Language getLanguage() const override;
 
 	bool hasFeature(EngineFeature f) const override;
-	static void registerDefaultSettings();
+
 	void applyGameSettings() override;
 	static Common::Array<Common::Keymap *> initKeymaps(const char *target);
 
@@ -202,11 +201,6 @@ public:
 	void startNewGame();
 };
 
-struct RivenLanguage {
-	Common::Language language;
-	const char *archiveSuffix;
-};
-
 } // End of namespace Mohawk
 
 #endif
diff --git a/engines/mohawk/riven_metaengine/metaengine.cpp b/engines/mohawk/riven_metaengine/metaengine.cpp
new file mode 100644
index 0000000000..e182826de3
--- /dev/null
+++ b/engines/mohawk/riven_metaengine/metaengine.cpp
@@ -0,0 +1,45 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "mohawk/riven_metaengine/metaengine.h"
+#include "mohawk/riven_metaengine/graphics_detection_enums.h"
+
+void Mohawk::MohawkMetaEngine_Riven::registerDefaultSettings() {
+	ConfMan.registerDefault("zip_mode", false);
+	ConfMan.registerDefault("water_effects", true);
+	ConfMan.registerDefault("transition_mode", kRivenTransitionModeFastest);
+}
+
+const Mohawk::RivenLanguage *Mohawk::MohawkMetaEngine_Riven::listLanguages() {
+	static const RivenLanguage languages[] = {
+	    { Common::EN_ANY,   "english"  },
+	    { Common::FR_FRA,   "french"   },
+	    { Common::DE_DEU,   "german"   },
+	    { Common::IT_ITA,   "italian"  },
+	    { Common::JA_JPN,   "japanese" },
+	    { Common::PL_POL,   "polish"   },
+	    { Common::RU_RUS,   "russian"  },
+	    { Common::ES_ESP,   "spanish"  },
+	    { Common::UNK_LANG, nullptr    }
+	};
+	return languages;
+}
diff --git a/engines/mohawk/riven_metaengine/metaengine.h b/engines/mohawk/riven_metaengine/metaengine.h
new file mode 100644
index 0000000000..1ebf846b19
--- /dev/null
+++ b/engines/mohawk/riven_metaengine/metaengine.h
@@ -0,0 +1,44 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef MOHAWK_RIVEN_METAENGINE_H
+#define MOHAWK_RIVEN_METAENGINE_H
+
+#include "common/config-manager.h"
+#include "common/language.h"
+
+namespace Mohawk {
+
+struct RivenLanguage {
+	Common::Language language;
+	const char *archiveSuffix;
+};
+
+class MohawkMetaEngine_Riven {
+public:
+    static void registerDefaultSettings();
+    static const RivenLanguage *listLanguages();
+};
+
+} // End of namespace Mohawk
+
+#endif // MOHAWK_RIVEN_METAENGINE_H


Commit: 65320b26a6ce27996c0739424a4fa1b8ddf50425
    https://github.com/scummvm/scummvm/commit/65320b26a6ce27996c0739424a4fa1b8ddf50425
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MOHAWK: MYST: Move common myst engine/detection code to new class.

- This new class will help in detection.

Changed paths:
  A engines/mohawk/myst_metaengine/metaengine.cpp
  A engines/mohawk/myst_metaengine/metaengine.h
    engines/mohawk/myst.cpp
    engines/mohawk/myst.h


diff --git a/engines/mohawk/myst.cpp b/engines/mohawk/myst.cpp
index 1b426518d1..b190af4f29 100644
--- a/engines/mohawk/myst.cpp
+++ b/engines/mohawk/myst.cpp
@@ -62,6 +62,9 @@
 #include "mohawk/myst_stacks/slides.h"
 #include "mohawk/myst_stacks/stoneship.h"
 
+// Common files for detection & engines
+#include "mohawk/myst_metaengine/metaengine.h"
+
 namespace Mohawk {
 
 MohawkEngine_Myst::MohawkEngine_Myst(OSystem *syst, const MohawkGameDescription *gamedesc) :
@@ -444,20 +447,8 @@ Common::Error MohawkEngine_Myst::run() {
 	return Common::kNoError;
 }
 
-const MystLanguage *MohawkEngine_Myst::listLanguages() {
-	static const MystLanguage languages[] = {
-	    { Common::EN_ANY,   "english"  },
-	    { Common::FR_FRA,   "french"   },
-	    { Common::DE_DEU,   "german"   },
-	    { Common::PL_POL,   "polish"   },
-	    { Common::ES_ESP,   "spanish"  },
-	    { Common::UNK_LANG, nullptr    }
-	};
-	return languages;
-}
-
 const MystLanguage *MohawkEngine_Myst::getLanguageDesc(Common::Language language) {
-	const MystLanguage *languages = listLanguages();
+	const MystLanguage *languages = MohawkMetaEngine_Myst::listLanguages();
 
 	while (languages->language != Common::UNK_LANG) {
 		if (languages->language == language) {
@@ -535,12 +526,6 @@ void MohawkEngine_Myst::loadArchive(const char *archiveName, const char *languag
 	_mhk.push_back(archive);
 }
 
-void MohawkEngine_Myst::registerDefaultSettings() {
-	ConfMan.registerDefault("playmystflyby", false);
-	ConfMan.registerDefault("zip_mode", false);
-	ConfMan.registerDefault("transition_mode", false);
-}
-
 void MohawkEngine_Myst::applyGameSettings() {
 	// Allow changing the language when in the main menu when the game has not yet been started.
 	// It's not possible to reliably change the language once the game is started as the current
diff --git a/engines/mohawk/myst.h b/engines/mohawk/myst.h
index 150ea6221a..c2ac98a729 100644
--- a/engines/mohawk/myst.h
+++ b/engines/mohawk/myst.h
@@ -197,7 +197,7 @@ public:
 	}
 
 	bool hasFeature(EngineFeature f) const override;
-	static void registerDefaultSettings();
+
 	void applyGameSettings() override;
 	static Common::Array<Common::Keymap *> initKeymaps(const char *target);
 
@@ -210,7 +210,6 @@ public:
 	void doAction(MystEventAction action);
 	void scheduleAction(MystEventAction action);
 
-	static const MystLanguage *listLanguages();
 	static const MystLanguage *getLanguageDesc(Common::Language language);
 	Common::Language getLanguage() const override;
 
@@ -247,11 +246,6 @@ private:
 	MystEventAction _scheduledAction;
 };
 
-struct MystLanguage {
-	Common::Language language;
-	const char *archiveSuffix;
-};
-
 } // End of namespace Mohawk
 
 #endif
diff --git a/engines/mohawk/myst_metaengine/metaengine.cpp b/engines/mohawk/myst_metaengine/metaengine.cpp
new file mode 100644
index 0000000000..54976218ae
--- /dev/null
+++ b/engines/mohawk/myst_metaengine/metaengine.cpp
@@ -0,0 +1,41 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "mohawk/myst_metaengine/metaengine.h"
+
+void Mohawk::MohawkMetaEngine_Myst::registerDefaultSettings() {
+	ConfMan.registerDefault("playmystflyby", false);
+	ConfMan.registerDefault("zip_mode", false);
+	ConfMan.registerDefault("transition_mode", false);
+}
+
+const Mohawk::MystLanguage *Mohawk::MohawkMetaEngine_Myst::listLanguages() {
+	static const MystLanguage languages[] = {
+	    { Common::EN_ANY,   "english"  },
+	    { Common::FR_FRA,   "french"   },
+	    { Common::DE_DEU,   "german"   },
+	    { Common::PL_POL,   "polish"   },
+	    { Common::ES_ESP,   "spanish"  },
+	    { Common::UNK_LANG, nullptr    }
+	};
+	return languages;
+}
diff --git a/engines/mohawk/myst_metaengine/metaengine.h b/engines/mohawk/myst_metaengine/metaengine.h
new file mode 100644
index 0000000000..340cacd087
--- /dev/null
+++ b/engines/mohawk/myst_metaengine/metaengine.h
@@ -0,0 +1,44 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef MOHAWK_MYST_METAENGINE_H
+#define MOHAWK_MYST_METAENGINE_H
+
+#include "common/config-manager.h"
+#include "common/language.h"
+
+namespace Mohawk {
+
+struct MystLanguage {
+	Common::Language language;
+	const char *archiveSuffix;
+};
+
+class MohawkMetaEngine_Myst {
+public:
+    static void registerDefaultSettings();
+    static const MystLanguage *listLanguages();
+};
+
+} // End of namespace Mohawk
+
+#endif


Commit: b4a0fcca6c6fdc93b8d79094da486ec01e532f35
    https://github.com/scummvm/scummvm/commit/b4a0fcca6c6fdc93b8d79094da486ec01e532f35
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MOHAWK: Dialogs: Use the new classes to help in dialogs correctly.

Changed paths:
    engines/mohawk/dialogs.cpp


diff --git a/engines/mohawk/dialogs.cpp b/engines/mohawk/dialogs.cpp
index e18d276d79..af27c530f8 100644
--- a/engines/mohawk/dialogs.cpp
+++ b/engines/mohawk/dialogs.cpp
@@ -38,11 +38,13 @@
 #include "mohawk/myst.h"
 #include "mohawk/myst_actions.h"
 #include "mohawk/myst_scripts.h"
+#include "mohawk/myst_metaengine/metaengine.h"
 #endif
 
 #ifdef ENABLE_RIVEN
 #include "mohawk/riven.h"
 #include "mohawk/riven_graphics.h"
+#include "mohawk/riven_metaengine/metaengine.h"
 #endif
 
 namespace Mohawk {
@@ -140,7 +142,7 @@ MystOptionsWidget::MystOptionsWidget(GuiObject *boss, const Common::String &name
 
 			_languagePopUp = new GUI::PopUpWidget(widgetsBoss(), "MystOptionsDialog.Language");
 
-			const MystLanguage *languages = MohawkEngine_Myst::listLanguages();
+			const MystLanguage *languages = MohawkMetaEngine_Myst::listLanguages();
 			while (languages->language != Common::UNK_LANG) {
 				_languagePopUp->appendEntry(Common::getLanguageDescription(languages->language), languages->language);
 				languages++;
@@ -342,7 +344,7 @@ RivenOptionsWidget::RivenOptionsWidget(GuiObject *boss, const Common::String &na
 		_languagePopUp = new GUI::PopUpWidget(widgetsBoss(), "RivenOptionsDialog.Language");
 		_languagePopUp->setEnabled(canChangeLanguage);
 
-		const RivenLanguage *languages = MohawkEngine_Riven::listLanguages();
+		const RivenLanguage *languages = MohawkMetaEngine_Riven::listLanguages();
 		while (languages->language != Common::UNK_LANG) {
 			_languagePopUp->appendEntry(Common::getLanguageDescription(languages->language), languages->language);
 			languages++;


Commit: 45ad55df2dc5686e18aa85f83d4665eef797524d
    https://github.com/scummvm/scummvm/commit/45ad55df2dc5686e18aa85f83d4665eef797524d
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MOHAWK: Move shared engine/detection enums to new header file.

Changed paths:
  A engines/mohawk/detection_enums.h
    engines/mohawk/mohawk.h


diff --git a/engines/mohawk/detection_enums.h b/engines/mohawk/detection_enums.h
new file mode 100644
index 0000000000..5f844c2531
--- /dev/null
+++ b/engines/mohawk/detection_enums.h
@@ -0,0 +1,54 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef MOHAWK_DETECTION_ENUMS_H
+#define MOHAWK_DETECTION_ENUMS_H
+
+namespace Mohawk {
+
+enum MohawkGameType {
+	GType_MYST,
+	GType_MAKINGOF,
+	GType_RIVEN,
+	GType_CSTIME,
+	GType_LIVINGBOOKSV1,
+	GType_LIVINGBOOKSV2,
+	GType_LIVINGBOOKSV3,
+	GType_LIVINGBOOKSV4,
+	GType_LIVINGBOOKSV5
+};
+
+#define GAMEOPTION_ME   GUIO_GAMEOPTIONS1
+#define GAMEOPTION_25TH GUIO_GAMEOPTIONS2
+#define GAMEOPTION_DEMO GUIO_GAMEOPTIONS3
+
+enum MohawkGameFeatures {
+	GF_ME             = (1 << 0), // Myst Masterpiece Edition
+	GF_25TH           = (1 << 1), // Myst and Riven 25th Anniversary
+	GF_DVD            = (1 << 2),
+	GF_DEMO           = (1 << 3),
+	GF_LB_10          = (1 << 4)  // very early Living Books 1.0 games
+};
+
+} // End of namespace Mohawk
+
+#endif
diff --git a/engines/mohawk/mohawk.h b/engines/mohawk/mohawk.h
index 0f0ecaa7cf..55a0f667f4 100644
--- a/engines/mohawk/mohawk.h
+++ b/engines/mohawk/mohawk.h
@@ -28,6 +28,8 @@
 
 #include "engines/engine.h"
 
+#include "mohawk/detection_enums.h"
+
 class OSystem;
 
 namespace Common {
@@ -45,30 +47,6 @@ class SeekableReadStream;
  */
 namespace Mohawk {
 
-enum MohawkGameType {
-	GType_MYST,
-	GType_MAKINGOF,
-	GType_RIVEN,
-	GType_CSTIME,
-	GType_LIVINGBOOKSV1,
-	GType_LIVINGBOOKSV2,
-	GType_LIVINGBOOKSV3,
-	GType_LIVINGBOOKSV4,
-	GType_LIVINGBOOKSV5
-};
-
-#define GAMEOPTION_ME   GUIO_GAMEOPTIONS1
-#define GAMEOPTION_25TH GUIO_GAMEOPTIONS2
-#define GAMEOPTION_DEMO GUIO_GAMEOPTIONS3
-
-enum MohawkGameFeatures {
-	GF_ME             = (1 << 0), // Myst Masterpiece Edition
-	GF_25TH           = (1 << 1), // Myst and Riven 25th Anniversary
-	GF_DVD            = (1 << 2),
-	GF_DEMO           = (1 << 3),
-	GF_LB_10          = (1 << 4)  // very early Living Books 1.0 games
-};
-
 struct MohawkGameDescription;
 class Sound;
 class PauseDialog;


Commit: 52a420f4b18a35ec84eae35c11a4cf265d9c4d5d
    https://github.com/scummvm/scummvm/commit/52a420f4b18a35ec84eae35c11a4cf265d9c4d5d
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MOHAWK: Split detection features & adapt to new plugins.

Changed paths:
  A engines/mohawk/detection.h
  A engines/mohawk/metaengine.cpp
    configure
    engines/mohawk/detection.cpp
    engines/mohawk/module.mk


diff --git a/configure b/configure
index d7caff69b0..06d6594079 100755
--- a/configure
+++ b/configure
@@ -6170,7 +6170,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
 								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR"
-								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE" "SCI")
+								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE" "SCI" "MOHAWK")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/mohawk/detection.cpp b/engines/mohawk/detection.cpp
index baf03057b4..add3e96a9c 100644
--- a/engines/mohawk/detection.cpp
+++ b/engines/mohawk/detection.cpp
@@ -22,111 +22,22 @@
 
 #include "base/plugins.h"
 
-#include "backends/keymapper/action.h"
-#include "backends/keymapper/keymap.h"
-
 #include "engines/advancedDetector.h"
 #include "common/config-manager.h"
-#include "common/savefile.h"
-#include "common/system.h"
 #include "common/textconsole.h"
 #include "common/translation.h"
 
-#include "mohawk/dialogs.h"
-#include "mohawk/livingbooks.h"
-
-#ifdef ENABLE_CSTIME
-#include "mohawk/cstime.h"
-#endif
-
-#ifdef ENABLE_MYST
-#include "mohawk/myst.h"
-#include "mohawk/myst_state.h"
-#endif
-
-#ifdef ENABLE_MYSTME
-#ifndef ENABLE_MYST
-#error "Myst must be enabled for building Myst ME. Specify --enable-engine=myst,mystme"
-#endif
-#endif
+#include "mohawk/detection.h"
+#include "mohawk/detection_enums.h"
 
 #ifdef ENABLE_RIVEN
-#include "mohawk/riven.h"
-#include "mohawk/riven_saveload.h"
-#endif
-
-namespace Mohawk {
-
-struct MohawkGameDescription {
-	ADGameDescription desc;
-
-	uint8 gameType;
-	uint32 features;
-	const char *appName;
-};
-
-const char* MohawkEngine::getGameId() const {
-	return _gameDescription->desc.gameId;
-}
-
-uint32 MohawkEngine::getFeatures() const {
-	return _gameDescription->features;
-}
-
-bool MohawkEngine::isGameVariant(MohawkGameFeatures feature) const {
-	return (_gameDescription->features & feature) != 0;
-}
-
-Common::Platform MohawkEngine::getPlatform() const {
-	return _gameDescription->desc.platform;
-}
-
-const char *MohawkEngine::getAppName() const {
-	return _gameDescription->appName;
-}
-
-uint8 MohawkEngine::getGameType() const {
-	return _gameDescription->gameType;
-}
-
-Common::String MohawkEngine_LivingBooks::getBookInfoFileName() const {
-	return _gameDescription->desc.filesDescriptions[0].fileName;
-}
-
-Common::Language MohawkEngine::getLanguage() const {
-	return _gameDescription->desc.language;
-}
-
-bool MohawkEngine::hasFeature(EngineFeature f) const {
-	return
-		(f == kSupportsReturnToLauncher);
-}
+#include "mohawk/riven_metaengine/metaengine.h"
+#endif // ENABLE_RIVEN
 
 #ifdef ENABLE_MYST
+#include "mohawk/myst_metaengine/metaengine.h"
+#endif // ENABLE_MYST
 
-bool MohawkEngine_Myst::hasFeature(EngineFeature f) const {
-	return
-		MohawkEngine::hasFeature(f)
-	        || (f == kSupportsLoadingDuringRuntime)
-	        || (f == kSupportsSavingDuringRuntime)
-	        || (f == kSupportsChangingOptionsDuringRuntime);
-}
-
-#endif
-
-#ifdef ENABLE_RIVEN
-
-bool MohawkEngine_Riven::hasFeature(EngineFeature f) const {
-	return
-		MohawkEngine::hasFeature(f)
-	        || (f == kSupportsLoadingDuringRuntime)
-	        || (f == kSupportsSavingDuringRuntime)
-	        || (f == kSupportsChangingOptionsDuringRuntime);
-}
-
-#endif
-
-} // End of Namespace Mohawk
 
 static const PlainGameDescriptor mohawkGames[] = {
 	{"myst", "Myst"},
@@ -196,16 +107,7 @@ public:
 
 	DetectedGame toDetectedGame(const ADDetectedGame &adGame) const override;
 
-	bool hasFeature(MetaEngineFeature f) const override;
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	SaveStateList listSaves(const char *target) const override;
-	SaveStateList listSavesForPrefix(const char *prefix, const char *extension) const;
-	int getMaximumSaveSlot() const override { return 999; }
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-	Common::KeymapArray initKeymaps(const char *target) const override;
 	void registerDefaultSettings(const Common::String &target) const override;
-	GUI::OptionsContainerWidget *buildEngineOptionsWidget(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const override;
 };
 
 DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) const {
@@ -218,7 +120,7 @@ DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) cons
 	if (game.gameId == "myst"
 			&& Common::checkGameGUIOption(GAMEOPTION_25TH, game.getGUIOptions())
 			&& Common::checkGameGUIOption(GAMEOPTION_ME, game.getGUIOptions())) {
-		const Mohawk::MystLanguage *languages = Mohawk::MohawkEngine_Myst::listLanguages();
+		const Mohawk::MystLanguage *languages = Mohawk::MohawkMetaEngine_Myst::listLanguages();
 		while (languages->language != Common::UNK_LANG) {
 			game.appendGUIOptions(Common::getGameGUIOptionsDescriptionLanguage(languages->language));
 			languages++;
@@ -229,7 +131,7 @@ DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) cons
 #ifdef ENABLE_RIVEN
 	if (game.gameId == "riven"
 			&& Common::checkGameGUIOption(GAMEOPTION_25TH, game.getGUIOptions())) {
-		const Mohawk::RivenLanguage *languages = Mohawk::MohawkEngine_Riven::listLanguages();
+		const Mohawk::RivenLanguage *languages = Mohawk::MohawkMetaEngine_Riven::listLanguages();
 		while (languages->language != Common::UNK_LANG) {
 			game.appendGUIOptions(Common::getGameGUIOptionsDescriptionLanguage(languages->language));
 			languages++;
@@ -240,212 +142,21 @@ DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) cons
 	return game;
 }
 
-bool MohawkMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-		(f == kSupportsListSaves)
-		|| (f == kSupportsLoadingDuringStartup)
-		|| (f == kSupportsDeleteSave)
-		|| (f == kSavesSupportMetaInfo)
-		|| (f == kSavesSupportThumbnail)
-		|| (f == kSavesSupportCreationDate)
-		|| (f == kSavesSupportPlayTime);
-}
-
-SaveStateList MohawkMetaEngine::listSavesForPrefix(const char *prefix, const char *extension) const {
-	Common::String pattern = Common::String::format("%s-###.%s", prefix, extension);
-	Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
-	size_t prefixLen = strlen(prefix);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
-		// Extract the slot number from the filename
-		char slot[4];
-		slot[0] = (*filename)[prefixLen + 1];
-		slot[1] = (*filename)[prefixLen + 2];
-		slot[2] = (*filename)[prefixLen + 3];
-		slot[3] = '\0';
-
-		int slotNum = atoi(slot);
-
-		saveList.push_back(SaveStateDescriptor(slotNum, ""));
-	}
-
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-
-	return saveList;
-}
-
-SaveStateList MohawkMetaEngine::listSaves(const char *target) const {
-	Common::String gameId = ConfMan.get("gameid", target);
-	SaveStateList saveList;
-
-	// Loading games is only supported in Myst/Riven currently.
-#ifdef ENABLE_MYST
-	if (gameId == "myst") {
-		saveList = listSavesForPrefix("myst", "mys");
-
-		for (SaveStateList::iterator save = saveList.begin(); save != saveList.end(); ++save) {
-			// Read the description from the save
-			int slot = save->getSaveSlot();
-			Common::String description = Mohawk::MystGameState::querySaveDescription(slot);
-			save->setDescription(description);
-		}
-	}
-#endif
-#ifdef ENABLE_RIVEN
-	if (gameId == "riven") {
-		saveList = listSavesForPrefix("riven", "rvn");
-
-		for (SaveStateList::iterator save = saveList.begin(); save != saveList.end(); ++save) {
-			// Read the description from the save
-			int slot = save->getSaveSlot();
-			Common::String description = Mohawk::RivenSaveLoad::querySaveDescription(slot);
-			save->setDescription(description);
-		}
-	}
-#endif
-
-	return saveList;
-}
-
-void MohawkMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String gameId = ConfMan.get("gameid", target);
-
-	// Removing saved games is only supported in Myst/Riven currently.
-#ifdef ENABLE_MYST
-	if (gameId == "myst") {
-		Mohawk::MystGameState::deleteSave(slot);
-	}
-#endif
-#ifdef ENABLE_RIVEN
-	if (gameId == "riven") {
-		Mohawk::RivenSaveLoad::deleteSave(slot);
-	}
-#endif
-}
-
-SaveStateDescriptor MohawkMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String gameId = ConfMan.get("gameid", target);
-
-#ifdef ENABLE_MYST
-	if (gameId == "myst") {
-		return Mohawk::MystGameState::querySaveMetaInfos(slot);
-	}
-#endif
-#ifdef ENABLE_RIVEN
-	if (gameId == "riven") {
-		return Mohawk::RivenSaveLoad::querySaveMetaInfos(slot);
-	} else
-#endif
-	{
-		return SaveStateDescriptor();
-	}
-}
-
-Common::KeymapArray MohawkMetaEngine::initKeymaps(const char *target) const {
-	Common::String gameId = ConfMan.get("gameid", target);
-
-#ifdef ENABLE_MYST
-	if (gameId == "myst" || gameId == "makingofmyst") {
-		return Mohawk::MohawkEngine_Myst::initKeymaps(target);
-	}
-#endif
-#ifdef ENABLE_RIVEN
-	if (gameId == "riven") {
-		return Mohawk::MohawkEngine_Riven::initKeymaps(target);
-	}
-#endif
-
-	return AdvancedMetaEngine::initKeymaps(target);
-}
-
 void MohawkMetaEngine::registerDefaultSettings(const Common::String &target) const {
 	Common::String gameId = ConfMan.get("gameid", target);
 
 #ifdef ENABLE_MYST
 	if (gameId == "myst" || gameId == "makingofmyst") {
-		return Mohawk::MohawkEngine_Myst::registerDefaultSettings();
+		return Mohawk::MohawkMetaEngine_Myst::registerDefaultSettings();
 	}
 #endif
 #ifdef ENABLE_RIVEN
 	if (gameId == "riven") {
-		return Mohawk::MohawkEngine_Riven::registerDefaultSettings();
+		return Mohawk::MohawkMetaEngine_Riven::registerDefaultSettings();
 	}
 #endif
 
 	return AdvancedMetaEngine::registerDefaultSettings(target);
 }
 
-GUI::OptionsContainerWidget *MohawkMetaEngine::buildEngineOptionsWidget(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
-	Common::String gameId = ConfMan.get("gameid", target);
-
-#ifdef ENABLE_MYST
-	if (gameId == "myst" || gameId == "makingofmyst") {
-		return new Mohawk::MystOptionsWidget(boss, name, target);
-	}
-#endif
-#ifdef ENABLE_RIVEN
-	if (gameId == "riven") {
-		return new Mohawk::RivenOptionsWidget(boss, name, target);
-	}
-#endif
-
-	return AdvancedMetaEngine::buildEngineOptionsWidget(boss, name, target);
-}
-
-bool MohawkMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Mohawk::MohawkGameDescription *gd = (const Mohawk::MohawkGameDescription *)desc;
-
-	if (gd) {
-		switch (gd->gameType) {
-		case Mohawk::GType_MYST:
-		case Mohawk::GType_MAKINGOF:
-#ifdef ENABLE_MYST
-#ifndef ENABLE_MYSTME
-			if (gd->features & Mohawk::GF_ME) {
-				warning("Myst ME support not compiled in");
-				return false;
-			}
-#endif
-			*engine = new Mohawk::MohawkEngine_Myst(syst, gd);
-			break;
-#else
-			warning("Myst support not compiled in");
-			return false;
-#endif
-		case Mohawk::GType_RIVEN:
-#ifdef ENABLE_RIVEN
-			*engine = new Mohawk::MohawkEngine_Riven(syst, gd);
-			break;
-#else
-			warning("Riven support not compiled in");
-			return false;
-#endif
-		case Mohawk::GType_LIVINGBOOKSV1:
-		case Mohawk::GType_LIVINGBOOKSV2:
-		case Mohawk::GType_LIVINGBOOKSV3:
-		case Mohawk::GType_LIVINGBOOKSV4:
-		case Mohawk::GType_LIVINGBOOKSV5:
-			*engine = new Mohawk::MohawkEngine_LivingBooks(syst, gd);
-			break;
-		case Mohawk::GType_CSTIME:
-#ifdef ENABLE_CSTIME
-			*engine = new Mohawk::MohawkEngine_CSTime(syst, gd);
-			break;
-#else
-			warning("CSTime support not compiled in");
-			return false;
-#endif
-		default:
-			error("Unknown Mohawk Engine");
-		}
-	}
-
-	return (gd != nullptr);
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(MOHAWK)
-	REGISTER_PLUGIN_DYNAMIC(MOHAWK, PLUGIN_TYPE_ENGINE, MohawkMetaEngine);
-#else
-	REGISTER_PLUGIN_STATIC(MOHAWK, PLUGIN_TYPE_ENGINE, MohawkMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(MOHAWK_DETECTION, PLUGIN_TYPE_METAENGINE, MohawkMetaEngine);
diff --git a/engines/mohawk/detection.h b/engines/mohawk/detection.h
new file mode 100644
index 0000000000..aa9d2c96fc
--- /dev/null
+++ b/engines/mohawk/detection.h
@@ -0,0 +1,38 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef MOHAWK_DETECTION_H
+#define MOHAWK_DETECTION_H
+
+namespace Mohawk {
+
+struct MohawkGameDescription {
+	ADGameDescription desc;
+
+	uint8 gameType;
+	uint32 features;
+	const char *appName;
+};
+
+} // End of namespace Mohawk
+
+#endif
diff --git a/engines/mohawk/metaengine.cpp b/engines/mohawk/metaengine.cpp
new file mode 100644
index 0000000000..764e2d8c18
--- /dev/null
+++ b/engines/mohawk/metaengine.cpp
@@ -0,0 +1,333 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "backends/keymapper/action.h"
+#include "backends/keymapper/keymap.h"
+
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "engines/advancedDetector.h"
+
+#include "mohawk/mohawk.h"
+#include "mohawk/dialogs.h"
+#include "mohawk/livingbooks.h"
+
+#ifdef ENABLE_CSTIME
+#include "mohawk/cstime.h"
+#endif
+
+#ifdef ENABLE_MYST
+#include "mohawk/myst.h"
+#include "mohawk/myst_state.h"
+#endif
+
+#ifdef ENABLE_MYSTME
+#ifndef ENABLE_MYST
+#error "Myst must be enabled for building Myst ME. Specify --enable-engine=myst,mystme"
+#endif
+#endif
+
+#ifdef ENABLE_RIVEN
+#include "mohawk/riven.h"
+#include "mohawk/riven_saveload.h"
+#endif
+
+#include "mohawk/detection.h"
+
+namespace Mohawk {
+
+const char* MohawkEngine::getGameId() const {
+	return _gameDescription->desc.gameId;
+}
+
+uint32 MohawkEngine::getFeatures() const {
+	return _gameDescription->features;
+}
+
+bool MohawkEngine::isGameVariant(MohawkGameFeatures feature) const {
+	return (_gameDescription->features & feature) != 0;
+}
+
+Common::Platform MohawkEngine::getPlatform() const {
+	return _gameDescription->desc.platform;
+}
+
+const char *MohawkEngine::getAppName() const {
+	return _gameDescription->appName;
+}
+
+uint8 MohawkEngine::getGameType() const {
+	return _gameDescription->gameType;
+}
+
+Common::String MohawkEngine_LivingBooks::getBookInfoFileName() const {
+	return _gameDescription->desc.filesDescriptions[0].fileName;
+}
+
+Common::Language MohawkEngine::getLanguage() const {
+	return _gameDescription->desc.language;
+}
+
+bool MohawkEngine::hasFeature(EngineFeature f) const {
+	return
+		(f == kSupportsReturnToLauncher);
+}
+
+#ifdef ENABLE_MYST
+
+bool MohawkEngine_Myst::hasFeature(EngineFeature f) const {
+	return
+		MohawkEngine::hasFeature(f)
+	        || (f == kSupportsLoadingDuringRuntime)
+	        || (f == kSupportsSavingDuringRuntime)
+	        || (f == kSupportsChangingOptionsDuringRuntime);
+}
+
+#endif
+
+#ifdef ENABLE_RIVEN
+
+bool MohawkEngine_Riven::hasFeature(EngineFeature f) const {
+	return
+		MohawkEngine::hasFeature(f)
+	        || (f == kSupportsLoadingDuringRuntime)
+	        || (f == kSupportsSavingDuringRuntime)
+	        || (f == kSupportsChangingOptionsDuringRuntime);
+}
+
+#endif
+
+} // End of Namespace Mohawk
+
+class MohawkMetaEngineConnect : public AdvancedMetaEngineConnect {
+public:
+    const char *getName() const override {
+		return "mohawk";
+	}
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	SaveStateList listSavesForPrefix(const char *prefix, const char *extension) const;
+	int getMaximumSaveSlot() const override { return 999; }
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+
+	Common::KeymapArray initKeymaps(const char *target) const override;
+
+	GUI::OptionsContainerWidget *buildEngineOptionsWidgetDynamic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const override;
+};
+
+bool MohawkMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+		(f == kSupportsListSaves)
+		|| (f == kSupportsLoadingDuringStartup)
+		|| (f == kSupportsDeleteSave)
+		|| (f == kSavesSupportMetaInfo)
+		|| (f == kSavesSupportThumbnail)
+		|| (f == kSavesSupportCreationDate)
+		|| (f == kSavesSupportPlayTime);
+}
+
+SaveStateList MohawkMetaEngineConnect::listSavesForPrefix(const char *prefix, const char *extension) const {
+	Common::String pattern = Common::String::format("%s-###.%s", prefix, extension);
+	Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
+	size_t prefixLen = strlen(prefix);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator filename = filenames.begin(); filename != filenames.end(); ++filename) {
+		// Extract the slot number from the filename
+		char slot[4];
+		slot[0] = (*filename)[prefixLen + 1];
+		slot[1] = (*filename)[prefixLen + 2];
+		slot[2] = (*filename)[prefixLen + 3];
+		slot[3] = '\0';
+
+		int slotNum = atoi(slot);
+
+		saveList.push_back(SaveStateDescriptor(slotNum, ""));
+	}
+
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+
+	return saveList;
+}
+
+SaveStateList MohawkMetaEngineConnect::listSaves(const char *target) const {
+	Common::String gameId = ConfMan.get("gameid", target);
+	SaveStateList saveList;
+
+	// Loading games is only supported in Myst/Riven currently.
+#ifdef ENABLE_MYST
+	if (gameId == "myst") {
+		saveList = listSavesForPrefix("myst", "mys");
+
+		for (SaveStateList::iterator save = saveList.begin(); save != saveList.end(); ++save) {
+			// Read the description from the save
+			int slot = save->getSaveSlot();
+			Common::String description = Mohawk::MystGameState::querySaveDescription(slot);
+			save->setDescription(description);
+		}
+	}
+#endif
+#ifdef ENABLE_RIVEN
+	if (gameId == "riven") {
+		saveList = listSavesForPrefix("riven", "rvn");
+
+		for (SaveStateList::iterator save = saveList.begin(); save != saveList.end(); ++save) {
+			// Read the description from the save
+			int slot = save->getSaveSlot();
+			Common::String description = Mohawk::RivenSaveLoad::querySaveDescription(slot);
+			save->setDescription(description);
+		}
+	}
+#endif
+
+	return saveList;
+}
+
+void MohawkMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String gameId = ConfMan.get("gameid", target);
+
+	// Removing saved games is only supported in Myst/Riven currently.
+#ifdef ENABLE_MYST
+	if (gameId == "myst") {
+		Mohawk::MystGameState::deleteSave(slot);
+	}
+#endif
+#ifdef ENABLE_RIVEN
+	if (gameId == "riven") {
+		Mohawk::RivenSaveLoad::deleteSave(slot);
+	}
+#endif
+}
+
+SaveStateDescriptor MohawkMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String gameId = ConfMan.get("gameid", target);
+
+#ifdef ENABLE_MYST
+	if (gameId == "myst") {
+		return Mohawk::MystGameState::querySaveMetaInfos(slot);
+	}
+#endif
+#ifdef ENABLE_RIVEN
+	if (gameId == "riven") {
+		return Mohawk::RivenSaveLoad::querySaveMetaInfos(slot);
+	} else
+#endif
+	{
+		return SaveStateDescriptor();
+	}
+}
+
+Common::KeymapArray MohawkMetaEngineConnect::initKeymaps(const char *target) const {
+	Common::String gameId = ConfMan.get("gameid", target);
+
+#ifdef ENABLE_MYST
+	if (gameId == "myst" || gameId == "makingofmyst") {
+		return Mohawk::MohawkEngine_Myst::initKeymaps(target);
+	}
+#endif
+#ifdef ENABLE_RIVEN
+	if (gameId == "riven") {
+		return Mohawk::MohawkEngine_Riven::initKeymaps(target);
+	}
+#endif
+
+	return AdvancedMetaEngineConnect::initKeymaps(target);
+}
+
+bool MohawkMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Mohawk::MohawkGameDescription *gd = (const Mohawk::MohawkGameDescription *)desc;
+
+	if (gd) {
+		switch (gd->gameType) {
+		case Mohawk::GType_MYST:
+		case Mohawk::GType_MAKINGOF:
+#ifdef ENABLE_MYST
+#ifndef ENABLE_MYSTME
+			if (gd->features & Mohawk::GF_ME) {
+				warning("Myst ME support not compiled in");
+				return false;
+			}
+#endif
+			*engine = new Mohawk::MohawkEngine_Myst(syst, gd);
+			break;
+#else
+			warning("Myst support not compiled in");
+			return false;
+#endif
+		case Mohawk::GType_RIVEN:
+#ifdef ENABLE_RIVEN
+			*engine = new Mohawk::MohawkEngine_Riven(syst, gd);
+			break;
+#else
+			warning("Riven support not compiled in");
+			return false;
+#endif
+		case Mohawk::GType_LIVINGBOOKSV1:
+		case Mohawk::GType_LIVINGBOOKSV2:
+		case Mohawk::GType_LIVINGBOOKSV3:
+		case Mohawk::GType_LIVINGBOOKSV4:
+		case Mohawk::GType_LIVINGBOOKSV5:
+			*engine = new Mohawk::MohawkEngine_LivingBooks(syst, gd);
+			break;
+		case Mohawk::GType_CSTIME:
+#ifdef ENABLE_CSTIME
+			*engine = new Mohawk::MohawkEngine_CSTime(syst, gd);
+			break;
+#else
+			warning("CSTime support not compiled in");
+			return false;
+#endif
+		default:
+			error("Unknown Mohawk Engine");
+		}
+	}
+
+	return (gd != nullptr);
+}
+
+GUI::OptionsContainerWidget *MohawkMetaEngineConnect::buildEngineOptionsWidgetDynamic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
+	Common::String gameId = ConfMan.get("gameid", target);
+
+#ifdef ENABLE_MYST
+	if (gameId == "myst" || gameId == "makingofmyst") {
+		return new Mohawk::MystOptionsWidget(boss, name, target);
+	}
+#endif
+#ifdef ENABLE_RIVEN
+	if (gameId == "riven") {
+		return new Mohawk::RivenOptionsWidget(boss, name, target);
+	}
+#endif
+
+	return MetaEngineConnect::buildEngineOptionsWidgetDynamic(boss, name, target);
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(MOHAWK)
+	REGISTER_PLUGIN_DYNAMIC(MOHAWK, PLUGIN_TYPE_ENGINE, MohawkMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(MOHAWK, PLUGIN_TYPE_ENGINE, MohawkMetaEngineConnect);
+#endif
diff --git a/engines/mohawk/module.mk b/engines/mohawk/module.mk
index e76b1aefaf..c0444fadda 100644
--- a/engines/mohawk/module.mk
+++ b/engines/mohawk/module.mk
@@ -4,7 +4,6 @@ MODULE_OBJS = \
 	bitmap.o \
 	console.o \
 	cursors.o \
-	detection.o \
 	dialogs.o \
 	graphics.o \
 	installer_archive.o \
@@ -12,6 +11,7 @@ MODULE_OBJS = \
 	livingbooks_code.o \
 	livingbooks_graphics.o \
 	livingbooks_lbx.o \
+	metaengine.o \
 	mohawk.o \
 	resource.o \
 	sound.o \
@@ -30,6 +30,7 @@ endif
 
 ifdef ENABLE_MYST
 MODULE_OBJS += \
+	myst_metaengine/metaengine.o \
 	myst.o \
 	myst_areas.o \
 	myst_card.o \
@@ -55,6 +56,7 @@ endif
 
 ifdef ENABLE_RIVEN
 MODULE_OBJS += \
+	riven_metaengine/metaengine.o \
 	riven.o \
 	riven_card.o \
 	riven_graphics.o \
@@ -83,3 +85,21 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# If we're building a dynamic module, build the relevant
+# submodule. A static part already will have these, so
+# no need to add them again.
+ifeq ($(ENABLE_MOHAWK), DYNAMIC_PLUGIN)
+
+ifdef ENABLE_MYST
+DETECT_OBJS += $(MODULE)/myst_metaengine/metaengine.o
+endif
+
+ifdef ENABLE_RIVEN
+DETECT_OBJS += $(MODULE)/riven_metaengine/metaengine.o
+endif
+
+endif


Commit: 53c772aebbf79a6b4c1db04f7b1671a0facb30f7
    https://github.com/scummvm/scummvm/commit/53c772aebbf79a6b4c1db04f7b1671a0facb30f7
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ULTIMA: Split detection features & adapt to new plugins.

Changed paths:
  A engines/ultima/metaengine.cpp
  A engines/ultima/metaengine.h
    configure
    engines/ultima/detection.cpp
    engines/ultima/detection.h
    engines/ultima/module.mk
    engines/ultima/nuvie/files/nuvie_io_file.cpp
    engines/ultima/ultima8/filesys/savegame.cpp
    engines/ultima/ultima8/ultima8.cpp


diff --git a/configure b/configure
index 06d6594079..3f9c61f8dd 100755
--- a/configure
+++ b/configure
@@ -6170,7 +6170,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
 								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR"
-								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE" "SCI" "MOHAWK")
+								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE" "SCI" "MOHAWK" "ULTIMA")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/ultima/detection.cpp b/engines/ultima/detection.cpp
index 2b35be3da8..8f62f6fe46 100644
--- a/engines/ultima/detection.cpp
+++ b/engines/ultima/detection.cpp
@@ -20,20 +20,9 @@
  *
  */
 
-#include "ultima/detection.h"
 #include "base/plugins.h"
-#include "common/system.h"
-#include "common/config-manager.h"
-#include "common/savefile.h"
-#include "common/str-array.h"
-#include "common/memstream.h"
-#include "ultima/shared/early/ultima_early.h"
-#include "ultima/ultima4/ultima4.h"
-#include "ultima/ultima4/meta_engine.h"
-#include "ultima/nuvie/meta_engine.h"
-#include "ultima/nuvie/nuvie.h"
-#include "ultima/ultima8/ultima8.h"
-#include "ultima/ultima8/meta_engine.h"
+
+#include "ultima/detection.h"
 
 namespace Ultima {
 
@@ -67,75 +56,4 @@ UltimaMetaEngine::UltimaMetaEngine() : AdvancedMetaEngine(Ultima::GAME_DESCRIPTI
 	_directoryGlobs = DIRECTORY_GLOBS;
 }
 
-bool UltimaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
-	const Ultima::UltimaGameDescription *gd = (const Ultima::UltimaGameDescription *)desc;
-	if (gd) {
-		switch (gd->gameId) {
-#ifndef RELEASE_BUILD
-		case Ultima::GAME_ULTIMA1:
-			*engine = new Ultima::Shared::UltimaEarlyEngine(syst, gd);
-			break;
-#endif
-		case Ultima::GAME_ULTIMA4:
-			*engine = new Ultima::Ultima4::Ultima4Engine(syst, gd);
-			break;
-		case Ultima::GAME_ULTIMA6:
-		case Ultima::GAME_MARTIAN_DREAMS:
-		case Ultima::GAME_SAVAGE_EMPIRE:
-			*engine = new Ultima::Nuvie::NuvieEngine(syst, gd);
-			break;
-		case Ultima::GAME_ULTIMA8:
-		case Ultima::GAME_CRUSADER_REG:
-		case Ultima::GAME_CRUSADER_REM:
-			*engine = new Ultima::Ultima8::Ultima8Engine(syst, gd);
-			break;
-
-		default:
-			error("Unsupported ultima engine game specified");
-		}
-	}
-	return gd != 0;
-}
-
-int UltimaMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVES;
-}
-
-SaveStateList UltimaMetaEngine::listSaves(const char *target) const {
-	SaveStateList saveList = AdvancedMetaEngine::listSaves(target);
-
-	Common::String gameId = getGameId(target);
-	if (gameId == "ultima6" || gameId == "ultima6_enh")
-		Ultima::Nuvie::MetaEngine::listSaves(saveList);
-
-	return saveList;
-}
-
-Common::KeymapArray UltimaMetaEngine::initKeymaps(const char *target) const {
-	const Common::String gameId = getGameId(target);
-	if (gameId == "ultima4" || gameId == "ultima4_enh")
-		return Ultima::Ultima4::MetaEngine::initKeymaps();
-	if (gameId == "ultima8" || gameId == "remorse" || gameId == "regret")
-		return Ultima::Ultima8::MetaEngine::initKeymaps(gameId);
-
-	return Common::KeymapArray();
-}
-
-Common::String UltimaMetaEngine::getGameId(const char *target) {
-	// Store a copy of the active domain
-	Common::String currDomain = ConfMan.getActiveDomainName();
-
-	// Switch to the given target domain and get it's game Id
-	ConfMan.setActiveDomain(target);
-	Common::String gameId = ConfMan.get("gameid");
-
-	// Switch back to the original domain and return the game Id
-	ConfMan.setActiveDomain(currDomain);
-	return gameId;
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(ULTIMA)
-REGISTER_PLUGIN_DYNAMIC(ULTIMA, PLUGIN_TYPE_ENGINE, UltimaMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(ULTIMA, PLUGIN_TYPE_ENGINE, UltimaMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(ULTIMA_DETECTION, PLUGIN_TYPE_METAENGINE, UltimaMetaEngine);
diff --git a/engines/ultima/detection.h b/engines/ultima/detection.h
index a64459d1a9..388d2fb5b2 100644
--- a/engines/ultima/detection.h
+++ b/engines/ultima/detection.h
@@ -24,9 +24,6 @@
 #define ULTIMA_DETECTION
 
 #include "engines/advancedDetector.h"
-#include "backends/keymapper/keymapper.h"
-
-#define MAX_SAVES 99
 
 namespace Ultima {
 
@@ -62,11 +59,6 @@ struct UltimaGameDescription {
 } // End of namespace Ultima
 
 class UltimaMetaEngine : public AdvancedMetaEngine {
-private:
-	/**
-	 * Gets the game Id given a target string
-	 */
-	static Common::String getGameId(const char *target);
 public:
 	UltimaMetaEngine();
 	~UltimaMetaEngine() override {}
@@ -82,19 +74,6 @@ public:
 	const char *getOriginalCopyright() const override {
 		return "Ultima Games (C) 1980-1995 Origin Systems Inc.";
 	}
-
-	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
-	int getMaximumSaveSlot() const override;
-
-	/**
-	 * Return a list of all save states associated with the given target.
-	 */
-	SaveStateList listSaves(const char *target) const override;
-
-	/**
-	 * Initialize keymaps
-	 */
-	Common::KeymapArray initKeymaps(const char *target) const override;
 };
 
 #endif
diff --git a/engines/ultima/metaengine.cpp b/engines/ultima/metaengine.cpp
new file mode 100644
index 0000000000..84aae06901
--- /dev/null
+++ b/engines/ultima/metaengine.cpp
@@ -0,0 +1,115 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "ultima/detection.h"
+#include "base/plugins.h"
+#include "common/system.h"
+#include "common/config-manager.h"
+#include "common/savefile.h"
+#include "common/str-array.h"
+#include "common/memstream.h"
+#include "ultima/shared/early/ultima_early.h"
+#include "ultima/ultima4/ultima4.h"
+#include "ultima/ultima4/meta_engine.h"
+#include "ultima/nuvie/meta_engine.h"
+#include "ultima/nuvie/nuvie.h"
+#include "ultima/ultima8/ultima8.h"
+#include "ultima/ultima8/meta_engine.h"
+
+#include "ultima/metaengine.h"
+
+const char *UltimaMetaEngineConnect::getName() const {
+	return "ultima";
+}
+
+bool UltimaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+	const Ultima::UltimaGameDescription *gd = (const Ultima::UltimaGameDescription *)desc;
+	if (gd) {
+		switch (gd->gameId) {
+#ifndef RELEASE_BUILD
+		case Ultima::GAME_ULTIMA1:
+			*engine = new Ultima::Shared::UltimaEarlyEngine(syst, gd);
+			break;
+#endif
+		case Ultima::GAME_ULTIMA4:
+			*engine = new Ultima::Ultima4::Ultima4Engine(syst, gd);
+			break;
+		case Ultima::GAME_ULTIMA6:
+		case Ultima::GAME_MARTIAN_DREAMS:
+		case Ultima::GAME_SAVAGE_EMPIRE:
+			*engine = new Ultima::Nuvie::NuvieEngine(syst, gd);
+			break;
+		case Ultima::GAME_ULTIMA8:
+		case Ultima::GAME_CRUSADER_REG:
+		case Ultima::GAME_CRUSADER_REM:
+			*engine = new Ultima::Ultima8::Ultima8Engine(syst, gd);
+			break;
+
+		default:
+			error("Unsupported ultima engine game specified");
+		}
+	}
+	return gd != 0;
+}
+
+int UltimaMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVES;
+}
+
+SaveStateList UltimaMetaEngineConnect::listSaves(const char *target) const {
+	SaveStateList saveList = AdvancedMetaEngineConnect::listSaves(target);
+
+	Common::String gameId = getGameId(target);
+	if (gameId == "ultima6" || gameId == "ultima6_enh")
+		Ultima::Nuvie::MetaEngine::listSaves(saveList);
+
+	return saveList;
+}
+
+Common::KeymapArray UltimaMetaEngineConnect::initKeymaps(const char *target) const {
+	const Common::String gameId = getGameId(target);
+	if (gameId == "ultima4" || gameId == "ultima4_enh")
+		return Ultima::Ultima4::MetaEngine::initKeymaps();
+	if (gameId == "ultima8" || gameId == "remorse" || gameId == "regret")
+		return Ultima::Ultima8::MetaEngine::initKeymaps(gameId);
+
+	return Common::KeymapArray();
+}
+
+Common::String UltimaMetaEngineConnect::getGameId(const char *target) {
+	// Store a copy of the active domain
+	Common::String currDomain = ConfMan.getActiveDomainName();
+
+	// Switch to the given target domain and get it's game Id
+	ConfMan.setActiveDomain(target);
+	Common::String gameId = ConfMan.get("gameid");
+
+	// Switch back to the original domain and return the game Id
+	ConfMan.setActiveDomain(currDomain);
+	return gameId;
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(ULTIMA)
+	REGISTER_PLUGIN_DYNAMIC(ULTIMA, PLUGIN_TYPE_ENGINE, UltimaMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(ULTIMA, PLUGIN_TYPE_ENGINE, UltimaMetaEngineConnect);
+#endif
diff --git a/engines/ultima/metaengine.h b/engines/ultima/metaengine.h
new file mode 100644
index 0000000000..0dc0756141
--- /dev/null
+++ b/engines/ultima/metaengine.h
@@ -0,0 +1,55 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef ULTIMA_METAENGINE_H
+#define ULTIMA_METAENGINE_H
+
+#include "engines/advancedDetector.h"
+#include "common/system.h"
+
+#define MAX_SAVES 99
+
+class UltimaMetaEngineConnect : public AdvancedMetaEngineConnect {
+private:
+	/**
+	 * Gets the game Id given a target string
+	 */
+	static Common::String getGameId(const char *target);
+public:
+	const char *getName() const override;
+
+	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
+	int getMaximumSaveSlot() const override;
+
+	/**
+	 * Return a list of all save states associated with the given target.
+	 */
+	SaveStateList listSaves(const char *target) const override;
+
+	/**
+	 * Initialize keymaps
+	 */
+	Common::KeymapArray initKeymaps(const char *target) const override;
+
+};
+
+#endif
diff --git a/engines/ultima/module.mk b/engines/ultima/module.mk
index 200809d838..59822cf863 100644
--- a/engines/ultima/module.mk
+++ b/engines/ultima/module.mk
@@ -1,7 +1,7 @@
 MODULE := engines/ultima
 
 MODULE_OBJS := \
-	detection.o \
+	metaengine.o \
 	shared/actions/action.o \
 	shared/actions/huh.o \
 	shared/actions/pass.o \
@@ -591,3 +591,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/ultima/nuvie/files/nuvie_io_file.cpp b/engines/ultima/nuvie/files/nuvie_io_file.cpp
index 5acfe4fa5b..b8f0fa1357 100644
--- a/engines/ultima/nuvie/files/nuvie_io_file.cpp
+++ b/engines/ultima/nuvie/files/nuvie_io_file.cpp
@@ -164,7 +164,7 @@ void NuvieIOFileWrite::close() {
 	} else if (_saveFile) {
 		// Writing using savefile interface, so flush out data
 		_saveFile->write(_saveFileData.getData(), _saveFileData.size());
-		MetaEngine::appendExtendedSave(_saveFile, Shared::g_ultima->getTotalPlayTime(), _description, _isAutosave);
+		MetaEngineConnect::appendExtendedSave(_saveFile, Shared::g_ultima->getTotalPlayTime(), _description, _isAutosave);
 
 		_saveFile->finalize();
 		delete _saveFile;
diff --git a/engines/ultima/ultima8/filesys/savegame.cpp b/engines/ultima/ultima8/filesys/savegame.cpp
index 58e506e266..8e5a5e1dd2 100644
--- a/engines/ultima/ultima8/filesys/savegame.cpp
+++ b/engines/ultima/ultima8/filesys/savegame.cpp
@@ -36,7 +36,7 @@ namespace Ultima8 {
 #define SAVEGAME_VERSION 5
 
 SavegameReader::SavegameReader(Common::SeekableReadStream *rs, bool metadataOnly) : _file(rs), _version(0) {
-	if (!MetaEngine::readSavegameHeader(rs, &_header))
+	if (!MetaEngineConnect::readSavegameHeader(rs, &_header))
 		return;
 
 	// Validate the identifier for a valid savegame
diff --git a/engines/ultima/ultima8/ultima8.cpp b/engines/ultima/ultima8/ultima8.cpp
index 88be4868eb..d11a899ab8 100644
--- a/engines/ultima/ultima8/ultima8.cpp
+++ b/engines/ultima/ultima8/ultima8.cpp
@@ -1105,7 +1105,7 @@ bool Ultima8Engine::newGame(int saveSlot) {
 
 	// First validate we still have a save file for the slot
 	if (saveSlot != -1) {
-		SaveStateDescriptor desc = getMetaEngine().querySaveMetaInfos(_targetName.c_str(), saveSlot);
+		SaveStateDescriptor desc = getMetaEngineConnect().querySaveMetaInfos(_targetName.c_str(), saveSlot);
 		if (desc.getSaveSlot() != saveSlot)
 			saveSlot = -1;
 	}


Commit: 27d16ba9c5a32020b3e038db60f791ae03ebc152
    https://github.com/scummvm/scummvm/commit/27d16ba9c5a32020b3e038db60f791ae03ebc152
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GLK: Move game-description struct into a header file from glk.h.

Changed paths:
  A engines/glk/game_description.h
    engines/glk/glk.h


diff --git a/engines/glk/game_description.h b/engines/glk/game_description.h
new file mode 100644
index 0000000000..bebc497e33
--- /dev/null
+++ b/engines/glk/game_description.h
@@ -0,0 +1,39 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef GLK_GAME_DESCRIPTION_H
+#define GLK_GAME_DESCRIPTION_H
+
+namespace Glk {
+
+struct GlkGameDescription {
+	Common::String _gameId;
+	Common::Language _language;
+	Common::Platform _platform;
+	Common::String _filename;
+	Common::String _md5;
+	uint _options;
+};
+
+} // End of namespace Glk
+
+#endif
diff --git a/engines/glk/glk.h b/engines/glk/glk.h
index dae30548ad..1bbae76ca4 100644
--- a/engines/glk/glk.h
+++ b/engines/glk/glk.h
@@ -32,6 +32,7 @@
 #include "glk/streams.h"
 #include "glk/pc_speaker.h"
 #include "glk/quetzal.h"
+#include "glk/game_description.h"
 
 namespace Glk {
 
@@ -57,15 +58,6 @@ enum GlkDebugChannels {
 
 #define GLK_SAVEGAME_VERSION 1
 
-struct GlkGameDescription {
-	Common::String _gameId;
-	Common::Language _language;
-	Common::Platform _platform;
-	Common::String _filename;
-	Common::String _md5;
-	uint _options;
-};
-
 /**
  * Base class for the different interpreters
  */


Commit: 92839dce1c5da1987c2424ccba5635cd99ac8f5a
    https://github.com/scummvm/scummvm/commit/92839dce1c5da1987c2424ccba5635cd99ac8f5a
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GLK: Split detection features & adapt to new plugins.

- Additionally, adapt to renaming glulxe -> glulx

Changed paths:
  A engines/glk/metaengine.cpp
    configure
    engines/glk/detection.cpp
    engines/glk/detection.h
    engines/glk/module.mk


diff --git a/configure b/configure
index 3f9c61f8dd..e4c8c3f1c9 100755
--- a/configure
+++ b/configure
@@ -6170,7 +6170,7 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
 								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
 								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR"
-								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE" "SCI" "MOHAWK" "ULTIMA")
+								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE" "SCI" "MOHAWK" "ULTIMA" "GLK")
 detectId="_DETECTION"
 
 echo "Creating engines/plugins_table.h"
diff --git a/engines/glk/detection.cpp b/engines/glk/detection.cpp
index c18acd02a9..eb081845ba 100644
--- a/engines/glk/detection.cpp
+++ b/engines/glk/detection.cpp
@@ -20,44 +20,35 @@
  *
  */
 
-#include "glk/glk.h"
+#include "base/plugins.h"
+#include "common/md5.h"
+#include "common/memstream.h"
+#include "common/str-array.h"
+#include "common/file.h"
+#include "common/translation.h"
+#include "common/config-manager.h"
+
 #include "glk/detection.h"
-#include "glk/quetzal.h"
+#include "glk/game_description.h"
+
 #include "glk/adrift/detection.h"
-#include "glk/adrift/adrift.h"
 #include "glk/advsys/detection.h"
-#include "glk/advsys/advsys.h"
 #include "glk/agt/detection.h"
-#include "glk/agt/agt.h"
 #include "glk/alan2/detection.h"
-#include "glk/alan2/alan2.h"
 #include "glk/alan3/detection.h"
-#include "glk/alan3/alan3.h"
-#include "glk/archetype/archetype.h"
 #include "glk/archetype/detection.h"
 #include "glk/zcode/detection.h"
-#include "glk/zcode/zcode.h"
 #include "glk/hugo/detection.h"
-#include "glk/hugo/hugo.h"
 #include "glk/jacl/detection.h"
-#include "glk/jacl/jacl.h"
 #include "glk/level9/detection.h"
-#include "glk/level9/level9.h"
 #include "glk/magnetic/detection.h"
-#include "glk/magnetic/magnetic.h"
 #include "glk/quest/detection.h"
-#include "glk/quest/quest.h"
 #include "glk/scott/detection.h"
-#include "glk/scott/scott.h"
 
 #ifndef RELEASE_BUILD
-#include "glk/comprehend/comprehend.h"
 #include "glk/comprehend/detection.h"
 #include "glk/glulx/detection.h"
-#include "glk/glulx/glulx.h"
 #include "glk/tads/detection.h"
-#include "glk/tads/tads2/tads2.h"
-#include "glk/tads/tads3/tads3.h"
 #endif
 
 #include "base/plugins.h"
@@ -123,144 +114,6 @@ GlkDetectedGame::GlkDetectedGame(const char *id, const char *desc, const Common:
 
 } // End of namespace Glk
 
-bool GlkMetaEngine::hasFeature(MetaEngineFeature f) const {
-	return
-	    (f == kSupportsListSaves) ||
-	    (f == kSupportsLoadingDuringStartup) ||
-	    (f == kSupportsDeleteSave) ||
-	    (f == kSavesSupportMetaInfo) ||
-	    (f == kSavesSupportCreationDate) ||
-	    (f == kSavesSupportPlayTime) ||
-	    (f == kSimpleSavesNames);
-}
-
-bool Glk::GlkEngine::hasFeature(EngineFeature f) const {
-	return
-	    (f == kSupportsReturnToLauncher) ||
-	    (f == kSupportsLoadingDuringRuntime) ||
-	    (f == kSupportsSavingDuringRuntime);
-}
-
-bool isGameAllowed(GameSupportLevel supportLevel) {
-	bool showTestingWarning = false;
-#ifdef RELEASE_BUILD
-	showTestingWarning = true;
-#endif
-
-	if (((supportLevel == kUnstableGame
-		|| (supportLevel == kTestingGame && showTestingWarning)))
-		&& !Engine::warnUserAboutUnsupportedGame())
-		return false;
-
-	return true;
-}
-
-template<class META, class ENG>bool create(OSystem *syst,
-		Glk::GlkGameDescription &gameDesc, Engine *&engine) {
-
-	Glk::GameDescriptor gd = META::findGame(gameDesc._gameId.c_str());
-	if (gd._description) {
-		if (!isGameAllowed(gd._supportLevel))
-			return true;
-
-		gameDesc._options = gd._options;
-		engine = new ENG(syst, gameDesc);
-		return true;
-	} else {
-		return false;
-	}
-}
-
-Common::Error GlkMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
-#ifndef RELEASE_BUILD
-	Glk::GameDescriptor td = Glk::GameDescriptor::empty();
-#endif
-	assert(engine);
-
-	// Populate the game description
-	Glk::GlkGameDescription gameDesc;
-	gameDesc._gameId = ConfMan.get("gameid");
-	gameDesc._filename = ConfMan.get("filename");
-
-	gameDesc._language = Common::UNK_LANG;
-	gameDesc._platform = Common::kPlatformUnknown;
-	if (ConfMan.hasKey("language"))
-		gameDesc._language = Common::parseLanguage(ConfMan.get("language"));
-	if (ConfMan.hasKey("platform"))
-		gameDesc._platform = Common::parsePlatform(ConfMan.get("platform"));
-
-	// If the game description has no filename, the engine has been launched directly from
-	// the command line. Do a scan for supported games for that Id in the game folder
-	if (gameDesc._filename.empty()) {
-		gameDesc._filename = findFileByGameId(gameDesc._gameId);
-		if (gameDesc._filename.empty())
-			return Common::kNoGameDataFoundError;
-	}
-
-	// Get the MD5
-	Common::File f;
-	if (!f.open(Common::FSNode(ConfMan.get("path")).getChild(gameDesc._filename)))
-		return Common::kNoGameDataFoundError;
-
-	gameDesc._md5 = Common::computeStreamMD5AsString(f, 5000);
-	f.close();
-
-	// Create the correct engine
-	*engine = nullptr;
-	if ((create<Glk::Adrift::AdriftMetaEngine, Glk::Adrift::Adrift>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::AdvSys::AdvSysMetaEngine, Glk::AdvSys::AdvSys>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::AGT::AGTMetaEngine, Glk::AGT::AGT>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::Alan2::Alan2MetaEngine, Glk::Alan2::Alan2>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::Alan3::Alan3MetaEngine, Glk::Alan3::Alan3>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::Archetype::ArchetypeMetaEngine, Glk::Archetype::Archetype>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::Hugo::HugoMetaEngine, Glk::Hugo::Hugo>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::JACL::JACLMetaEngine, Glk::JACL::JACL>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::Level9::Level9MetaEngine, Glk::Level9::Level9>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::Magnetic::MagneticMetaEngine, Glk::Magnetic::Magnetic>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::Quest::QuestMetaEngine, Glk::Quest::Quest>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::Scott::ScottMetaEngine, Glk::Scott::Scott>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::ZCode::ZCodeMetaEngine, Glk::ZCode::ZCode>(syst, gameDesc, *engine))) {}
-#ifndef RELEASE_BUILD
-	else if ((create<Glk::Comprehend::ComprehendMetaEngine, Glk::Comprehend::Comprehend>(syst, gameDesc, *engine))) {}
-	else if ((create<Glk::Glulx::GlulxMetaEngine, Glk::Glulx::Glulx>(syst, gameDesc, *engine))) {}
-	else if ((td = Glk::TADS::TADSMetaEngine::findGame(gameDesc._gameId.c_str()))._description) {
-		if (!isGameAllowed(td._supportLevel))
-			return Common::kUserCanceled;
-		else if (td._options & Glk::TADS::OPTION_TADS3)
-			new Glk::TADS::TADS3::TADS3(syst, gameDesc);
-		else
-			new Glk::TADS::TADS2::TADS2(syst, gameDesc);
-	}
-#endif
-	else {
-		return Common::kNoGameDataFoundError;
-	}
-
-	return *engine ? Common::kNoError : Common::kUserCanceled;
-}
-
-Common::String GlkMetaEngine::findFileByGameId(const Common::String &gameId) const {
-	// Get the list of files in the folder and return detection against them
-	Common::FSNode folder = Common::FSNode(ConfMan.get("path"));
-	Common::FSList fslist;
-	folder.getChildren(fslist, Common::FSNode::kListFilesOnly);
-
-	// Iterate over the files
-	for (Common::FSList::iterator i = fslist.begin(); i != fslist.end(); ++i) {
-		// Run a detection on each file in the folder individually
-		Common::FSList singleList;
-		singleList.push_back(*i);
-		DetectedGames games = detectGames(singleList);
-
-		// If a detection was found with the correct game Id, we have a winner
-		if (!games.empty() && games.front().gameId == gameId)
-			return (*i).getName();
-	}
-
-	// No match found
-	return Common::String();
-}
-
 PlainGameList GlkMetaEngine::getSupportedGames() const {
 	PlainGameList list;
 	Glk::Adrift::AdriftMetaEngine::getSupportedGames(list);
@@ -384,66 +237,4 @@ const ExtraGuiOptions GlkMetaEngine::getExtraGuiOptions(const Common::String &)
 	return options;
 }
 
-SaveStateList GlkMetaEngine::listSaves(const char *target) const {
-	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
-	Common::StringArray filenames;
-	Common::String saveDesc;
-	Common::String pattern = Common::String::format("%s.0##", target);
-
-	filenames = saveFileMan->listSavefiles(pattern);
-
-	SaveStateList saveList;
-	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
-		const char *ext = strrchr(file->c_str(), '.');
-		int slot = ext ? atoi(ext + 1) : -1;
-
-		if (slot >= 0 && slot <= MAX_SAVES) {
-			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
-
-			if (in) {
-				Common::String saveName;
-				if (Glk::QuetzalReader::getSavegameDescription(in, saveName))
-					saveList.push_back(SaveStateDescriptor(slot, saveName));
-
-				delete in;
-			}
-		}
-	}
-
-	// Sort saves based on slot number.
-	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
-	return saveList;
-}
-
-int GlkMetaEngine::getMaximumSaveSlot() const {
-	return MAX_SAVES;
-}
-
-void GlkMetaEngine::removeSaveState(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	g_system->getSavefileManager()->removeSavefile(filename);
-}
-
-SaveStateDescriptor GlkMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
-	Common::String filename = Common::String::format("%s.%03d", target, slot);
-	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename);
-	SaveStateDescriptor ssd;
-	bool result = false;
-
-	if (in) {
-		result = Glk::QuetzalReader::getSavegameMetaInfo(in, ssd);
-		ssd.setSaveSlot(slot);
-		delete in;
-	}
-
-	if (result)
-		return ssd;
-
-	return SaveStateDescriptor();
-}
-
-#if PLUGIN_ENABLED_DYNAMIC(GLK)
-REGISTER_PLUGIN_DYNAMIC(GLK, PLUGIN_TYPE_ENGINE, GlkMetaEngine);
-#else
-REGISTER_PLUGIN_STATIC(GLK, PLUGIN_TYPE_ENGINE, GlkMetaEngine);
-#endif
+REGISTER_PLUGIN_STATIC(GLK_DETECTION, PLUGIN_TYPE_METAENGINE, GlkMetaEngine);
diff --git a/engines/glk/detection.h b/engines/glk/detection.h
index 7ce50bc5b4..e1e97e4001 100644
--- a/engines/glk/detection.h
+++ b/engines/glk/detection.h
@@ -26,14 +26,10 @@
 #include "engines/advancedDetector.h"
 #include "engines/game.h"
 
-#define MAX_SAVES 99
-
 /**
  * ScummVM Meta Engine interface
  */
 class GlkMetaEngine : public MetaEngine {
-private:
-	Common::String findFileByGameId(const Common::String &gameId) const;
 public:
 	GlkMetaEngine() : MetaEngine() {}
 
@@ -49,13 +45,6 @@ public:
 		return "Infocom games (C) Infocom\nScott Adams games (C) Scott Adams";
 	}
 
-	bool hasFeature(MetaEngineFeature f) const override;
-	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
-	SaveStateList listSaves(const char *target) const override;
-	int getMaximumSaveSlot() const override;
-	void removeSaveState(const char *target, int slot) const override;
-	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
-
 	/**
 	 * Returns a list of games supported by this engine.
 	 */
diff --git a/engines/glk/metaengine.cpp b/engines/glk/metaengine.cpp
new file mode 100644
index 0000000000..6df7d0bcd6
--- /dev/null
+++ b/engines/glk/metaengine.cpp
@@ -0,0 +1,293 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+#include "common/md5.h"
+#include "common/memstream.h"
+#include "common/str-array.h"
+#include "common/file.h"
+#include "common/translation.h"
+#include "common/config-manager.h"
+
+#include "glk/detection.h"
+#include "glk/game_description.h"
+
+#include "glk/adrift/detection.h"
+#include "glk/advsys/detection.h"
+#include "glk/agt/detection.h"
+#include "glk/alan2/detection.h"
+#include "glk/alan3/detection.h"
+#include "glk/archetype/detection.h"
+#include "glk/zcode/detection.h"
+#include "glk/zcode/zcode.h"
+#include "glk/hugo/detection.h"
+#include "glk/jacl/detection.h"
+#include "glk/level9/detection.h"
+#include "glk/magnetic/detection.h"
+#include "glk/quest/detection.h"
+#include "glk/scott/detection.h"
+#include "glk/scott/scott.h"
+
+#ifndef RELEASE_BUILD
+#include "glk/comprehend/comprehend.h"
+#include "glk/comprehend/detection.h"
+#include "glk/glulx/detection.h"
+#include "glk/glulx/glulx.h"
+#include "glk/tads/detection.h"
+#include "glk/tads/tads2/tads2.h"
+#include "glk/tads/tads3/tads3.h"
+#endif
+
+#include "base/plugins.h"
+#include "common/md5.h"
+#include "common/memstream.h"
+#include "common/savefile.h"
+#include "common/str-array.h"
+#include "common/system.h"
+#include "graphics/surface.h"
+#include "common/config-manager.h"
+#include "common/file.h"
+#include "common/translation.h"
+
+#define MAX_SAVES 99
+
+class GlkMetaEngineConnect : public MetaEngineConnect {
+private:
+	Common::String findFileByGameId(const Common::String &gameId) const;
+public:
+    const char* getName() const override {
+        return "glk";
+    }
+
+    bool hasFeature(MetaEngineFeature f) const override;
+	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
+
+	SaveStateList listSaves(const char *target) const override;
+	int getMaximumSaveSlot() const override;
+	void removeSaveState(const char *target, int slot) const override;
+	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
+};
+
+bool GlkMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+	return
+	    (f == kSupportsListSaves) ||
+	    (f == kSupportsLoadingDuringStartup) ||
+	    (f == kSupportsDeleteSave) ||
+	    (f == kSavesSupportMetaInfo) ||
+	    (f == kSavesSupportCreationDate) ||
+	    (f == kSavesSupportPlayTime) ||
+	    (f == kSimpleSavesNames);
+}
+
+bool Glk::GlkEngine::hasFeature(EngineFeature f) const {
+	return
+	    (f == kSupportsReturnToLauncher) ||
+	    (f == kSupportsLoadingDuringRuntime) ||
+	    (f == kSupportsSavingDuringRuntime);
+}
+
+bool isGameAllowed(GameSupportLevel supportLevel) {
+	bool showTestingWarning = false;
+#ifdef RELEASE_BUILD
+	showTestingWarning = true;
+#endif
+
+	if (((supportLevel == kUnstableGame
+		|| (supportLevel == kTestingGame && showTestingWarning)))
+		&& !Engine::warnUserAboutUnsupportedGame())
+		return false;
+
+	return true;
+}
+
+template<class META, class ENG>bool create(OSystem *syst,
+		Glk::GlkGameDescription &gameDesc, Engine *&engine) {
+
+	Glk::GameDescriptor gd = META::findGame(gameDesc._gameId.c_str());
+	if (gd._description) {
+		if (!isGameAllowed(gd._supportLevel))
+			return true;
+
+		gameDesc._options = gd._options;
+		engine = new ENG(syst, gameDesc);
+		return true;
+	} else {
+		return false;
+	}
+}
+
+Common::String GlkMetaEngineConnect::findFileByGameId(const Common::String &gameId) const {
+	// Get the list of files in the folder and return detection against them
+	Common::FSNode folder = Common::FSNode(ConfMan.get("path"));
+	Common::FSList fslist;
+	folder.getChildren(fslist, Common::FSNode::kListFilesOnly);
+
+	// Get the matching MetaEngine for this Engine.
+	const MetaEngine &metaEngine = g_engine->getMetaEngine();
+
+	// Iterate over the files
+	for (Common::FSList::iterator i = fslist.begin(); i != fslist.end(); ++i) {
+		// Run a detection on each file in the folder individually
+		Common::FSList singleList;
+		singleList.push_back(*i);
+		DetectedGames games = metaEngine.detectGames(singleList);
+
+		// If a detection was found with the correct game Id, we have a winner
+		if (!games.empty() && games.front().gameId == gameId)
+			return (*i).getName();
+	}
+
+	// No match found
+	return Common::String();
+}
+
+Common::Error GlkMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+#ifndef RELEASE_BUILD
+	Glk::GameDescriptor td = Glk::GameDescriptor::empty();
+#endif
+	assert(engine);
+
+	// Populate the game description
+	Glk::GlkGameDescription gameDesc;
+	gameDesc._gameId = ConfMan.get("gameid");
+	gameDesc._filename = ConfMan.get("filename");
+
+	gameDesc._language = Common::UNK_LANG;
+	gameDesc._platform = Common::kPlatformUnknown;
+	if (ConfMan.hasKey("language"))
+		gameDesc._language = Common::parseLanguage(ConfMan.get("language"));
+	if (ConfMan.hasKey("platform"))
+		gameDesc._platform = Common::parsePlatform(ConfMan.get("platform"));
+
+	// If the game description has no filename, the engine has been launched directly from
+	// the command line. Do a scan for supported games for that Id in the game folder
+	if (gameDesc._filename.empty()) {
+		gameDesc._filename = findFileByGameId(gameDesc._gameId);
+		if (gameDesc._filename.empty())
+			return Common::kNoGameDataFoundError;
+	}
+
+	// Get the MD5
+	Common::File f;
+	if (!f.open(Common::FSNode(ConfMan.get("path")).getChild(gameDesc._filename)))
+		return Common::kNoGameDataFoundError;
+
+	gameDesc._md5 = Common::computeStreamMD5AsString(f, 5000);
+	f.close();
+
+	// Create the correct engine
+	*engine = nullptr;
+	if ((create<Glk::Adrift::AdriftMetaEngine, Glk::Adrift::Adrift>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::AdvSys::AdvSysMetaEngine, Glk::AdvSys::AdvSys>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::AGT::AGTMetaEngine, Glk::AGT::AGT>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::Alan2::Alan2MetaEngine, Glk::Alan2::Alan2>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::Alan3::Alan3MetaEngine, Glk::Alan3::Alan3>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::Archetype::ArchetypeMetaEngine, Glk::Archetype::Archetype>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::Hugo::HugoMetaEngine, Glk::Hugo::Hugo>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::JACL::JACLMetaEngine, Glk::JACL::JACL>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::Level9::Level9MetaEngine, Glk::Level9::Level9>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::Magnetic::MagneticMetaEngine, Glk::Magnetic::Magnetic>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::Quest::QuestMetaEngine, Glk::Quest::Quest>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::Scott::ScottMetaEngine, Glk::Scott::Scott>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::ZCode::ZCodeMetaEngine, Glk::ZCode::ZCode>(syst, gameDesc, *engine))) {}
+#ifndef RELEASE_BUILD
+	else if ((create<Glk::Comprehend::ComprehendMetaEngine, Glk::Comprehend::Comprehend>(syst, gameDesc, *engine))) {}
+	else if ((create<Glk::Glulx::GlulxMetaEngine, Glk::Glulx::Glulx>(syst, gameDesc, *engine))) {}
+	else if ((td = Glk::TADS::TADSMetaEngine::findGame(gameDesc._gameId.c_str()))._description) {
+		if (!isGameAllowed(td._supportLevel))
+			return Common::kUserCanceled;
+		else if (td._options & Glk::TADS::OPTION_TADS3)
+			new Glk::TADS::TADS3::TADS3(syst, gameDesc);
+		else
+			new Glk::TADS::TADS2::TADS2(syst, gameDesc);
+	}
+#endif
+	else {
+		return Common::kNoGameDataFoundError;
+	}
+
+	return *engine ? Common::kNoError : Common::kUserCanceled;
+}
+
+SaveStateList GlkMetaEngineConnect::listSaves(const char *target) const {
+	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
+	Common::StringArray filenames;
+	Common::String saveDesc;
+	Common::String pattern = Common::String::format("%s.0##", target);
+
+	filenames = saveFileMan->listSavefiles(pattern);
+
+	SaveStateList saveList;
+	for (Common::StringArray::const_iterator file = filenames.begin(); file != filenames.end(); ++file) {
+		const char *ext = strrchr(file->c_str(), '.');
+		int slot = ext ? atoi(ext + 1) : -1;
+
+		if (slot >= 0 && slot <= MAX_SAVES) {
+			Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(*file);
+
+			if (in) {
+				Common::String saveName;
+				if (Glk::QuetzalReader::getSavegameDescription(in, saveName))
+					saveList.push_back(SaveStateDescriptor(slot, saveName));
+
+				delete in;
+			}
+		}
+	}
+
+	// Sort saves based on slot number.
+	Common::sort(saveList.begin(), saveList.end(), SaveStateDescriptorSlotComparator());
+	return saveList;
+}
+
+int GlkMetaEngineConnect::getMaximumSaveSlot() const {
+	return MAX_SAVES;
+}
+
+void GlkMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	g_system->getSavefileManager()->removeSavefile(filename);
+}
+
+SaveStateDescriptor GlkMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+	Common::String filename = Common::String::format("%s.%03d", target, slot);
+	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename);
+	SaveStateDescriptor ssd;
+	bool result = false;
+
+	if (in) {
+		result = Glk::QuetzalReader::getSavegameMetaInfo(in, ssd);
+		ssd.setSaveSlot(slot);
+		delete in;
+	}
+
+	if (result)
+		return ssd;
+
+	return SaveStateDescriptor();
+}
+
+#if PLUGIN_ENABLED_DYNAMIC(GLK)
+	REGISTER_PLUGIN_DYNAMIC(GLK, PLUGIN_TYPE_ENGINE, GlkMetaEngineConnect);
+#else
+	REGISTER_PLUGIN_STATIC(GLK, PLUGIN_TYPE_ENGINE, GlkMetaEngineConnect);
+#endif
diff --git a/engines/glk/module.mk b/engines/glk/module.mk
index d3b53007b7..4153863dbb 100644
--- a/engines/glk/module.mk
+++ b/engines/glk/module.mk
@@ -4,12 +4,12 @@ MODULE_OBJS := \
 	blorb.o \
 	conf.o \
 	debugger.o \
-	detection.o \
 	events.o \
 	fonts.o \
 	glk.o \
 	glk_api.o \
 	glk_dispa.o \
+	metaengine.o \
 	pc_speaker.o \
 	picture.o \
 	quetzal.o \
@@ -321,3 +321,33 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# If building as static, skip the below, as
+# they're already in the executable.
+
+ifeq ($(ENABLE_GLK), DYNAMIC_PLUGIN)
+# Sub-engine detection objects
+DETECT_OBJS += $(MODULE)/adrift/detection.o
+DETECT_OBJS += $(MODULE)/advsys/detection.o
+DETECT_OBJS += $(MODULE)/agt/detection.o
+DETECT_OBJS += $(MODULE)/alan2/detection.o
+DETECT_OBJS += $(MODULE)/alan3/detection.o
+DETECT_OBJS += $(MODULE)/archetype/detection.o
+DETECT_OBJS += $(MODULE)/comprehend/detection.o
+DETECT_OBJS += $(MODULE)/glulx/detection.o
+DETECT_OBJS += $(MODULE)/hugo/detection.o
+DETECT_OBJS += $(MODULE)/jacl/detection.o
+DETECT_OBJS += $(MODULE)/level9/detection.o
+DETECT_OBJS += $(MODULE)/magnetic/detection.o
+DETECT_OBJS += $(MODULE)/quest/detection.o
+DETECT_OBJS += $(MODULE)/scott/detection.o
+DETECT_OBJS += $(MODULE)/tads/detection.o
+DETECT_OBJS += $(MODULE)/zcode/detection.o
+
+# Dependencies of detection objects
+DETECT_OBJS += $(MODULE)/blorb.o
+DETECT_OBJS += $(MODULE)/advsys/game.o
+endif


Commit: 84ddd3ac880b554f15df8a2d505650741621a0d5
    https://github.com/scummvm/scummvm/commit/84ddd3ac880b554f15df8a2d505650741621a0d5
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Remove comments referring to old game detection

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index c236b4b066..1502c96850 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -623,28 +623,6 @@ DetectionResults EngineManager::detectGames(const Common::FSList &fslist) const
 	PluginList plugins;
 	PluginList::const_iterator iter;
 
-	/**
-	 * Reference to old detection of games.
-	 * PLUGINS TODO: Remove at end.
-	PluginMan.loadFirstPlugin();
-	do {
-		plugins = getPlugins();
-		// Iterate over all known games and for each check if it might be
-		// the game in the presented directory.
-		for (iter = plugins.begin(); iter != plugins.end(); ++iter) {
-			const MetaEngine &metaEngine = (*iter)->get<MetaEngine>();
-			DetectedGames engineCandidates = metaEngine.detectGames(fslist);
-
-			for (uint i = 0; i < engineCandidates.size(); i++) {
-				engineCandidates[i].path = fslist.begin()->getParent().getPath();
-				engineCandidates[i].shortPath = fslist.begin()->getParent().getDisplayName();
-				candidates.push_back(engineCandidates[i]);
-			}
-
-		}
-	} while (PluginMan.loadNextPlugin());
-	 */
-
 	// MetaEngines are always loaded into memory, so, get them and
 	// run detection for all of them.
 	plugins = getPlugins(PLUGIN_TYPE_METAENGINE);


Commit: 8b43e79695e12b0d927fb2df1c7f26ad2c12d374
    https://github.com/scummvm/scummvm/commit/8b43e79695e12b0d927fb2df1c7f26ad2c12d374
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GUI: Fix namespaces for saveload dialogs when cloud is enabled.

Changed paths:
    gui/saveload-dialog.cpp


diff --git a/gui/saveload-dialog.cpp b/gui/saveload-dialog.cpp
index 894529233a..81f162c28d 100644
--- a/gui/saveload-dialog.cpp
+++ b/gui/saveload-dialog.cpp
@@ -248,7 +248,7 @@ void SaveLoadChooserDialog::handleTickle() {
 		Common::Array<Common::String> files = CloudMan.getSyncingFiles();
 		if (!files.empty()) {
 			{
-				SaveLoadCloudSyncProgressDialog dialog(_metaEngine ? _metaEngine->hasFeature(MetaEngine::kSimpleSavesNames) : false);
+				SaveLoadCloudSyncProgressDialog dialog(_metaEngine ? _metaEngine->hasFeature(MetaEngineConnect::kSimpleSavesNames) : false);
 				CloudMan.setSyncTarget(&dialog);
 				int result = dialog.runModal();
 				if (result == kCancelSyncCmd) {
@@ -302,7 +302,7 @@ void SaveLoadChooserDialog::listSaves() {
 
 #if defined(USE_CLOUD) && defined(USE_LIBCURL)
 	//if there is Cloud support, add currently synced files as "locked" saves in the list
-	if (_metaEngine->hasFeature(MetaEngine::kSimpleSavesNames)) {
+	if (_metaEngine->hasFeature(MetaEngineConnect::kSimpleSavesNames)) {
 		Common::String pattern = _target + ".###";
 		Common::Array<Common::String> files = CloudMan.getSyncingFiles(); //returns empty array if not syncing
 		for (uint32 i = 0; i < files.size(); ++i) {


Commit: 53f08789ebdd84f09a1f32e0cc291b98d94f1080
    https://github.com/scummvm/scummvm/commit/53f08789ebdd84f09a1f32e0cc291b98d94f1080
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Restore functionalities of uncached plugin manager for the new changes.

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index 1502c96850..5fe5e82727 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -269,23 +269,27 @@ void PluginManager::addPluginProvider(PluginProvider *pp) {
 Plugin *PluginManager::giveEngineFromMetaEngine(const Plugin *plugin) {
 	assert(plugin->getType() == PLUGIN_TYPE_METAENGINE);
 
-	PluginList pl = PluginMan.getPlugins(PLUGIN_TYPE_ENGINE);
 	Plugin *enginePlugin = nullptr;
+	bool found = false;
 
 	// Use the engineID from MetaEngine for comparasion.
 	Common::String metaEnginePluginName = plugin->getEngineId();
-
-	// Iterate over all engine plugins.
-	for (PluginList::const_iterator itr = pl.begin(); itr != pl.end(); itr++) {
-		// The getName() provides a name which is similiar to getEngineId.
-		// Because engines are engines themselves, this function is simply named getName.
-		Common::String enginePluginName((*itr)->getName());
-
-		if (metaEnginePluginName.equalsIgnoreCase(enginePluginName)) {
-			enginePlugin = (*itr);
-			break;
+	PluginMan.loadFirstPlugin();
+	do {
+		PluginList pl = PluginMan.getPlugins(PLUGIN_TYPE_ENGINE);
+		// Iterate over all engine plugins.
+		for (PluginList::const_iterator itr = pl.begin(); itr != pl.end(); itr++) {
+			// The getName() provides a name which is similiar to getEngineId.
+			// Because engines are engines themselves, this function is simply named getName.
+			Common::String enginePluginName((*itr)->getName());
+
+			if (metaEnginePluginName.equalsIgnoreCase(enginePluginName)) {
+				enginePlugin = (*itr);
+				found = true;
+				break;
+			}
 		}
-	}
+	} while (!found && PluginMan.loadNextPlugin());
 
 	if (enginePlugin) {
 		warning("MetaEngine: %s \t matched to \t Engine: %s", plugin->getName(), enginePlugin->getFileName());
@@ -487,27 +491,16 @@ void PluginManager::unloadAllPlugins() {
 
 void PluginManager::unloadPluginsExcept(PluginType type, const Plugin *plugin, bool deletePlugin /*=true*/) {
 	Plugin *found = NULL;
-
-	// If someone calls this function with a nullptr Plugin, we clear everything, and no need to search
-	// for individual plugin.
-	if (plugin) {
-		if (type != plugin->getType()) {
-			warning("Plugins: unloadPluginExcept: mismatching type of plugins requested to unload. Operation not carried out.");
-			return;
-		}
-
-		for (PluginList::iterator p = _pluginsInMem[type].begin(); p != _pluginsInMem[type].end(); ++p) {
-			if (*p == plugin) {
-				found = *p;
-			} else {
-				(*p)->unloadPlugin();
-				if (deletePlugin) {
-					delete *p;
-				}
+	for (PluginList::iterator p = _pluginsInMem[type].begin(); p != _pluginsInMem[type].end(); ++p) {
+		if (*p == plugin) {
+			found = *p;
+		} else {
+			(*p)->unloadPlugin();
+			if (deletePlugin) {
+				delete *p;
 			}
 		}
 	}
-
 	_pluginsInMem[type].clear();
 	if (found != NULL) {
 		_pluginsInMem[type].push_back(found);


Commit: 7fe1eb330d40387f40644440fc0ef1f5ac9f14d8
    https://github.com/scummvm/scummvm/commit/7fe1eb330d40387f40644440fc0ef1f5ac9f14d8
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DREAMWEB: Remove redundant and unreachable return statement

Changed paths:
    engines/dreamweb/metaengine.cpp


diff --git a/engines/dreamweb/metaengine.cpp b/engines/dreamweb/metaengine.cpp
index e127960ed3..1d7a1c213f 100644
--- a/engines/dreamweb/metaengine.cpp
+++ b/engines/dreamweb/metaengine.cpp
@@ -69,7 +69,6 @@ bool DreamWeb::DreamWebEngine::hasFeature(EngineFeature f) const {
 	default:
 		return false;
 	}
-	return false;
 }
 
 bool DreamWebMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {


Commit: fa8aa6e9f445a8d408db0e63e9f1309a6064849f
    https://github.com/scummvm/scummvm/commit/fa8aa6e9f445a8d408db0e63e9f1309a6064849f
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
AGI: Move detection related code to a new folder, add AGI-Detection module.

Changed paths:
  A engines/agi/detection/detection.cpp
  A engines/agi/detection/detection.h
  A engines/agi/detection/detection_tables.h
  A engines/agi/detection/module.mk
  A engines/agi/detection/wagparser.cpp
  A engines/agi/detection/wagparser.h
  R engines/agi/detection.cpp
  R engines/agi/detection.h
  R engines/agi/detection_tables.h
  R engines/agi/wagparser.cpp
  R engines/agi/wagparser.h
    engines/agi/metaengine.cpp
    engines/agi/module.mk


diff --git a/engines/agi/detection.cpp b/engines/agi/detection/detection.cpp
similarity index 98%
rename from engines/agi/detection.cpp
rename to engines/agi/detection/detection.cpp
index 10b4772f85..ea43d2c819 100644
--- a/engines/agi/detection.cpp
+++ b/engines/agi/detection/detection.cpp
@@ -29,8 +29,8 @@
 #include "engines/advancedDetector.h"
 
 #include "agi/detection_enums.h"
-#include "agi/detection.h"
-#include "agi/wagparser.h" // for fallback detection
+#include "agi/detection/detection.h"
+#include "agi/detection/wagparser.h" // for fallback detection
 
 static const PlainGameDescriptor agiGames[] = {
 	{"agi", "Sierra AGI game"},
@@ -64,7 +64,7 @@ static const PlainGameDescriptor agiGames[] = {
 	{0, 0}
 };
 
-#include "agi/detection_tables.h"
+#include "agi/detection/detection_tables.h"
 
 static const ADExtraGuiOptionsMap optionsList[] = {
 	{
diff --git a/engines/agi/detection.h b/engines/agi/detection/detection.h
similarity index 100%
rename from engines/agi/detection.h
rename to engines/agi/detection/detection.h
diff --git a/engines/agi/detection_tables.h b/engines/agi/detection/detection_tables.h
similarity index 100%
rename from engines/agi/detection_tables.h
rename to engines/agi/detection/detection_tables.h
diff --git a/engines/agi/detection/module.mk b/engines/agi/detection/module.mk
new file mode 100644
index 0000000000..879a2323cf
--- /dev/null
+++ b/engines/agi/detection/module.mk
@@ -0,0 +1,11 @@
+MODULE := engines/agi/detection
+
+MODULE_OBJS :=
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# External dependencies of detection.
+# This is unneeded by the engine module itself,
+# so seperate it completely.
+DETECT_OBJS += $(MODULE)/wagparser.o
diff --git a/engines/agi/wagparser.cpp b/engines/agi/detection/wagparser.cpp
similarity index 99%
rename from engines/agi/wagparser.cpp
rename to engines/agi/detection/wagparser.cpp
index fa11654ad9..f7ace22153 100644
--- a/engines/agi/wagparser.cpp
+++ b/engines/agi/detection/wagparser.cpp
@@ -26,7 +26,7 @@
 #include "common/debug.h"
 #include "common/textconsole.h"
 
-#include "agi/wagparser.h"
+#include "agi/detection/wagparser.h"
 
 namespace Agi {
 
diff --git a/engines/agi/wagparser.h b/engines/agi/detection/wagparser.h
similarity index 100%
rename from engines/agi/wagparser.h
rename to engines/agi/detection/wagparser.h
diff --git a/engines/agi/metaengine.cpp b/engines/agi/metaengine.cpp
index f2507a8f37..1f7aa20909 100644
--- a/engines/agi/metaengine.cpp
+++ b/engines/agi/metaengine.cpp
@@ -38,7 +38,7 @@
 #include "agi/preagi_troll.h"
 #include "agi/preagi_winnie.h"
 
-#include "agi/detection.h"
+#include "agi/detection/detection.h"
 
 namespace Agi {
 
diff --git a/engines/agi/module.mk b/engines/agi/module.mk
index d66e4129de..84a7138086 100644
--- a/engines/agi/module.mk
+++ b/engines/agi/module.mk
@@ -49,11 +49,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# External dependencies of detection.
-# This is unneeded by the engine module itself,
-# so seperate it completely.
-DETECT_OBJS += $(MODULE)/wagparser.o


Commit: ff74297940472656ea1f2b5ded38d13bc491cefb
    https://github.com/scummvm/scummvm/commit/ff74297940472656ea1f2b5ded38d13bc491cefb
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PLUMBERS: Move detection related code to a new folder, add new Detection module.

Changed paths:
  A engines/plumbers/detection/detection.cpp
  A engines/plumbers/detection/module.mk
  R engines/plumbers/detection.cpp
    engines/plumbers/module.mk


diff --git a/engines/plumbers/detection.cpp b/engines/plumbers/detection/detection.cpp
similarity index 100%
rename from engines/plumbers/detection.cpp
rename to engines/plumbers/detection/detection.cpp
diff --git a/engines/plumbers/detection/module.mk b/engines/plumbers/detection/module.mk
new file mode 100644
index 0000000000..2bad793b2b
--- /dev/null
+++ b/engines/plumbers/detection/module.mk
@@ -0,0 +1,6 @@
+MODULE := engines/plumbers/detection
+
+MODULE_OBJS :=
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/plumbers/module.mk b/engines/plumbers/module.mk
index 63fde172d3..02dbcdf579 100644
--- a/engines/plumbers/module.mk
+++ b/engines/plumbers/module.mk
@@ -12,6 +12,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o


Commit: 05e170415c8ae15df8c26c326f6e2e18da707eaa
    https://github.com/scummvm/scummvm/commit/05e170415c8ae15df8c26c326f6e2e18da707eaa
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CONFIGURE: TEMP: Add support to build detection features as dynamic.

- A commit to show how the new makefiles structure and flow would look like. This is not final.

Changed paths:
    configure


diff --git a/configure b/configure
index e4c8c3f1c9..7de4a9b85b 100755
--- a/configure
+++ b/configure
@@ -241,6 +241,8 @@ PANDOC=""
 _pandocpath="$PATH"
 _pandocformat="default"
 _pandocext="default"
+# Detection features to be linked into executable or not
+_detection_features_static="true"
 # The following variables are automatically detected, and should not
 # be modified otherwise. Consider them read-only.
 _posix=no
@@ -1022,6 +1024,8 @@ Game engines:
 $engines_help
 Optional Features:
   --enable-static          build a static binary instead of using shared objects
+  --enable-detection-static  build detection features into executable (default)
+  --enable-detection-dynamic build detection features into a library
   --enable-c++11           build as C++11 if the compiler allows that
   --disable-debug          disable building with debugging symbols
   --enable-Werror          treat warnings as errors
@@ -1221,6 +1225,8 @@ for ac_option in $@; do
 	--enable-dependency-tracking)                        ;;
 	# End of ignored options.
 	--enable-static)              _static_build=yes      ;;
+	--enable-detection-static)    _detection_features_static="true";;
+	--enable-detection-dynamic)   _detection_features_static="false";;
 	--disable-16bit)              _16bit=no              ;;
 	--enable-highres)             _highres=yes           ;;
 	--disable-highres)            _highres=no            ;;
@@ -6139,6 +6145,8 @@ for engine in $_sorted_engines; do
 		# main engine
 		cat >> engines/engines.mk << EOF
 
+MODULES += engines/$engine/detection
+
 ifdef ENABLE_$j
 DEFINES += -DENABLE_$j=\$(ENABLE_$j)
 MODULES += engines/$engine
@@ -6160,6 +6168,14 @@ EOF
 	fi
 done
 
+if [ "${_detection_features_static}" == "false" ]; then
+	cat >> engines/engines.mk << EOF
+
+# This build was configured to use detection as a dynamic plugin.
+MODULES += detection
+EOF
+fi
+
 declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
 								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
 								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
@@ -6173,6 +6189,29 @@ declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRA
 								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE" "SCI" "MOHAWK" "ULTIMA" "GLK")
 detectId="_DETECTION"
 
+##################################################
+
+declare -a engi=("AGI" "PLUMBERS")
+
+echo "Creating detection/detection_table.h"
+cat > detection/detection_table.h << EOF
+/* This file is automatically generated by configure */
+/* DO NOT EDIT MANUALLY */
+// This file is being included by "detection/detection.cpp"
+EOF
+
+# Below line, we'll have for each engine in sorted engines: LINK_PLUGIN-detection.
+# Temporary to see, we have 2 engines.
+# Once each engine's modules are shifted in the same way as these 2, we can remove the array
+# and do it for all engines.
+for engine in "${engi[@]}"; do
+cat >> detection/detection_table.h << EOF
+LINK_PLUGIN(${engine}${detectId})
+EOF
+done
+
+##################################################
+
 echo "Creating engines/plugins_table.h"
 cat > engines/plugins_table.h << EOF
 /* This file is automatically generated by configure */
@@ -6187,7 +6226,7 @@ for engine in $_sorted_engines; do
 			if [ $j == $eng ]; then
 				cat >> engines/plugins_table.h << EOF
 #if PLUGIN_ENABLED($j)
-LINK_PLUGIN(${j}${detectId})
+//LINK_PLUGIN(${j}${detectId})
 #endif
 EOF
 				cat >> engines/plugins_table.h << EOF


Commit: 74149fe7cdb3dd797fb1b1005f34dbfcb197df1b
    https://github.com/scummvm/scummvm/commit/74149fe7cdb3dd797fb1b1005f34dbfcb197df1b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: DETECTION: Add a new module detection.

- This is being done to enable support of building detection as dynamic libraries.

Changed paths:
  A detection/detection.cpp
  A detection/detection.h
  A detection/module.mk


diff --git a/detection/detection.cpp b/detection/detection.cpp
new file mode 100644
index 0000000000..ef74f1f795
--- /dev/null
+++ b/detection/detection.cpp
@@ -0,0 +1,47 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+
+#include "base/plugins.h"
+#include "engines/metaengine.h"
+#include "engines/advanceddetector.h"
+#include "detection/detection.h"
+
+const char *Detection::getName() const {
+    return "detection";
+}
+
+Detection::Detection() {
+
+    #define LINK_PLUGIN(ID) \
+			extern PluginType g_##ID##_type; \
+			extern PluginObject *g_##ID##_getObject(); \
+			_pl.push_back(new StaticPlugin(g_##ID##_getObject(), g_##ID##_type));
+
+    #include "engines/detection_table.h"
+}
+
+Detection::~Detection() {
+}
+
+REGISTER_PLUGIN_DYNAMIC(DETECTION, PLUGIN_TYPE_DETECTION, Detection);
+
diff --git a/detection/detection.h b/detection/detection.h
new file mode 100644
index 0000000000..da79b432a7
--- /dev/null
+++ b/detection/detection.h
@@ -0,0 +1,33 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#include "base/plugins.h"
+
+class Detection : public PluginObject {
+public:
+    PluginList _pl;
+public:
+    Detection();
+    ~Detection();
+
+    const char *getName() const override;
+};
diff --git a/detection/module.mk b/detection/module.mk
new file mode 100644
index 0000000000..b53e7bad1e
--- /dev/null
+++ b/detection/module.mk
@@ -0,0 +1,15 @@
+MODULE := detection
+
+DETECT_OBJS_DYNAMIC=$(addprefix ../,$(DETECT_OBJS))
+
+MODULE_OBJS := \
+	detection.o \
+	$(DETECT_OBJS_DYNAMIC)
+
+# Reset detect objects, so none of them build into the executable.
+DETECT_OBJS :=
+
+PLUGIN := 1
+
+# Include common rules
+include $(srcdir)/rules.mk


Commit: 408158edc9aeb3908376957d5180d7d0eb502eca
    https://github.com/scummvm/scummvm/commit/408158edc9aeb3908376957d5180d7d0eb502eca
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Add a new type of plugin - DETECTION.

Changed paths:
    base/plugins.cpp
    base/plugins.h


diff --git a/base/plugins.cpp b/base/plugins.cpp
index 5fe5e82727..f8976804de 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -36,6 +36,7 @@ int pluginTypeVersions[PLUGIN_TYPE_MAX] = {
 	PLUGIN_TYPE_METAENGINE_VERSION,
 	PLUGIN_TYPE_ENGINE_VERSION,
 	PLUGIN_TYPE_MUSIC_VERSION,
+	PLUGIN_TYPE_DETECTION_VERSION,
 };
 
 
diff --git a/base/plugins.h b/base/plugins.h
index 9f2674b33f..fc62dd4445 100644
--- a/base/plugins.h
+++ b/base/plugins.h
@@ -63,6 +63,7 @@ enum PluginType {
 	PLUGIN_TYPE_METAENGINE = 0,
 	PLUGIN_TYPE_ENGINE,
 	PLUGIN_TYPE_MUSIC,
+	PLUGIN_TYPE_DETECTION,
 	/* PLUGIN_TYPE_SCALER, */	// TODO: Add graphics scaler plugins
 
 	PLUGIN_TYPE_MAX
@@ -73,6 +74,7 @@ enum PluginType {
 #define PLUGIN_TYPE_METAENGINE_VERSION 1
 #define PLUGIN_TYPE_ENGINE_VERSION 2
 #define PLUGIN_TYPE_MUSIC_VERSION 1
+#define PLUGIN_TYPE_DETECTION_VERSION 1
 
 extern int pluginTypeVersions[PLUGIN_TYPE_MAX];
 


Commit: b78534dcb0b16420297369ba5ffad581d3c112c9
    https://github.com/scummvm/scummvm/commit/b78534dcb0b16420297369ba5ffad581d3c112c9
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Seperate declaration/definition of StaticPlugins.

- Move declarations inside plugins.h to make it visible to detection/detection.cpp

Changed paths:
    base/plugins.cpp
    base/plugins.h


diff --git a/base/plugins.cpp b/base/plugins.cpp
index f8976804de..4596281440 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -58,23 +58,19 @@ const char *Plugin::getEngineId() const {
 	return nullptr;
 }
 
-class StaticPlugin : public Plugin {
-public:
-	StaticPlugin(PluginObject *pluginobject, PluginType type) {
-		assert(pluginobject);
-		assert(type < PLUGIN_TYPE_MAX);
-		_pluginObject = pluginobject;
-		_type = type;
-	}
-
-	~StaticPlugin() {
-		delete _pluginObject;
-	}
+StaticPlugin::StaticPlugin(PluginObject *pluginobject, PluginType type) {
+	assert(pluginobject);
+	assert(type < PLUGIN_TYPE_MAX);
+	_pluginObject = pluginobject;
+	_type = type;
+}
 
-	virtual bool loadPlugin()		{ return true; }
-	virtual void unloadPlugin()		{}
-};
+StaticPlugin::~StaticPlugin() {
+	delete _pluginObject;
+}
 
+bool StaticPlugin::loadPlugin()		{ return true; }
+void StaticPlugin::unloadPlugin()	{}
 class StaticPluginProvider : public PluginProvider {
 public:
 	StaticPluginProvider() {
diff --git a/base/plugins.h b/base/plugins.h
index fc62dd4445..cc40feb618 100644
--- a/base/plugins.h
+++ b/base/plugins.h
@@ -215,6 +215,15 @@ public:
 	virtual const char *getFileName() const { return 0; }
 };
 
+class StaticPlugin : public Plugin {
+public:
+	StaticPlugin(PluginObject *pluginobject, PluginType type);
+	~StaticPlugin();
+	virtual bool loadPlugin();
+	virtual void unloadPlugin();
+};
+
+
 /** List of Plugin instances. */
 typedef Common::Array<Plugin *> PluginList;
 


Commit: 8dfaf6cc0e54b2a211b47fdd8853b806ed3d8f55
    https://github.com/scummvm/scummvm/commit/8dfaf6cc0e54b2a211b47fdd8853b806ed3d8f55
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Add support for detection plugins to be loaded on demand.

- Mainly used for UncachedPluginManagers.
- CachedPluginManagers will not handle these, as metaengines will always be available in memory.

Changed paths:
    base/plugins.cpp
    base/plugins.h


diff --git a/base/plugins.cpp b/base/plugins.cpp
index 4596281440..fdaa94cd6b 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -30,6 +30,8 @@
 #include "common/fs.h"
 #endif
 
+#include "detection/detection.h"
+
 // Plugin versioning
 
 int pluginTypeVersions[PLUGIN_TYPE_MAX] = {
@@ -71,6 +73,7 @@ StaticPlugin::~StaticPlugin() {
 
 bool StaticPlugin::loadPlugin()		{ return true; }
 void StaticPlugin::unloadPlugin()	{}
+
 class StaticPluginProvider : public PluginProvider {
 public:
 	StaticPluginProvider() {
@@ -335,6 +338,11 @@ void PluginManagerUncached::init() {
 
 	unloadPluginsExcept(PLUGIN_TYPE_ENGINE, NULL, false); // empty the engine plugins
 
+	Common::String detectPluginName = "detection";
+	detectPluginName += PLUGIN_SUFFIX;
+
+	bool foundDetectPlugin = false;
+
 	for (ProviderList::iterator pp = _providers.begin();
 	                            pp != _providers.end();
 	                            ++pp) {
@@ -345,6 +353,15 @@ void PluginManagerUncached::init() {
 			// file plugins. Currently this is the case. If it changes, we
 			// should find a fast way of detecting whether a plugin is a
 			// music or an engine plugin.
+			if (!foundDetectPlugin && (*pp)->isFilePluginProvider()) {
+				Common::String pName = (*p)->getFileName();
+				if (pName.hasSuffix(detectPluginName)) {
+					_detectionPlugin = (*p);
+					foundDetectPlugin = true;
+					continue;
+				}
+			}
+
 			if ((*pp)->isFilePluginProvider()) {
 				_allEnginePlugins.push_back(*p);
 			} else if ((*p)->loadPlugin()) { // and this is the proper method
@@ -417,6 +434,47 @@ void PluginManagerUncached::updateConfigWithFileName(const Common::String &engin
 	}
 }
 
+void PluginManagerUncached::loadDetectionPlugin() {
+	bool linkMetaEngines = false;
+
+	if (_isDetectionLoaded) {
+		warning("Detection plugin is already loaded. Adding each available engines to the memory.");
+		linkMetaEngines = true;
+	} else {
+		if (_detectionPlugin) {
+			if (_detectionPlugin->loadPlugin()) {
+				assert((_detectionPlugin)->getType() == PLUGIN_TYPE_DETECTION);
+
+				linkMetaEngines = true;
+				_isDetectionLoaded = true;
+			} else {
+				warning("Detection plugin was not loaded correctly.");
+				return;
+			}
+		} else {
+			warning("Detection plugin not found.");
+			return;
+		}
+	}
+
+	if (linkMetaEngines) {
+		_pluginsInMem[PLUGIN_TYPE_METAENGINE].clear();
+		PluginList &pl = (_detectionPlugin)->get<Detection>()._pl;
+		Common::for_each(pl.begin(), pl.end(), Common::bind1st(Common::mem_fun(&PluginManagerUncached::tryLoadPlugin), this));
+	}
+
+}
+
+void PluginManagerUncached::unloadDetectionPlugin() {
+	if (_isDetectionLoaded) {
+		_pluginsInMem[PLUGIN_TYPE_METAENGINE].clear();
+		_detectionPlugin->unloadPlugin();
+		_isDetectionLoaded = false;
+	} else {
+		warning("Detection plugin is already unloaded.");
+	}
+}
+
 void PluginManagerUncached::loadFirstPlugin() {
 	unloadPluginsExcept(PLUGIN_TYPE_ENGINE, NULL, false);
 
diff --git a/base/plugins.h b/base/plugins.h
index cc40feb618..45f7a2d381 100644
--- a/base/plugins.h
+++ b/base/plugins.h
@@ -367,6 +367,8 @@ public:
 	virtual bool loadNextPlugin() { return false; }
 	virtual bool loadPluginFromEngineId(const Common::String &engineId) { return false; }
 	virtual void updateConfigWithFileName(const Common::String &engineId) {}
+	virtual void loadDetectionPlugin() {}
+	virtual void unloadDetectionPlugin() {}
 
 	// Functions used only by the cached PluginManager
 	virtual void loadAllPlugins();
@@ -386,9 +388,12 @@ class PluginManagerUncached : public PluginManager {
 protected:
 	friend class PluginManager;
 	PluginList _allEnginePlugins;
+	Plugin  *_detectionPlugin;
 	PluginList::iterator _currentPlugin;
 
-	PluginManagerUncached() {}
+	bool _isDetectionLoaded;
+
+	PluginManagerUncached() : _isDetectionLoaded(false) {}
 	bool loadPluginByFileName(const Common::String &filename);
 
 public:
@@ -397,6 +402,8 @@ public:
 	virtual bool loadNextPlugin();
 	virtual bool loadPluginFromEngineId(const Common::String &engineId);
 	virtual void updateConfigWithFileName(const Common::String &engineId);
+	virtual void loadDetectionPlugin() override;
+	virtual void unloadDetectionPlugin() override;
 
 	virtual void loadAllPlugins() {} 	// we don't allow these
 	virtual void loadAllPluginsOfType(PluginType type) {}


Commit: 5f5363f03b6fc19ea20d18ae4451dbc83e5aba40
    https://github.com/scummvm/scummvm/commit/5f5363f03b6fc19ea20d18ae4451dbc83e5aba40
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: MAIN: Load/Unload detection plugin for UncachedPluginMan as/when needed.

- Used only in context of UncachedPluginMan
- Always load on startup
- When starting a game, unload all other MetaEngines except the one needed.

Changed paths:
    base/main.cpp


diff --git a/base/main.cpp b/base/main.cpp
index 942e45caa2..3b91095438 100644
--- a/base/main.cpp
+++ b/base/main.cpp
@@ -153,6 +153,8 @@ void saveLastLaunchedTarget(const Common::String &target) {
 
 // TODO: specify the possible return values here
 static Common::Error runGame(const Plugin *plugin, OSystem &system, const Common::String &edebuglevels) {
+	assert(plugin);
+
 	// Determine the game data path, for validation and error messages
 	Common::FSNode dir(ConfMan.get("path"));
 	Common::String target = ConfMan.getActiveDomainName();
@@ -436,6 +438,7 @@ extern "C" int scummvm_main(int argc, const char * const argv[]) {
 
 	PluginManager::instance().init();
  	PluginManager::instance().loadAllPlugins(); // load plugins for cached plugin manager
+	PluginManager::instance().loadDetectionPlugin(); // load detection plugin for uncached plugin manager
 
 	// If we received an invalid music parameter via command line we check this here.
 	// We can't check this before loading the music plugins.
@@ -552,6 +555,12 @@ extern "C" int scummvm_main(int argc, const char * const argv[]) {
 			// Then, pass in the pointer to enginePlugin, with the matching type, so our function behaves as-is.
 			PluginManager::instance().unloadPluginsExcept(PLUGIN_TYPE_ENGINE, enginePlugin);
 
+#if defined(UNCACHED_PLUGINS) && defined(DYNAMIC_MODULES)
+			// Unload all MetaEngines not needed for the current engine, if we're using uncached plugins
+			// to save extra memory.
+			PluginManager::instance().unloadPluginsExcept(PLUGIN_TYPE_METAENGINE, plugin);
+#endif
+
 #ifdef ENABLE_EVENTRECORDER
 			Common::String recordMode = ConfMan.get("record_mode");
 			Common::String recordFileName = ConfMan.get("record_file_name");
@@ -591,6 +600,7 @@ extern "C" int scummvm_main(int argc, const char * const argv[]) {
 #if defined(UNCACHED_PLUGINS) && defined(DYNAMIC_MODULES)
 			// do our best to prevent fragmentation by unloading as soon as we can
 			PluginManager::instance().unloadPluginsExcept(PLUGIN_TYPE_ENGINE, NULL, false);
+			PluginManager::instance().unloadDetectionPlugin();
 			// reallocate the config manager to get rid of any fragmentation
 			ConfMan.defragment();
 			// The keymapper keeps pointers to the configuration domains. It needs to be reinitialized.
@@ -646,6 +656,7 @@ extern "C" int scummvm_main(int argc, const char * const argv[]) {
 			}
 
 			PluginManager::instance().loadAllPluginsOfType(PLUGIN_TYPE_ENGINE); // only for cached manager
+			PluginManager::instance().loadDetectionPlugin(); // only for uncached manager
 		} else {
 			GUI::displayErrorDialog(_("Could not find any engine capable of running the selected game"));
 
@@ -669,6 +680,7 @@ extern "C" int scummvm_main(int argc, const char * const argv[]) {
 	Cloud::CloudManager::destroy();
 #endif
 #endif
+	PluginManager::instance().unloadDetectionPlugin();
 	PluginManager::instance().unloadAllPlugins();
 	PluginManager::destroy();
 	GUI::GuiManager::destroy();


Commit: e16ec08d8b3e3e9c12102b4620436e41c9d55518
    https://github.com/scummvm/scummvm/commit/e16ec08d8b3e3e9c12102b4620436e41c9d55518
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: DETECTION: Use correct header file

Changed paths:
    detection/detection.cpp


diff --git a/detection/detection.cpp b/detection/detection.cpp
index ef74f1f795..222dcc84e1 100644
--- a/detection/detection.cpp
+++ b/detection/detection.cpp
@@ -37,7 +37,7 @@ Detection::Detection() {
 			extern PluginObject *g_##ID##_getObject(); \
 			_pl.push_back(new StaticPlugin(g_##ID##_getObject(), g_##ID##_type));
 
-    #include "engines/detection_table.h"
+    #include "detection/detection_table.h"
 }
 
 Detection::~Detection() {


Commit: 8189a0531637ba89d9850c306eed6e94c01343b0
    https://github.com/scummvm/scummvm/commit/8189a0531637ba89d9850c306eed6e94c01343b0
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: ALL: Adapt to changes for new plugins by defining a new detection module

For each engine:
- Make a new folder detection
- Move detection-related files inside the folder
- Add a new module "enginename/detection"
- Add DETECT_OBJS here
- Adjust the normal engine module to remove detect_objs
- Adjust every file for the new changes.

Changed paths:
  A engines/access/detection/detection.cpp
  A engines/access/detection/detection.h
  A engines/access/detection/detection_enums.h
  A engines/access/detection/detection_tables.h
  A engines/access/detection/module.mk
  A engines/adl/detection/detection.cpp
  A engines/adl/detection/detection.h
  A engines/adl/detection/detection_enums.h
  A engines/adl/detection/module.mk
  A engines/agos/detection/detection.cpp
  A engines/agos/detection/detection.h
  A engines/agos/detection/detection_enums.h
  A engines/agos/detection/detection_tables.h
  A engines/agos/detection/module.mk
  A engines/avalanche/detection/detection.cpp
  A engines/avalanche/detection/detection.h
  A engines/avalanche/detection/module.mk
  A engines/bbvs/detection/detection.cpp
  A engines/bbvs/detection/detection_enums.h
  A engines/bbvs/detection/module.mk
  A engines/bladerunner/detection/detection.cpp
  A engines/bladerunner/detection/detection_tables.h
  A engines/bladerunner/detection/module.mk
  A engines/cge/detection/detection.cpp
  A engines/cge/detection/module.mk
  A engines/cge2/detection/detection.cpp
  A engines/cge2/detection/module.mk
  A engines/chewy/detection/detection.cpp
  A engines/chewy/detection/detection.h
  A engines/chewy/detection/module.mk
  A engines/cine/detection/detection.cpp
  A engines/cine/detection/detection.h
  A engines/cine/detection/detection_enums.h
  A engines/cine/detection/detection_tables.h
  A engines/cine/detection/module.mk
  A engines/composer/detection/detection.cpp
  A engines/composer/detection/detection.h
  A engines/composer/detection/detection_enums.h
  A engines/composer/detection/detection_tables.h
  A engines/composer/detection/module.mk
  A engines/cruise/detection/detection.cpp
  A engines/cruise/detection/detection.h
  A engines/cruise/detection/module.mk
  A engines/cryo/detection/detection.cpp
  A engines/cryo/detection/module.mk
  A engines/cryomni3d/detection/detection.cpp
  A engines/cryomni3d/detection/detection.h
  A engines/cryomni3d/detection/detection_enums.h
  A engines/cryomni3d/detection/detection_tables.h
  A engines/cryomni3d/detection/module.mk
  A engines/director/detection/detection.cpp
  A engines/director/detection/detection.h
  A engines/director/detection/detection_enums.h
  A engines/director/detection/detection_tables.h
  A engines/director/detection/module.mk
  A engines/dm/detection/detection.cpp
  A engines/dm/detection/detection.h
  A engines/dm/detection/detection_enums.h
  A engines/dm/detection/module.mk
  A engines/draci/detection/detection.cpp
  A engines/draci/detection/module.mk
  A engines/dragons/detection/detection.cpp
  A engines/dragons/detection/detection.h
  A engines/dragons/detection/detection_enums.h
  A engines/dragons/detection/module.mk
  A engines/drascula/detection/detection.cpp
  A engines/drascula/detection/detection.h
  A engines/drascula/detection/detection_enums.h
  A engines/drascula/detection/module.mk
  A engines/dreamweb/detection/detection.cpp
  A engines/dreamweb/detection/detection.h
  A engines/dreamweb/detection/detection_tables.h
  A engines/dreamweb/detection/module.mk
  A engines/fullpipe/detection/detection.cpp
  A engines/fullpipe/detection/module.mk
  A engines/glk/detection/detection.cpp
  A engines/glk/detection/module.mk
  A engines/gnap/detection/detection.cpp
  A engines/gnap/detection/module.mk
  A engines/gob/detection/module.mk
  A engines/griffon/detection/detection.cpp
  A engines/griffon/detection/module.mk
  A engines/groovie/detection/detection.cpp
  A engines/groovie/detection/detection.h
  A engines/groovie/detection/detection_enums.h
  A engines/groovie/detection/module.mk
  A engines/hdb/detection/detection.cpp
  A engines/hdb/detection/detection_enums.h
  A engines/hdb/detection/module.mk
  A engines/hopkins/detection/detection.cpp
  A engines/hopkins/detection/detection.h
  A engines/hopkins/detection/detection_tables.h
  A engines/hopkins/detection/module.mk
  A engines/hugo/detection/detection.cpp
  A engines/hugo/detection/detection.h
  A engines/hugo/detection/detection_enums.h
  A engines/hugo/detection/module.mk
  A engines/illusions/detection/detection.cpp
  A engines/illusions/detection/detection.h
  A engines/illusions/detection/detection_enums.h
  A engines/illusions/detection/module.mk
  A engines/kingdom/detection/detection.cpp
  A engines/kingdom/detection/module.mk
  A engines/kyra/detection/detection.cpp
  A engines/kyra/detection/detection.h
  A engines/kyra/detection/detection_enums.h
  A engines/kyra/detection/detection_tables.h
  A engines/kyra/detection/module.mk
  A engines/lab/detection/detection.cpp
  A engines/lab/detection/detection_enums.h
  A engines/lab/detection/module.mk
  A engines/lastexpress/detection/detection.cpp
  A engines/lastexpress/detection/module.mk
  A engines/lilliput/detection/detection.cpp
  A engines/lilliput/detection/detection.h
  A engines/lilliput/detection/detection_enums.h
  A engines/lilliput/detection/module.mk
  A engines/lure/detection/detection.cpp
  A engines/lure/detection/detection.h
  A engines/lure/detection/detection_enums.h
  A engines/lure/detection/module.mk
  A engines/macventure/detection/detection.cpp
  A engines/macventure/detection/module.mk
  A engines/made/detection/detection.cpp
  A engines/made/detection/detection.h
  A engines/made/detection/detection_enums.h
  A engines/made/detection/detection_tables.h
  A engines/made/detection/module.mk
  A engines/mads/detection/detection.cpp
  A engines/mads/detection/detection.h
  A engines/mads/detection/detection_enums.h
  A engines/mads/detection/detection_tables.h
  A engines/mads/detection/module.mk
  A engines/mohawk/detection/detection.cpp
  A engines/mohawk/detection/detection.h
  A engines/mohawk/detection/detection_enums.h
  A engines/mohawk/detection/detection_tables.h
  A engines/mohawk/detection/module.mk
  A engines/mortevielle/detection/detection.cpp
  A engines/mortevielle/detection/detection.h
  A engines/mortevielle/detection/detection_enums.h
  A engines/mortevielle/detection/detection_tables.h
  A engines/mortevielle/detection/module.mk
  A engines/mutationofjb/detection/detection.cpp
  A engines/mutationofjb/detection/module.mk
  A engines/neverhood/detection/detection.cpp
  A engines/neverhood/detection/detection.h
  A engines/neverhood/detection/module.mk
  A engines/pegasus/detection/detection.cpp
  A engines/pegasus/detection/detection.h
  A engines/pegasus/detection/detection_enums.h
  A engines/pegasus/detection/module.mk
  A engines/petka/detection/detection.cpp
  A engines/petka/detection/detection_tables.h
  A engines/petka/detection/module.mk
  A engines/pink/detection/detection.cpp
  A engines/pink/detection/detection_tables.h
  A engines/pink/detection/module.mk
  A engines/prince/detection/detection.cpp
  A engines/prince/detection/detection.h
  A engines/prince/detection/detection_enums.h
  A engines/prince/detection/module.mk
  A engines/queen/detection/detection.cpp
  A engines/queen/detection/detection.h
  A engines/queen/detection/module.mk
  A engines/saga/detection/detection.cpp
  A engines/saga/detection/detection.h
  A engines/saga/detection/detection_enums.h
  A engines/saga/detection/detection_tables.h
  A engines/saga/detection/module.mk
  A engines/sci/detection/detection.cpp
  A engines/sci/detection/detection_defines.h
  A engines/sci/detection/detection_enums.h
  A engines/sci/detection/detection_tables.h
  A engines/sci/detection/module.mk
  A engines/scumm/detection/detection.cpp
  A engines/scumm/detection/detection.h
  A engines/scumm/detection/detection_internal.h
  A engines/scumm/detection/detection_steam.h
  A engines/scumm/detection/detection_tables.h
  A engines/scumm/detection/module.mk
  A engines/sherlock/detection/detection.cpp
  A engines/sherlock/detection/detection.h
  A engines/sherlock/detection/detection_enums.h
  A engines/sherlock/detection/detection_tables.h
  A engines/sherlock/detection/module.mk
  A engines/sky/detection/detection.cpp
  A engines/sky/detection/module.mk
  A engines/sludge/detection/detection.cpp
  A engines/sludge/detection/detection.h
  A engines/sludge/detection/detection_tables.h
  A engines/sludge/detection/module.mk
  A engines/startrek/detection/detection.cpp
  A engines/startrek/detection/detection.h
  A engines/startrek/detection/detection_enums.h
  A engines/startrek/detection/module.mk
  A engines/supernova/detection/detection.cpp
  A engines/supernova/detection/module.mk
  A engines/sword1/detection/detection.cpp
  A engines/sword1/detection/module.mk
  A engines/sword2/detection/detection.cpp
  A engines/sword2/detection/detection_enums.h
  A engines/sword2/detection/detection_internal.h
  A engines/sword2/detection/module.mk
  A engines/sword25/detection/detection.cpp
  A engines/sword25/detection/detection_enums.h
  A engines/sword25/detection/detection_tables.h
  A engines/sword25/detection/module.mk
  A engines/teenagent/detection/detection.cpp
  A engines/teenagent/detection/module.mk
  A engines/testbed/detection/detection.cpp
  A engines/testbed/detection/module.mk
  A engines/tinsel/detection/detection.cpp
  A engines/tinsel/detection/detection.h
  A engines/tinsel/detection/detection_enums.h
  A engines/tinsel/detection/detection_tables.h
  A engines/tinsel/detection/module.mk
  A engines/titanic/detection/detection.cpp
  A engines/titanic/detection/detection.h
  A engines/titanic/detection/detection_tables.h
  A engines/titanic/detection/module.mk
  A engines/toltecs/detection/detection.cpp
  A engines/toltecs/detection/detection.h
  A engines/toltecs/detection/module.mk
  A engines/tony/detection/detection.cpp
  A engines/tony/detection/detection.h
  A engines/tony/detection/detection_tables.h
  A engines/tony/detection/module.mk
  A engines/toon/detection/detection.cpp
  A engines/toon/detection/module.mk
  A engines/touche/detection/detection.cpp
  A engines/touche/detection/module.mk
  A engines/tsage/detection/detection.cpp
  A engines/tsage/detection/detection.h
  A engines/tsage/detection/detection_enums.h
  A engines/tsage/detection/detection_tables.h
  A engines/tsage/detection/module.mk
  A engines/tucker/detection/detection.cpp
  A engines/tucker/detection/detection_enums.h
  A engines/tucker/detection/module.mk
  A engines/ultima/detection/detection.cpp
  A engines/ultima/detection/detection_tables.h
  A engines/ultima/detection/module.mk
  A engines/voyeur/detection/detection.cpp
  A engines/voyeur/detection/detection.h
  A engines/voyeur/detection/detection_tables.h
  A engines/voyeur/detection/module.mk
  A engines/wage/detection/detection.cpp
  A engines/wage/detection/detection_tables.h
  A engines/wage/detection/module.mk
  A engines/wintermute/detection/detection.cpp
  A engines/wintermute/detection/detection.h
  A engines/wintermute/detection/detection_enums.h
  A engines/wintermute/detection/detection_tables.h
  A engines/wintermute/detection/module.mk
  A engines/xeen/detection/detection.cpp
  A engines/xeen/detection/detection.h
  A engines/xeen/detection/detection_enums.h
  A engines/xeen/detection/detection_tables.h
  A engines/xeen/detection/module.mk
  A engines/zvision/detection/detection.cpp
  A engines/zvision/detection/detection.h
  A engines/zvision/detection/detection_enums.h
  A engines/zvision/detection/detection_tables.h
  A engines/zvision/detection/module.mk
  R engines/access/detection.cpp
  R engines/access/detection.h
  R engines/access/detection_enums.h
  R engines/access/detection_tables.h
  R engines/adl/detection.cpp
  R engines/adl/detection.h
  R engines/adl/detection_enums.h
  R engines/agos/detection.cpp
  R engines/agos/detection.h
  R engines/agos/detection_enums.h
  R engines/agos/detection_tables.h
  R engines/avalanche/detection.cpp
  R engines/avalanche/detection.h
  R engines/bbvs/detection.cpp
  R engines/bbvs/detection_enums.h
  R engines/bladerunner/detection.cpp
  R engines/bladerunner/detection_tables.h
  R engines/cge/detection.cpp
  R engines/cge2/detection.cpp
  R engines/chewy/detection.cpp
  R engines/chewy/detection.h
  R engines/cine/detection.cpp
  R engines/cine/detection.h
  R engines/cine/detection_enums.h
  R engines/cine/detection_tables.h
  R engines/composer/detection.cpp
  R engines/composer/detection.h
  R engines/composer/detection_enums.h
  R engines/composer/detection_tables.h
  R engines/cruise/detection.cpp
  R engines/cruise/detection.h
  R engines/cryo/detection.cpp
  R engines/cryomni3d/detection.cpp
  R engines/cryomni3d/detection.h
  R engines/cryomni3d/detection_enums.h
  R engines/cryomni3d/detection_tables.h
  R engines/director/detection.cpp
  R engines/director/detection.h
  R engines/director/detection_enums.h
  R engines/director/detection_tables.h
  R engines/dm/detection.cpp
  R engines/dm/detection.h
  R engines/dm/detection_enums.h
  R engines/draci/detection.cpp
  R engines/dragons/detection.cpp
  R engines/dragons/detection.h
  R engines/dragons/detection_enums.h
  R engines/drascula/detection.cpp
  R engines/drascula/detection.h
  R engines/drascula/detection_enums.h
  R engines/dreamweb/detection.cpp
  R engines/dreamweb/detection.h
  R engines/dreamweb/detection_tables.h
  R engines/fullpipe/detection.cpp
  R engines/glk/detection.cpp
  R engines/gnap/detection.cpp
  R engines/griffon/detection.cpp
  R engines/groovie/detection.cpp
  R engines/groovie/detection.h
  R engines/groovie/detection_enums.h
  R engines/hdb/detection.cpp
  R engines/hdb/detection_enums.h
  R engines/hopkins/detection.cpp
  R engines/hopkins/detection.h
  R engines/hopkins/detection_tables.h
  R engines/hugo/detection.cpp
  R engines/hugo/detection.h
  R engines/hugo/detection_enums.h
  R engines/illusions/detection.cpp
  R engines/illusions/detection.h
  R engines/illusions/detection_enums.h
  R engines/kingdom/detection.cpp
  R engines/kyra/detection.cpp
  R engines/kyra/detection.h
  R engines/kyra/detection_enums.h
  R engines/kyra/detection_tables.h
  R engines/lab/detection.cpp
  R engines/lab/detection_enums.h
  R engines/lastexpress/detection.cpp
  R engines/lilliput/detection.cpp
  R engines/lilliput/detection.h
  R engines/lilliput/detection_enums.h
  R engines/lure/detection.cpp
  R engines/lure/detection.h
  R engines/lure/detection_enums.h
  R engines/macventure/detection.cpp
  R engines/made/detection.cpp
  R engines/made/detection.h
  R engines/made/detection_enums.h
  R engines/made/detection_tables.h
  R engines/mads/detection.cpp
  R engines/mads/detection.h
  R engines/mads/detection_enums.h
  R engines/mads/detection_tables.h
  R engines/mohawk/detection.cpp
  R engines/mohawk/detection.h
  R engines/mohawk/detection_enums.h
  R engines/mohawk/detection_tables.h
  R engines/mortevielle/detection.cpp
  R engines/mortevielle/detection.h
  R engines/mortevielle/detection_enums.h
  R engines/mortevielle/detection_tables.h
  R engines/mutationofjb/detection.cpp
  R engines/neverhood/detection.cpp
  R engines/neverhood/detection.h
  R engines/pegasus/detection.cpp
  R engines/pegasus/detection.h
  R engines/petka/detection.cpp
  R engines/petka/detection_tables.h
  R engines/pink/detection.cpp
  R engines/pink/detection_tables.h
  R engines/prince/detection.cpp
  R engines/prince/detection.h
  R engines/prince/detection_enums.h
  R engines/queen/detection.cpp
  R engines/queen/detection.h
  R engines/saga/detection.cpp
  R engines/saga/detection.h
  R engines/saga/detection_enums.h
  R engines/saga/detection_tables.h
  R engines/sci/detection.cpp
  R engines/sci/detection_defines.h
  R engines/sci/detection_enums.h
  R engines/sci/detection_tables.h
  R engines/scumm/detection.cpp
  R engines/scumm/detection.h
  R engines/scumm/detection_internal.h
  R engines/scumm/detection_steam.h
  R engines/scumm/detection_tables.h
  R engines/sherlock/detection.cpp
  R engines/sherlock/detection.h
  R engines/sherlock/detection_enums.h
  R engines/sherlock/detection_tables.h
  R engines/sky/detection.cpp
  R engines/sludge/detection.cpp
  R engines/sludge/detection.h
  R engines/sludge/detection_tables.h
  R engines/startrek/detection.cpp
  R engines/startrek/detection.h
  R engines/startrek/detection_enums.h
  R engines/supernova/detection.cpp
  R engines/sword1/detection.cpp
  R engines/sword2/detection.cpp
  R engines/sword2/detection_enums.h
  R engines/sword2/detection_internal.h
  R engines/sword25/detection.cpp
  R engines/sword25/detection_enums.h
  R engines/sword25/detection_tables.h
  R engines/teenagent/detection.cpp
  R engines/testbed/detection.cpp
  R engines/tinsel/detection.cpp
  R engines/tinsel/detection.h
  R engines/tinsel/detection_enums.h
  R engines/tinsel/detection_tables.h
  R engines/titanic/detection.cpp
  R engines/titanic/detection.h
  R engines/titanic/detection_tables.h
  R engines/toltecs/detection.cpp
  R engines/toltecs/detection.h
  R engines/tony/detection.cpp
  R engines/tony/detection.h
  R engines/tony/detection_tables.h
  R engines/toon/detection.cpp
  R engines/touche/detection.cpp
  R engines/tsage/detection.cpp
  R engines/tsage/detection.h
  R engines/tsage/detection_enums.h
  R engines/tsage/detection_tables.h
  R engines/tucker/detection.cpp
  R engines/tucker/detection_enums.h
  R engines/ultima/detection.cpp
  R engines/ultima/detection_tables.h
  R engines/voyeur/detection.cpp
  R engines/voyeur/detection.h
  R engines/voyeur/detection_tables.h
  R engines/wage/detection.cpp
  R engines/wage/detection_tables.h
  R engines/wintermute/detection.cpp
  R engines/wintermute/detection.h
  R engines/wintermute/detection_enums.h
  R engines/wintermute/detection_tables.h
  R engines/xeen/detection.cpp
  R engines/xeen/detection.h
  R engines/xeen/detection_enums.h
  R engines/xeen/detection_tables.h
  R engines/zvision/detection.cpp
  R engines/zvision/detection.h
  R engines/zvision/detection_enums.h
  R engines/zvision/detection_tables.h
    engines/access/access.h
    engines/access/metaengine.cpp
    engines/access/module.mk
    engines/adl/adl.h
    engines/adl/adl_v2.cpp
    engines/adl/hires4.cpp
    engines/adl/hires5.cpp
    engines/adl/metaengine.cpp
    engines/adl/module.mk
    engines/agi/detection/module.mk
    engines/agos/agos.h
    engines/agos/metaengine.cpp
    engines/agos/module.mk
    engines/avalanche/metaengine.cpp
    engines/avalanche/module.mk
    engines/bbvs/bbvs.h
    engines/bbvs/module.mk
    engines/bladerunner/metaengine.cpp
    engines/bladerunner/module.mk
    engines/cge/module.mk
    engines/cge2/module.mk
    engines/chewy/metaengine.cpp
    engines/chewy/module.mk
    engines/cine/cine.h
    engines/cine/metaengine.cpp
    engines/cine/module.mk
    engines/composer/composer.h
    engines/composer/metaengine.cpp
    engines/composer/module.mk
    engines/cruise/metaengine.cpp
    engines/cruise/module.mk
    engines/cryo/module.mk
    engines/cryomni3d/cryomni3d.h
    engines/cryomni3d/metaengine.cpp
    engines/cryomni3d/module.mk
    engines/director/director.h
    engines/director/metaengine.cpp
    engines/director/module.mk
    engines/dm/dm.h
    engines/dm/module.mk
    engines/draci/module.mk
    engines/dragons/dragons.h
    engines/dragons/module.mk
    engines/drascula/drascula.h
    engines/drascula/metaengine.cpp
    engines/drascula/module.mk
    engines/dreamweb/metaengine.cpp
    engines/dreamweb/module.mk
    engines/fullpipe/module.mk
    engines/glk/module.mk
    engines/gnap/module.mk
    engines/gob/module.mk
    engines/griffon/module.mk
    engines/groovie/groovie.cpp
    engines/groovie/groovie.h
    engines/groovie/metaengine.cpp
    engines/groovie/module.mk
    engines/groovie/script.h
    engines/hdb/metaengine.cpp
    engines/hdb/module.mk
    engines/hopkins/metaengine.cpp
    engines/hopkins/module.mk
    engines/hugo/hugo.h
    engines/hugo/metaengine.cpp
    engines/hugo/module.mk
    engines/illusions/illusions.h
    engines/illusions/metaengine.cpp
    engines/illusions/module.mk
    engines/kingdom/module.mk
    engines/kyra/kyra_v1.h
    engines/kyra/metaengine.cpp
    engines/kyra/module.mk
    engines/lab/lab.h
    engines/lab/module.mk
    engines/lastexpress/module.mk
    engines/lilliput/lilliput.h
    engines/lilliput/metaengine.cpp
    engines/lilliput/module.mk
    engines/lure/lure.h
    engines/lure/metaengine.cpp
    engines/lure/module.mk
    engines/macventure/module.mk
    engines/made/made.h
    engines/made/metaengine.cpp
    engines/made/module.mk
    engines/mads/mads.h
    engines/mads/metaengine.cpp
    engines/mads/module.mk
    engines/mohawk/metaengine.cpp
    engines/mohawk/module.mk
    engines/mohawk/mohawk.h
    engines/mortevielle/metaengine.cpp
    engines/mortevielle/module.mk
    engines/mortevielle/mortevielle.h
    engines/mutationofjb/module.mk
    engines/neverhood/metaengine.cpp
    engines/neverhood/module.mk
    engines/pegasus/metaengine.cpp
    engines/pegasus/module.mk
    engines/petka/module.mk
    engines/pink/module.mk
    engines/plumbers/detection/module.mk
    engines/prince/metaengine.cpp
    engines/prince/module.mk
    engines/prince/prince.h
    engines/queen/metaengine.cpp
    engines/queen/module.mk
    engines/saga/metaengine.cpp
    engines/saga/module.mk
    engines/saga/saga.h
    engines/sci/module.mk
    engines/sci/sci.h
    engines/scumm/file.h
    engines/scumm/metaengine.cpp
    engines/scumm/module.mk
    engines/scumm/scumm.cpp
    engines/scumm/scumm.h
    engines/sherlock/metaengine.cpp
    engines/sherlock/module.mk
    engines/sherlock/sherlock.h
    engines/sky/module.mk
    engines/sludge/metaengine.cpp
    engines/sludge/module.mk
    engines/startrek/metaengine.cpp
    engines/startrek/module.mk
    engines/startrek/startrek.h
    engines/supernova/module.mk
    engines/sword1/module.mk
    engines/sword2/metaengine.cpp
    engines/sword2/module.mk
    engines/sword2/sword2.h
    engines/sword25/module.mk
    engines/sword25/sword25.h
    engines/teenagent/module.mk
    engines/testbed/module.mk
    engines/tinsel/metaengine.cpp
    engines/tinsel/module.mk
    engines/tinsel/tinsel.h
    engines/titanic/metaengine.cpp
    engines/titanic/module.mk
    engines/toltecs/metaengine.cpp
    engines/toltecs/module.mk
    engines/tony/metaengine.cpp
    engines/tony/module.mk
    engines/toon/module.mk
    engines/touche/module.mk
    engines/tsage/metaengine.cpp
    engines/tsage/module.mk
    engines/tsage/tsage.h
    engines/tucker/module.mk
    engines/tucker/tucker.h
    engines/ultima/module.mk
    engines/voyeur/metaengine.cpp
    engines/voyeur/module.mk
    engines/wage/module.mk
    engines/wintermute/base/base_sprite.cpp
    engines/wintermute/metaengine.cpp
    engines/wintermute/module.mk
    engines/wintermute/wintermute.cpp
    engines/wintermute/wintermute.h
    engines/xeen/metaengine.cpp
    engines/xeen/module.mk
    engines/xeen/xeen.h
    engines/zvision/metaengine.cpp
    engines/zvision/module.mk
    engines/zvision/zvision.h


diff --git a/engines/access/access.h b/engines/access/access.h
index 26cf6f4f4d..43d5af19b2 100644
--- a/engines/access/access.h
+++ b/engines/access/access.h
@@ -50,7 +50,7 @@
 #include "access/scripts.h"
 #include "access/sound.h"
 #include "access/video.h"
-#include "access/detection_enums.h"
+#include "access/detection/detection_enums.h"
 
 /**
  * This is the namespace of the Access engine.
diff --git a/engines/access/detection.cpp b/engines/access/detection/detection.cpp
similarity index 92%
rename from engines/access/detection.cpp
rename to engines/access/detection/detection.cpp
index e76bc9f163..9b596223c4 100644
--- a/engines/access/detection.cpp
+++ b/engines/access/detection/detection.cpp
@@ -22,8 +22,8 @@
 
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
-#include "access/detection.h"
-#include "access/detection_enums.h"
+#include "access/detection/detection.h"
+#include "access/detection/detection_enums.h"
 
 static const PlainGameDescriptor AccessGames[] = {
 	{"amazon", "Amazon: Guardians of Eden"},
@@ -31,7 +31,7 @@ static const PlainGameDescriptor AccessGames[] = {
 	{0, 0}
 };
 
-#include "access/detection_tables.h"
+#include "access/detection/detection_tables.h"
 
 class AccessMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/access/detection.h b/engines/access/detection/detection.h
similarity index 100%
rename from engines/access/detection.h
rename to engines/access/detection/detection.h
diff --git a/engines/access/detection_enums.h b/engines/access/detection/detection_enums.h
similarity index 100%
rename from engines/access/detection_enums.h
rename to engines/access/detection/detection_enums.h
diff --git a/engines/access/detection_tables.h b/engines/access/detection/detection_tables.h
similarity index 100%
rename from engines/access/detection_tables.h
rename to engines/access/detection/detection_tables.h
diff --git a/engines/access/detection/module.mk b/engines/access/detection/module.mk
new file mode 100644
index 0000000000..e9ed99f685
--- /dev/null
+++ b/engines/access/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/access/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/access/metaengine.cpp b/engines/access/metaengine.cpp
index 3ed66d49f1..8264a563ba 100644
--- a/engines/access/metaengine.cpp
+++ b/engines/access/metaengine.cpp
@@ -32,7 +32,7 @@
 #include "access/amazon/amazon_game.h"
 #include "access/martian/martian_game.h"
 
-#include "access/detection.h"
+#include "access/detection/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/access/module.mk b/engines/access/module.mk
index 03465dd715..db336ec3e2 100644
--- a/engines/access/module.mk
+++ b/engines/access/module.mk
@@ -41,6 +41,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/adl/adl.h b/engines/adl/adl.h
index 1035b41028..f60e3bd987 100644
--- a/engines/adl/adl.h
+++ b/engines/adl/adl.h
@@ -41,7 +41,7 @@
 #include "adl/console.h"
 #include "adl/disk.h"
 #include "adl/sound.h"
-#include "adl/detection_enums.h"
+#include "adl/detection/detection_enums.h"
 
 namespace Common {
 class ReadStream;
diff --git a/engines/adl/adl_v2.cpp b/engines/adl/adl_v2.cpp
index d13455c353..c3baef35f8 100644
--- a/engines/adl/adl_v2.cpp
+++ b/engines/adl/adl_v2.cpp
@@ -26,7 +26,7 @@
 #include "adl/adl_v2.h"
 #include "adl/display.h"
 #include "adl/graphics.h"
-#include "adl/detection_enums.h"
+#include "adl/detection/detection_enums.h"
 
 namespace Adl {
 
diff --git a/engines/adl/detection.cpp b/engines/adl/detection/detection.cpp
similarity index 99%
rename from engines/adl/detection.cpp
rename to engines/adl/detection/detection.cpp
index fcb5b2bcd4..86a345449e 100644
--- a/engines/adl/detection.cpp
+++ b/engines/adl/detection/detection.cpp
@@ -27,8 +27,8 @@
 
 #include "engines/advancedDetector.h"
 
-#include "adl/detection_enums.h"
-#include "adl/detection.h"
+#include "adl/detection/detection_enums.h"
+#include "adl/detection/detection.h"
 #include "adl/disk.h"
 #include "adl/disk_image_helpers.h"
 
diff --git a/engines/adl/detection.h b/engines/adl/detection/detection.h
similarity index 100%
rename from engines/adl/detection.h
rename to engines/adl/detection/detection.h
diff --git a/engines/adl/detection_enums.h b/engines/adl/detection/detection_enums.h
similarity index 100%
rename from engines/adl/detection_enums.h
rename to engines/adl/detection/detection_enums.h
diff --git a/engines/adl/detection/module.mk b/engines/adl/detection/module.mk
new file mode 100644
index 0000000000..8ba9932c22
--- /dev/null
+++ b/engines/adl/detection/module.mk
@@ -0,0 +1,11 @@
+MODULE := engines/adl/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_ADL), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/../disk.o
+endif
diff --git a/engines/adl/hires4.cpp b/engines/adl/hires4.cpp
index b251d44d97..f571b658f9 100644
--- a/engines/adl/hires4.cpp
+++ b/engines/adl/hires4.cpp
@@ -29,7 +29,7 @@
 #include "common/memstream.h"
 
 #include "adl/adl_v3.h"
-#include "adl/detection_enums.h"
+#include "adl/detection/detection_enums.h"
 #include "adl/display_a2.h"
 #include "adl/graphics.h"
 #include "adl/disk.h"
diff --git a/engines/adl/hires5.cpp b/engines/adl/hires5.cpp
index ef8749eedd..350a7a02c2 100644
--- a/engines/adl/hires5.cpp
+++ b/engines/adl/hires5.cpp
@@ -27,7 +27,7 @@
 #include "common/stream.h"
 
 #include "adl/adl_v4.h"
-#include "adl/detection_enums.h"
+#include "adl/detection/detection_enums.h"
 #include "adl/display_a2.h"
 #include "adl/graphics.h"
 #include "adl/disk.h"
diff --git a/engines/adl/metaengine.cpp b/engines/adl/metaengine.cpp
index a7dd3cdf51..195fba010d 100644
--- a/engines/adl/metaengine.cpp
+++ b/engines/adl/metaengine.cpp
@@ -28,8 +28,8 @@
 
 #include "graphics/thumbnail.h"
 
-#include "adl/detection_enums.h"
-#include "adl/detection.h"
+#include "adl/detection/detection_enums.h"
+#include "adl/detection/detection.h"
 #include "adl/disk_image_helpers.h"
 
 namespace Adl {
diff --git a/engines/adl/module.mk b/engines/adl/module.mk
index da28b7016b..df7e3f8dd1 100644
--- a/engines/adl/module.mk
+++ b/engines/adl/module.mk
@@ -28,13 +28,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Only include if building as a dynamic module.
-# Static module already has the contents.
-ifeq ($(ENABLE_ADL), DYNAMIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/disk.o
-endif
diff --git a/engines/agi/detection/module.mk b/engines/agi/detection/module.mk
index 879a2323cf..f25e7061aa 100644
--- a/engines/agi/detection/module.mk
+++ b/engines/agi/detection/module.mk
@@ -1,7 +1,5 @@
 MODULE := engines/agi/detection
 
-MODULE_OBJS :=
-
 # Detection objects
 DETECT_OBJS += $(MODULE)/detection.o
 
diff --git a/engines/agos/agos.h b/engines/agos/agos.h
index eee7406c87..fa32f4fa8c 100644
--- a/engines/agos/agos.h
+++ b/engines/agos/agos.h
@@ -35,7 +35,7 @@
 #include "audio/mixer.h"
 
 #include "agos/vga.h"
-#include "agos/detection_enums.h"
+#include "agos/detection/detection_enums.h"
 
 /**
  * This is the namespace of the AGOS engine.
diff --git a/engines/agos/detection.cpp b/engines/agos/detection/detection.cpp
similarity index 95%
rename from engines/agos/detection.cpp
rename to engines/agos/detection/detection.cpp
index 32dd815412..ca7325dfcc 100644
--- a/engines/agos/detection.cpp
+++ b/engines/agos/detection/detection.cpp
@@ -29,8 +29,8 @@
 #include "common/textconsole.h"
 #include "common/installshield_cab.h"
 
-#include "agos/detection.h"
-#include "agos/detection_enums.h"
+#include "agos/detection/detection.h"
+#include "agos/detection/detection_enums.h"
 #include "agos/intern_detection.h"
 #include "agos/obsolete.h" // Obsolete ID table.
 
@@ -57,7 +57,7 @@ static const PlainGameDescriptor agosGames[] = {
 	{0, 0}
 };
 
-#include "agos/detection_tables.h"
+#include "agos/detection/detection_tables.h"
 
 static const char *const directoryGlobs[] = {
 	"execute", // Used by Simon1 Acorn CD
diff --git a/engines/agos/detection.h b/engines/agos/detection/detection.h
similarity index 100%
rename from engines/agos/detection.h
rename to engines/agos/detection/detection.h
diff --git a/engines/agos/detection_enums.h b/engines/agos/detection/detection_enums.h
similarity index 100%
rename from engines/agos/detection_enums.h
rename to engines/agos/detection/detection_enums.h
diff --git a/engines/agos/detection_tables.h b/engines/agos/detection/detection_tables.h
similarity index 100%
rename from engines/agos/detection_tables.h
rename to engines/agos/detection/detection_tables.h
diff --git a/engines/agos/detection/module.mk b/engines/agos/detection/module.mk
new file mode 100644
index 0000000000..a034c3a3d6
--- /dev/null
+++ b/engines/agos/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/agos/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/agos/metaengine.cpp b/engines/agos/metaengine.cpp
index 7bac156118..8402b67ee9 100644
--- a/engines/agos/metaengine.cpp
+++ b/engines/agos/metaengine.cpp
@@ -30,7 +30,7 @@
 
 #include "agos/intern.h"
 #include "agos/agos.h"
-#include "agos/detection.h"
+#include "agos/detection/detection.h"
 #include "agos/obsolete.h"
 
 class AgosMetaEngineConnect : public AdvancedMetaEngineConnect {
diff --git a/engines/agos/module.mk b/engines/agos/module.mk
index 919f819c1c..4c4c1b77f3 100644
--- a/engines/agos/module.mk
+++ b/engines/agos/module.mk
@@ -69,6 +69,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/avalanche/detection.cpp b/engines/avalanche/detection/detection.cpp
similarity index 98%
rename from engines/avalanche/detection.cpp
rename to engines/avalanche/detection/detection.cpp
index d6baf0f64e..7d8f147248 100644
--- a/engines/avalanche/detection.cpp
+++ b/engines/avalanche/detection/detection.cpp
@@ -30,7 +30,7 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "avalanche/detection.h"
+#include "avalanche/detection/detection.h"
 
 namespace Avalanche {
 
diff --git a/engines/avalanche/detection.h b/engines/avalanche/detection/detection.h
similarity index 100%
rename from engines/avalanche/detection.h
rename to engines/avalanche/detection/detection.h
diff --git a/engines/avalanche/detection/module.mk b/engines/avalanche/detection/module.mk
new file mode 100644
index 0000000000..280c73c519
--- /dev/null
+++ b/engines/avalanche/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/avalanche/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/avalanche/metaengine.cpp b/engines/avalanche/metaengine.cpp
index f004c89964..4e1db1b76c 100644
--- a/engines/avalanche/metaengine.cpp
+++ b/engines/avalanche/metaengine.cpp
@@ -33,7 +33,7 @@
 #include "engines/advancedDetector.h"
 #include "graphics/thumbnail.h"
 
-#include "avalanche/detection.h"
+#include "avalanche/detection/detection.h"
 
 
 namespace Avalanche {
diff --git a/engines/avalanche/module.mk b/engines/avalanche/module.mk
index f8380b9bd1..29fabb76a4 100644
--- a/engines/avalanche/module.mk
+++ b/engines/avalanche/module.mk
@@ -30,6 +30,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/bbvs/bbvs.h b/engines/bbvs/bbvs.h
index d513c679f2..b06b9dc59d 100644
--- a/engines/bbvs/bbvs.h
+++ b/engines/bbvs/bbvs.h
@@ -36,7 +36,7 @@
 
 #include "engines/engine.h"
 
-#include "bbvs/detection_enums.h"
+#include "bbvs/detection/detection_enums.h"
 
 struct ADGameDescription;
 
diff --git a/engines/bbvs/detection.cpp b/engines/bbvs/detection/detection.cpp
similarity index 98%
rename from engines/bbvs/detection.cpp
rename to engines/bbvs/detection/detection.cpp
index af1942f411..6ef2d144ea 100644
--- a/engines/bbvs/detection.cpp
+++ b/engines/bbvs/detection/detection.cpp
@@ -23,7 +23,7 @@
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
 
-#include "bbvs/detection_enums.h"
+#include "bbvs/detection/detection_enums.h"
 
 static const PlainGameDescriptor bbvsGames[] = {
 	{ "bbvs", "Beavis and Butt-head in Virtual Stupidity" },
diff --git a/engines/bbvs/detection_enums.h b/engines/bbvs/detection/detection_enums.h
similarity index 100%
rename from engines/bbvs/detection_enums.h
rename to engines/bbvs/detection/detection_enums.h
diff --git a/engines/bbvs/detection/module.mk b/engines/bbvs/detection/module.mk
new file mode 100644
index 0000000000..89d5fa0194
--- /dev/null
+++ b/engines/bbvs/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/bbvs/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/bbvs/module.mk b/engines/bbvs/module.mk
index e20210494a..1b8c924738 100644
--- a/engines/bbvs/module.mk
+++ b/engines/bbvs/module.mk
@@ -30,6 +30,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/bladerunner/detection.cpp b/engines/bladerunner/detection/detection.cpp
similarity index 98%
rename from engines/bladerunner/detection.cpp
rename to engines/bladerunner/detection/detection.cpp
index ecef2d5b34..dc778f88d2 100644
--- a/engines/bladerunner/detection.cpp
+++ b/engines/bladerunner/detection/detection.cpp
@@ -22,7 +22,7 @@
 
 
 #include "bladerunner/bladerunner.h"
-#include "bladerunner/detection_tables.h"
+#include "bladerunner/detection/detection_tables.h"
 #include "bladerunner/savefile.h"
 
 #include "common/config-manager.h"
diff --git a/engines/bladerunner/detection_tables.h b/engines/bladerunner/detection/detection_tables.h
similarity index 100%
rename from engines/bladerunner/detection_tables.h
rename to engines/bladerunner/detection/detection_tables.h
diff --git a/engines/bladerunner/detection/module.mk b/engines/bladerunner/detection/module.mk
new file mode 100644
index 0000000000..538df57d3f
--- /dev/null
+++ b/engines/bladerunner/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/bladerunner/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/bladerunner/metaengine.cpp b/engines/bladerunner/metaengine.cpp
index 3ed0c04ccf..46d7da01e1 100644
--- a/engines/bladerunner/metaengine.cpp
+++ b/engines/bladerunner/metaengine.cpp
@@ -22,7 +22,6 @@
 
 
 #include "bladerunner/bladerunner.h"
-#include "bladerunner/detection_tables.h"
 #include "bladerunner/savefile.h"
 
 #include "common/config-manager.h"
diff --git a/engines/bladerunner/module.mk b/engines/bladerunner/module.mk
index aae2394a9b..a52b87426f 100644
--- a/engines/bladerunner/module.mk
+++ b/engines/bladerunner/module.mk
@@ -288,6 +288,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cge/detection.cpp b/engines/cge/detection/detection.cpp
similarity index 100%
rename from engines/cge/detection.cpp
rename to engines/cge/detection/detection.cpp
diff --git a/engines/cge/detection/module.mk b/engines/cge/detection/module.mk
new file mode 100644
index 0000000000..a9bdc97733
--- /dev/null
+++ b/engines/cge/detection/module.mk
@@ -0,0 +1,11 @@
+MODULE := engines/cge/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_CGE), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/../fileio.o
+endif
diff --git a/engines/cge/module.mk b/engines/cge/module.mk
index 407e0efa89..cc37bee472 100644
--- a/engines/cge/module.mk
+++ b/engines/cge/module.mk
@@ -27,13 +27,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Only include if building as a dynamic module.
-# Static module already has the contents.
-ifeq ($(ENABLE_CGE), DYNAMIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/fileio.o
-endif
diff --git a/engines/cge2/detection.cpp b/engines/cge2/detection/detection.cpp
similarity index 100%
rename from engines/cge2/detection.cpp
rename to engines/cge2/detection/detection.cpp
diff --git a/engines/cge2/detection/module.mk b/engines/cge2/detection/module.mk
new file mode 100644
index 0000000000..89a8a9d63d
--- /dev/null
+++ b/engines/cge2/detection/module.mk
@@ -0,0 +1,11 @@
+MODULE := engines/cge2/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_CGE2), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/../fileio.o
+endif
diff --git a/engines/cge2/module.mk b/engines/cge2/module.mk
index 208e8ba64b..17604a6194 100644
--- a/engines/cge2/module.mk
+++ b/engines/cge2/module.mk
@@ -28,13 +28,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Only include if building as a dynamic module.
-# Static module already has the contents.
-ifeq ($(ENABLE_CGE2), DYNAMIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/fileio.o
-endif
diff --git a/engines/chewy/detection.cpp b/engines/chewy/detection/detection.cpp
similarity index 98%
rename from engines/chewy/detection.cpp
rename to engines/chewy/detection/detection.cpp
index 17ed3f2b25..16d07d1e5f 100644
--- a/engines/chewy/detection.cpp
+++ b/engines/chewy/detection/detection.cpp
@@ -23,7 +23,7 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "chewy/detection.h"
+#include "chewy/detection/detection.h"
 
 static const PlainGameDescriptor chewyGames[] = {
 	{"chewy", "Chewy: Esc from F5"},
diff --git a/engines/chewy/detection.h b/engines/chewy/detection/detection.h
similarity index 100%
rename from engines/chewy/detection.h
rename to engines/chewy/detection/detection.h
diff --git a/engines/chewy/detection/module.mk b/engines/chewy/detection/module.mk
new file mode 100644
index 0000000000..f7fc8665b2
--- /dev/null
+++ b/engines/chewy/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/chewy/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/chewy/metaengine.cpp b/engines/chewy/metaengine.cpp
index bf14b79ebb..cfd9239cb7 100644
--- a/engines/chewy/metaengine.cpp
+++ b/engines/chewy/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "engines/advancedDetector.h"
 
 #include "chewy/chewy.h"
-#include "chewy/detection.h"
+#include "chewy/detection/detection.h"
 
 namespace Chewy {
 
diff --git a/engines/chewy/module.mk b/engines/chewy/module.mk
index 87d8042c52..e552c48e3a 100644
--- a/engines/chewy/module.mk
+++ b/engines/chewy/module.mk
@@ -20,6 +20,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cine/cine.h b/engines/cine/cine.h
index aec244e440..bab8c6f057 100644
--- a/engines/cine/cine.h
+++ b/engines/cine/cine.h
@@ -48,7 +48,7 @@
 #include "cine/various.h"
 #include "cine/console.h"
 #include "cine/sound.h"
-#include "cine/detection_enums.h"
+#include "cine/detection/detection_enums.h"
 
 //#define DUMP_SCRIPTS
 
diff --git a/engines/cine/detection.cpp b/engines/cine/detection/detection.cpp
similarity index 94%
rename from engines/cine/detection.cpp
rename to engines/cine/detection/detection.cpp
index 311c922507..0b144c5346 100644
--- a/engines/cine/detection.cpp
+++ b/engines/cine/detection/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "common/translation.h"
 
-#include "cine/detection.h"
-#include "cine/detection_enums.h"
+#include "cine/detection/detection.h"
+#include "cine/detection/detection_enums.h"
 
 static const PlainGameDescriptor cineGames[] = {
 	{"fw", "Future Wars"},
@@ -35,7 +35,7 @@ static const PlainGameDescriptor cineGames[] = {
 	{0, 0}
 };
 
-#include "cine/detection_tables.h"
+#include "cine/detection/detection_tables.h"
 
 static const ADExtraGuiOptionsMap optionsList[] = {
 	{
diff --git a/engines/cine/detection.h b/engines/cine/detection/detection.h
similarity index 100%
rename from engines/cine/detection.h
rename to engines/cine/detection/detection.h
diff --git a/engines/cine/detection_enums.h b/engines/cine/detection/detection_enums.h
similarity index 100%
rename from engines/cine/detection_enums.h
rename to engines/cine/detection/detection_enums.h
diff --git a/engines/cine/detection_tables.h b/engines/cine/detection/detection_tables.h
similarity index 100%
rename from engines/cine/detection_tables.h
rename to engines/cine/detection/detection_tables.h
diff --git a/engines/cine/detection/module.mk b/engines/cine/detection/module.mk
new file mode 100644
index 0000000000..7d384f8379
--- /dev/null
+++ b/engines/cine/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/cine/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cine/metaengine.cpp b/engines/cine/metaengine.cpp
index 12c2d0a7bc..19db79d3b6 100644
--- a/engines/cine/metaengine.cpp
+++ b/engines/cine/metaengine.cpp
@@ -32,7 +32,7 @@
 #include "cine/cine.h"
 #include "cine/various.h"
 
-#include "cine/detection.h"
+#include "cine/detection/detection.h"
 
 namespace Cine {
 
diff --git a/engines/cine/module.mk b/engines/cine/module.mk
index 510d3d0043..1c3dfbab46 100644
--- a/engines/cine/module.mk
+++ b/engines/cine/module.mk
@@ -30,6 +30,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/composer/composer.h b/engines/composer/composer.h
index 43716d648b..55759a8360 100644
--- a/engines/composer/composer.h
+++ b/engines/composer/composer.h
@@ -44,7 +44,7 @@
 
 #include "composer/resource.h"
 #include "composer/console.h"
-#include "composer/detection_enums.h"
+#include "composer/detection/detection_enums.h"
 
 namespace Audio {
 	class QueuingAudioStream;
diff --git a/engines/composer/detection.cpp b/engines/composer/detection/detection.cpp
similarity index 93%
rename from engines/composer/detection.cpp
rename to engines/composer/detection/detection.cpp
index 8144d0e17a..e583c6081a 100644
--- a/engines/composer/detection.cpp
+++ b/engines/composer/detection/detection.cpp
@@ -23,8 +23,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "composer/detection_enums.h"
-#include "composer/detection.h"
+#include "composer/detection/detection_enums.h"
+#include "composer/detection/detection.h"
 
 static const PlainGameDescriptor composerGames[] = {
 	{"babayaga", "Magic Tales: Baba Yaga and the Magic Geese"},
@@ -39,7 +39,7 @@ static const PlainGameDescriptor composerGames[] = {
 	{0, 0}
 };
 
-#include "composer/detection_tables.h"
+#include "composer/detection/detection_tables.h"
 
 using namespace Composer;
 
@@ -73,4 +73,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(COMPOSER_DETECTION, PLUGIN_TYPE_METAENGINE, ComposerMetaEngine);
\ No newline at end of file
+REGISTER_PLUGIN_STATIC(COMPOSER_DETECTION, PLUGIN_TYPE_METAENGINE, ComposerMetaEngine);
diff --git a/engines/composer/detection.h b/engines/composer/detection/detection.h
similarity index 100%
rename from engines/composer/detection.h
rename to engines/composer/detection/detection.h
diff --git a/engines/composer/detection_enums.h b/engines/composer/detection/detection_enums.h
similarity index 100%
rename from engines/composer/detection_enums.h
rename to engines/composer/detection/detection_enums.h
diff --git a/engines/composer/detection_tables.h b/engines/composer/detection/detection_tables.h
similarity index 100%
rename from engines/composer/detection_tables.h
rename to engines/composer/detection/detection_tables.h
diff --git a/engines/composer/detection/module.mk b/engines/composer/detection/module.mk
new file mode 100644
index 0000000000..f40bb0242d
--- /dev/null
+++ b/engines/composer/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/composer/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/composer/metaengine.cpp b/engines/composer/metaengine.cpp
index bb70d1bdc4..5460e0e493 100644
--- a/engines/composer/metaengine.cpp
+++ b/engines/composer/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "engines/advancedDetector.h"
 
 #include "composer/composer.h"
-#include "composer/detection.h"
+#include "composer/detection/detection.h"
 
 namespace Composer {
 
diff --git a/engines/composer/module.mk b/engines/composer/module.mk
index 6fdcc59d05..8d0ef0ee2c 100644
--- a/engines/composer/module.mk
+++ b/engines/composer/module.mk
@@ -16,6 +16,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cruise/detection.cpp b/engines/cruise/detection/detection.cpp
similarity index 99%
rename from engines/cruise/detection.cpp
rename to engines/cruise/detection/detection.cpp
index b47cdb59ee..f5772a3b05 100644
--- a/engines/cruise/detection.cpp
+++ b/engines/cruise/detection/detection.cpp
@@ -23,7 +23,7 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "cruise/detection.h"
+#include "cruise/detection/detection.h"
 
 static const PlainGameDescriptor cruiseGames[] = {
 	{"cruise", "Cruise for a Corpse"},
diff --git a/engines/cruise/detection.h b/engines/cruise/detection/detection.h
similarity index 100%
rename from engines/cruise/detection.h
rename to engines/cruise/detection/detection.h
diff --git a/engines/cruise/detection/module.mk b/engines/cruise/detection/module.mk
new file mode 100644
index 0000000000..47f6e46113
--- /dev/null
+++ b/engines/cruise/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/cruise/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cruise/metaengine.cpp b/engines/cruise/metaengine.cpp
index 83abf985fe..3e7d45349a 100644
--- a/engines/cruise/metaengine.cpp
+++ b/engines/cruise/metaengine.cpp
@@ -27,7 +27,7 @@
 
 #include "cruise/cruise.h"
 #include "cruise/saveload.h"
-#include "cruise/detection.h"
+#include "cruise/detection/detection.h"
 
 namespace Cruise {
 
diff --git a/engines/cruise/module.mk b/engines/cruise/module.mk
index 8487ff3ff0..8b8cf3d120 100644
--- a/engines/cruise/module.mk
+++ b/engines/cruise/module.mk
@@ -40,6 +40,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cryo/detection.cpp b/engines/cryo/detection/detection.cpp
similarity index 100%
rename from engines/cryo/detection.cpp
rename to engines/cryo/detection/detection.cpp
diff --git a/engines/cryo/detection/module.mk b/engines/cryo/detection/module.mk
new file mode 100644
index 0000000000..fe3b29d869
--- /dev/null
+++ b/engines/cryo/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/cryo/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cryo/module.mk b/engines/cryo/module.mk
index 11227ac5ee..f99f68814b 100644
--- a/engines/cryo/module.mk
+++ b/engines/cryo/module.mk
@@ -18,6 +18,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cryomni3d/cryomni3d.h b/engines/cryomni3d/cryomni3d.h
index d0dad279cf..51ed23b4af 100644
--- a/engines/cryomni3d/cryomni3d.h
+++ b/engines/cryomni3d/cryomni3d.h
@@ -38,7 +38,7 @@
 #include "cryomni3d/font_manager.h"
 #include "cryomni3d/objects.h"
 #include "cryomni3d/sprites.h"
-#include "cryomni3d/detection_enums.h"
+#include "cryomni3d/detection/detection_enums.h"
 
 class OSystem;
 
diff --git a/engines/cryomni3d/detection.cpp b/engines/cryomni3d/detection/detection.cpp
similarity index 93%
rename from engines/cryomni3d/detection.cpp
rename to engines/cryomni3d/detection/detection.cpp
index bc969065b8..b3f7467a2f 100644
--- a/engines/cryomni3d/detection.cpp
+++ b/engines/cryomni3d/detection/detection.cpp
@@ -27,8 +27,8 @@
 #include "common/file.h"
 #include "common/md5.h"
 
-#include "cryomni3d/detection.h"
-#include "cryomni3d/detection_enums.h"
+#include "cryomni3d/detection/detection.h"
+#include "cryomni3d/detection/detection_enums.h"
 
 namespace CryOmni3D {
 
@@ -37,7 +37,7 @@ static const PlainGameDescriptor cryomni3DGames[] = {
 	{0, 0}
 };
 
-#include "cryomni3d/detection_tables.h"
+#include "cryomni3d/detection/detection_tables.h"
 
 static const ADExtraGuiOptionsMap optionsList[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
diff --git a/engines/cryomni3d/detection.h b/engines/cryomni3d/detection/detection.h
similarity index 100%
rename from engines/cryomni3d/detection.h
rename to engines/cryomni3d/detection/detection.h
diff --git a/engines/cryomni3d/detection_enums.h b/engines/cryomni3d/detection/detection_enums.h
similarity index 100%
rename from engines/cryomni3d/detection_enums.h
rename to engines/cryomni3d/detection/detection_enums.h
diff --git a/engines/cryomni3d/detection_tables.h b/engines/cryomni3d/detection/detection_tables.h
similarity index 100%
rename from engines/cryomni3d/detection_tables.h
rename to engines/cryomni3d/detection/detection_tables.h
diff --git a/engines/cryomni3d/detection/module.mk b/engines/cryomni3d/detection/module.mk
new file mode 100644
index 0000000000..57c244b75e
--- /dev/null
+++ b/engines/cryomni3d/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/cryomni3d/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cryomni3d/metaengine.cpp b/engines/cryomni3d/metaengine.cpp
index edf688c661..94c2b57310 100644
--- a/engines/cryomni3d/metaengine.cpp
+++ b/engines/cryomni3d/metaengine.cpp
@@ -36,7 +36,7 @@
 #include "cryomni3d/versailles/engine.h"
 #endif
 
-#include "cryomni3d/detection.h"
+#include "cryomni3d/detection/detection.h"
 
 namespace CryOmni3D {
 
diff --git a/engines/cryomni3d/module.mk b/engines/cryomni3d/module.mk
index 2b8ed9dc7e..3b6559e6d3 100644
--- a/engines/cryomni3d/module.mk
+++ b/engines/cryomni3d/module.mk
@@ -39,6 +39,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/director/detection.cpp b/engines/director/detection/detection.cpp
similarity index 98%
rename from engines/director/detection.cpp
rename to engines/director/detection/detection.cpp
index 662ee94b83..9791adddcd 100644
--- a/engines/director/detection.cpp
+++ b/engines/director/detection/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "common/file.h"
 
-#include "director/detection_enums.h"
-#include "director/detection.h"
+#include "director/detection/detection_enums.h"
+#include "director/detection/detection.h"
 
 static const PlainGameDescriptor directorGames[] = {
 	{ "director",			"Macromedia Director Game" },
@@ -166,7 +166,7 @@ static const PlainGameDescriptor directorGames[] = {
 	{ 0, 0 }
 };
 
-#include "director/detection_tables.h"
+#include "director/detection/detection_tables.h"
 
 static const char *directoryGlobs[] = {
 	"install",
diff --git a/engines/director/detection.h b/engines/director/detection/detection.h
similarity index 100%
rename from engines/director/detection.h
rename to engines/director/detection/detection.h
diff --git a/engines/director/detection_enums.h b/engines/director/detection/detection_enums.h
similarity index 100%
rename from engines/director/detection_enums.h
rename to engines/director/detection/detection_enums.h
diff --git a/engines/director/detection_tables.h b/engines/director/detection/detection_tables.h
similarity index 100%
rename from engines/director/detection_tables.h
rename to engines/director/detection/detection_tables.h
diff --git a/engines/director/detection/module.mk b/engines/director/detection/module.mk
new file mode 100644
index 0000000000..8e1b03908c
--- /dev/null
+++ b/engines/director/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/director/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/director/director.h b/engines/director/director.h
index 1b20960b97..ef56ebe24a 100644
--- a/engines/director/director.h
+++ b/engines/director/director.h
@@ -36,7 +36,7 @@
 
 #include "director/types.h"
 #include "director/util.h"
-#include "director/detection_enums.h"
+#include "director/detection/detection_enums.h"
 
 namespace Common {
 class MacResManager;
diff --git a/engines/director/metaengine.cpp b/engines/director/metaengine.cpp
index 15f4313e56..607ae0acce 100644
--- a/engines/director/metaengine.cpp
+++ b/engines/director/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "common/config-manager.h"
 
 #include "director/director.h"
-#include "director/detection.h"
+#include "director/detection/detection.h"
 
 namespace Director {
 
diff --git a/engines/director/module.mk b/engines/director/module.mk
index 508ea8707a..65f8e86598 100644
--- a/engines/director/module.mk
+++ b/engines/director/module.mk
@@ -51,6 +51,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dm/detection.cpp b/engines/dm/detection/detection.cpp
similarity index 97%
rename from engines/dm/detection.cpp
rename to engines/dm/detection/detection.cpp
index aa051815f8..bbe2db53b7 100644
--- a/engines/dm/detection.cpp
+++ b/engines/dm/detection/detection.cpp
@@ -29,8 +29,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "dm/detection_enums.h"
-#include "dm/detection.h"
+#include "dm/detection/detection_enums.h"
+#include "dm/detection/detection.h"
 
 namespace DM {
 
diff --git a/engines/dm/detection.h b/engines/dm/detection/detection.h
similarity index 100%
rename from engines/dm/detection.h
rename to engines/dm/detection/detection.h
diff --git a/engines/dm/detection_enums.h b/engines/dm/detection/detection_enums.h
similarity index 100%
rename from engines/dm/detection_enums.h
rename to engines/dm/detection/detection_enums.h
diff --git a/engines/dm/detection/module.mk b/engines/dm/detection/module.mk
new file mode 100644
index 0000000000..f93250e3ed
--- /dev/null
+++ b/engines/dm/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/dm/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dm/dm.h b/engines/dm/dm.h
index 029b671c23..fa1d49a15d 100644
--- a/engines/dm/dm.h
+++ b/engines/dm/dm.h
@@ -39,8 +39,8 @@
 #include "advancedDetector.h"
 
 #include "dm/console.h"
-#include "dm/detection_enums.h"
-#include "dm/detection.h"
+#include "dm/detection/detection_enums.h"
+#include "dm/detection/detection.h"
 
 struct ADGameDescription;
 
diff --git a/engines/dm/module.mk b/engines/dm/module.mk
index 95688dada9..51ec4ecef8 100644
--- a/engines/dm/module.mk
+++ b/engines/dm/module.mk
@@ -60,6 +60,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/draci/detection.cpp b/engines/draci/detection/detection.cpp
similarity index 100%
rename from engines/draci/detection.cpp
rename to engines/draci/detection/detection.cpp
diff --git a/engines/draci/detection/module.mk b/engines/draci/detection/module.mk
new file mode 100644
index 0000000000..238f621d72
--- /dev/null
+++ b/engines/draci/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/draci/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/draci/module.mk b/engines/draci/module.mk
index 43afb8cbe3..f6ad32af8e 100644
--- a/engines/draci/module.mk
+++ b/engines/draci/module.mk
@@ -25,6 +25,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dragons/detection.cpp b/engines/dragons/detection/detection.cpp
similarity index 97%
rename from engines/dragons/detection.cpp
rename to engines/dragons/detection/detection.cpp
index 75c6f1861a..1cf5fa5bf0 100644
--- a/engines/dragons/detection.cpp
+++ b/engines/dragons/detection/detection.cpp
@@ -22,8 +22,8 @@
 
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
-#include "dragons/detection_enums.h"
-#include "dragons/detection.h"
+#include "dragons/detection/detection_enums.h"
+#include "dragons/detection/detection.h"
 
 static const PlainGameDescriptor dragonsGames[] = {
 		{ "dragons", "Blazing Dragons" },
diff --git a/engines/dragons/detection.h b/engines/dragons/detection/detection.h
similarity index 100%
rename from engines/dragons/detection.h
rename to engines/dragons/detection/detection.h
diff --git a/engines/dragons/detection_enums.h b/engines/dragons/detection/detection_enums.h
similarity index 100%
rename from engines/dragons/detection_enums.h
rename to engines/dragons/detection/detection_enums.h
diff --git a/engines/dragons/detection/module.mk b/engines/dragons/detection/module.mk
new file mode 100644
index 0000000000..d3c27c1b3c
--- /dev/null
+++ b/engines/dragons/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/dragons/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dragons/dragons.h b/engines/dragons/dragons.h
index c3b2883c93..e301b88ff6 100644
--- a/engines/dragons/dragons.h
+++ b/engines/dragons/dragons.h
@@ -25,8 +25,8 @@
 #include "gui/EventRecorder.h"
 #include "engines/engine.h"
 #include "dragons/specialopcodes.h"
-#include "dragons/detection_enums.h"
-#include "dragons/detection.h"
+#include "dragons/detection/detection_enums.h"
+#include "dragons/detection/detection.h"
 
 namespace Dragons {
 
diff --git a/engines/dragons/module.mk b/engines/dragons/module.mk
index e05786f525..edb6d20443 100644
--- a/engines/dragons/module.mk
+++ b/engines/dragons/module.mk
@@ -43,6 +43,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/drascula/detection.cpp b/engines/drascula/detection/detection.cpp
similarity index 98%
rename from engines/drascula/detection.cpp
rename to engines/drascula/detection/detection.cpp
index d8eb9b0a5a..e3aae16c9d 100644
--- a/engines/drascula/detection.cpp
+++ b/engines/drascula/detection/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "engines/advancedDetector.h"
 
-#include "drascula/detection_enums.h"
-#include "drascula/detection.h"
+#include "drascula/detection/detection_enums.h"
+#include "drascula/detection/detection.h"
 
 static const PlainGameDescriptor drasculaGames[] = {
 	{"drascula", "Drascula: The Vampire Strikes Back"},
diff --git a/engines/drascula/detection.h b/engines/drascula/detection/detection.h
similarity index 100%
rename from engines/drascula/detection.h
rename to engines/drascula/detection/detection.h
diff --git a/engines/drascula/detection_enums.h b/engines/drascula/detection/detection_enums.h
similarity index 100%
rename from engines/drascula/detection_enums.h
rename to engines/drascula/detection/detection_enums.h
diff --git a/engines/drascula/detection/module.mk b/engines/drascula/detection/module.mk
new file mode 100644
index 0000000000..275ec6b460
--- /dev/null
+++ b/engines/drascula/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/drascula/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/drascula/drascula.h b/engines/drascula/drascula.h
index 749f9c3033..c1b2c9bc86 100644
--- a/engines/drascula/drascula.h
+++ b/engines/drascula/drascula.h
@@ -39,7 +39,7 @@
 #include "engines/savestate.h"
 
 #include "drascula/console.h"
-#include "drascula/detection_enums.h"
+#include "drascula/detection/detection_enums.h"
 
 #include "audio/mixer.h"
 
diff --git a/engines/drascula/metaengine.cpp b/engines/drascula/metaengine.cpp
index ec732a512b..1adb8068e5 100644
--- a/engines/drascula/metaengine.cpp
+++ b/engines/drascula/metaengine.cpp
@@ -26,7 +26,7 @@
 #include "graphics/thumbnail.h"
 
 #include "drascula/drascula.h"
-#include "drascula/detection.h"
+#include "drascula/detection/detection.h"
 
 namespace Drascula {
 
diff --git a/engines/drascula/module.mk b/engines/drascula/module.mk
index 46dae3e731..3d2bf5ad37 100644
--- a/engines/drascula/module.mk
+++ b/engines/drascula/module.mk
@@ -25,6 +25,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dreamweb/detection.cpp b/engines/dreamweb/detection/detection.cpp
similarity index 96%
rename from engines/dreamweb/detection.cpp
rename to engines/dreamweb/detection/detection.cpp
index 19e9a502a1..ed5572bb1a 100644
--- a/engines/dreamweb/detection.cpp
+++ b/engines/dreamweb/detection/detection.cpp
@@ -28,14 +28,14 @@
 
 #include "engines/advancedDetector.h"
 
-#include "dreamweb/detection.h"
+#include "dreamweb/detection/detection.h"
 
 static const PlainGameDescriptor dreamWebGames[] = {
 	{ "dreamweb", "DreamWeb" },
 	{ 0, 0 }
 };
 
-#include "dreamweb/detection_tables.h"
+#include "dreamweb/detection/detection_tables.h"
 
 static const ADExtraGuiOptionsMap gameGuiOptions[] = {
 	{
diff --git a/engines/dreamweb/detection.h b/engines/dreamweb/detection/detection.h
similarity index 100%
rename from engines/dreamweb/detection.h
rename to engines/dreamweb/detection/detection.h
diff --git a/engines/dreamweb/detection_tables.h b/engines/dreamweb/detection/detection_tables.h
similarity index 99%
rename from engines/dreamweb/detection_tables.h
rename to engines/dreamweb/detection/detection_tables.h
index 73802e862e..651b07fe22 100644
--- a/engines/dreamweb/detection_tables.h
+++ b/engines/dreamweb/detection/detection_tables.h
@@ -23,7 +23,7 @@
 #ifndef DREAMWEB_DETECTION_TABLES_H
 #define DREAMWEB_DETECTION_TABLES_H
 
-#include "dreamweb/detection.h"
+#include "dreamweb/detection/detection.h"
 
 namespace DreamWeb {
 
diff --git a/engines/dreamweb/detection/module.mk b/engines/dreamweb/detection/module.mk
new file mode 100644
index 0000000000..7554d6e4a4
--- /dev/null
+++ b/engines/dreamweb/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/dreamweb/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dreamweb/metaengine.cpp b/engines/dreamweb/metaengine.cpp
index 1d7a1c213f..80acb819dc 100644
--- a/engines/dreamweb/metaengine.cpp
+++ b/engines/dreamweb/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "engines/advancedDetector.h"
 
 #include "dreamweb/dreamweb.h"
-#include "dreamweb/detection.h"
+#include "dreamweb/detection/detection.h"
 
 class DreamWebMetaEngineConnect : public AdvancedMetaEngineConnect {
 public:
diff --git a/engines/dreamweb/module.mk b/engines/dreamweb/module.mk
index d3c0f48a2a..15966d81b2 100644
--- a/engines/dreamweb/module.mk
+++ b/engines/dreamweb/module.mk
@@ -31,6 +31,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/fullpipe/detection.cpp b/engines/fullpipe/detection/detection.cpp
similarity index 100%
rename from engines/fullpipe/detection.cpp
rename to engines/fullpipe/detection/detection.cpp
diff --git a/engines/fullpipe/detection/module.mk b/engines/fullpipe/detection/module.mk
new file mode 100644
index 0000000000..cd09772f65
--- /dev/null
+++ b/engines/fullpipe/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/fullpipe/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/fullpipe/module.mk b/engines/fullpipe/module.mk
index 3e59fdcb79..232ab076db 100644
--- a/engines/fullpipe/module.mk
+++ b/engines/fullpipe/module.mk
@@ -75,6 +75,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/glk/detection.cpp b/engines/glk/detection/detection.cpp
similarity index 100%
rename from engines/glk/detection.cpp
rename to engines/glk/detection/detection.cpp
diff --git a/engines/glk/detection/module.mk b/engines/glk/detection/module.mk
new file mode 100644
index 0000000000..1608485f0a
--- /dev/null
+++ b/engines/glk/detection/module.mk
@@ -0,0 +1,30 @@
+MODULE := engines/glk/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Sub-engine detection objects
+DETECT_OBJS += $(MODULE)/../adrift/detection.o
+DETECT_OBJS += $(MODULE)/../advsys/detection.o
+DETECT_OBJS += $(MODULE)/../agt/detection.o
+DETECT_OBJS += $(MODULE)/../alan2/detection.o
+DETECT_OBJS += $(MODULE)/../alan3/detection.o
+DETECT_OBJS += $(MODULE)/../archetype/detection.o
+DETECT_OBJS += $(MODULE)/../comprehend/detection.o
+DETECT_OBJS += $(MODULE)/../glulx/detection.o
+DETECT_OBJS += $(MODULE)/../hugo/detection.o
+DETECT_OBJS += $(MODULE)/../jacl/detection.o
+DETECT_OBJS += $(MODULE)/../level9/detection.o
+DETECT_OBJS += $(MODULE)/../magnetic/detection.o
+DETECT_OBJS += $(MODULE)/../quest/detection.o
+DETECT_OBJS += $(MODULE)/../scott/detection.o
+DETECT_OBJS += $(MODULE)/../tads/detection.o
+DETECT_OBJS += $(MODULE)/../zcode/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_GLK), STATIC_PLUGIN)
+# Dependencies of detection objects
+DETECT_OBJS += $(MODULE)/../blorb.o
+DETECT_OBJS += $(MODULE)/../advsys/game.o
+endif
diff --git a/engines/glk/module.mk b/engines/glk/module.mk
index 4153863dbb..8b6eee35d4 100644
--- a/engines/glk/module.mk
+++ b/engines/glk/module.mk
@@ -29,7 +29,6 @@ MODULE_OBJS := \
 	window_text_buffer.o \
 	window_text_grid.o \
 	adrift/adrift.o \
-	adrift/detection.o \
 	adrift/os_glk.o \
 	adrift/scdebug.o \
 	adrift/scevents.o \
@@ -57,7 +56,6 @@ MODULE_OBJS := \
 	adrift/sxglob.o \
 	adrift/sxutils.o \
 	advsys/advsys.o \
-	advsys/detection.o \
 	advsys/game.o \
 	advsys/glk_interface.o \
 	advsys/vm.o \
@@ -67,7 +65,6 @@ MODULE_OBJS := \
 	agt/agxfile.o \
 	agt/auxfile.o \
 	agt/debugcmd.o \
-	agt/detection.o \
 	agt/disassemble.o \
 	agt/exec.o \
 	agt/filename.o \
@@ -83,7 +80,6 @@ MODULE_OBJS := \
 	agt/util.o \
 	agt/vars.o \
 	alan2/alan2.o \
-	alan2/detection.o \
 	alan2/alan_version.o \
 	alan2/args.o \
 	alan2/debug.o \
@@ -113,7 +109,6 @@ MODULE_OBJS := \
 	alan3/current.o \
 	alan3/debug.o \
 	alan3/decode.o \
-	alan3/detection.o \
 	alan3/dictionary.o \
 	alan3/event.o \
 	alan3/exe.o \
@@ -150,7 +145,6 @@ MODULE_OBJS := \
 	archetype/archetype.o \
 	archetype/array.o \
 	archetype/crypt.o \
-	archetype/detection.o \
 	archetype/error.o \
 	archetype/expression.o \
 	archetype/game_stat.o \
@@ -171,7 +165,6 @@ MODULE_OBJS := \
 	comprehend/comprehend.o \
 	comprehend/debugger.o \
 	comprehend/debugger_dumper.o \
-	comprehend/detection.o \
 	comprehend/dictionary.o \
 	comprehend/draw_surface.o \
 	comprehend/file_buf.o \
@@ -184,7 +177,6 @@ MODULE_OBJS := \
 	comprehend/opcode_map.o \
 	comprehend/pics.o \
 	glulx/accel.o \
-	glulx/detection.o \
 	glulx/exec.o \
 	glulx/float.o \
 	glulx/funcs.o \
@@ -197,7 +189,6 @@ MODULE_OBJS := \
 	glulx/serial.o \
 	glulx/string.o \
 	glulx/vm.o \
-	hugo/detection.o \
 	hugo/heexpr.o \
 	hugo/heglk.o \
 	hugo/hemedia.o \
@@ -211,7 +202,6 @@ MODULE_OBJS := \
 	hugo/hugo.o \
 	hugo/resource_archive.o \
 	hugo/stringfn.o \
-	jacl/detection.o \
 	jacl/display.o \
 	jacl/encapsulate.o \
 	jacl/errors.o \
@@ -228,15 +218,12 @@ MODULE_OBJS := \
 	jacl/resolvers.o \
 	jacl/utils.o \
 	level9/bitmap.o \
-	level9/detection.o \
 	level9/level9.o \
 	level9/level9_main.o \
 	level9/os_glk.o \
-	magnetic/detection.o \
 	magnetic/emu.o \
 	magnetic/glk.o \
 	magnetic/magnetic.o \
-	quest/detection.o \
 	quest/geas_file.o \
 	quest/geas_glk.o \
 	quest/geas_runner.o \
@@ -246,9 +233,7 @@ MODULE_OBJS := \
 	quest/read_file.o \
 	quest/string.o \
 	quest/streams.o \
-	scott/detection.o \
 	scott/scott.o \
-	tads/detection.o \
 	tads/os_banners.o \
 	tads/os_buffer.o \
 	tads/os_glk.o \
@@ -291,7 +276,6 @@ MODULE_OBJS := \
 	tads/tads3/tads3.o \
 	zcode/bitmap_font.o \
 	zcode/config.o \
-	zcode/detection.o \
 	zcode/zcode.o \
 	zcode/glk_interface.o \
 	zcode/mem.o \
@@ -321,33 +305,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# If building as static, skip the below, as
-# they're already in the executable.
-
-ifeq ($(ENABLE_GLK), DYNAMIC_PLUGIN)
-# Sub-engine detection objects
-DETECT_OBJS += $(MODULE)/adrift/detection.o
-DETECT_OBJS += $(MODULE)/advsys/detection.o
-DETECT_OBJS += $(MODULE)/agt/detection.o
-DETECT_OBJS += $(MODULE)/alan2/detection.o
-DETECT_OBJS += $(MODULE)/alan3/detection.o
-DETECT_OBJS += $(MODULE)/archetype/detection.o
-DETECT_OBJS += $(MODULE)/comprehend/detection.o
-DETECT_OBJS += $(MODULE)/glulx/detection.o
-DETECT_OBJS += $(MODULE)/hugo/detection.o
-DETECT_OBJS += $(MODULE)/jacl/detection.o
-DETECT_OBJS += $(MODULE)/level9/detection.o
-DETECT_OBJS += $(MODULE)/magnetic/detection.o
-DETECT_OBJS += $(MODULE)/quest/detection.o
-DETECT_OBJS += $(MODULE)/scott/detection.o
-DETECT_OBJS += $(MODULE)/tads/detection.o
-DETECT_OBJS += $(MODULE)/zcode/detection.o
-
-# Dependencies of detection objects
-DETECT_OBJS += $(MODULE)/blorb.o
-DETECT_OBJS += $(MODULE)/advsys/game.o
-endif
diff --git a/engines/gnap/detection.cpp b/engines/gnap/detection/detection.cpp
similarity index 100%
rename from engines/gnap/detection.cpp
rename to engines/gnap/detection/detection.cpp
diff --git a/engines/gnap/detection/module.mk b/engines/gnap/detection/module.mk
new file mode 100644
index 0000000000..950a149cbd
--- /dev/null
+++ b/engines/gnap/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/gnap/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/gnap/module.mk b/engines/gnap/module.mk
index 14f3aa5003..6e91598a4f 100644
--- a/engines/gnap/module.mk
+++ b/engines/gnap/module.mk
@@ -30,6 +30,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/gob/detection/module.mk b/engines/gob/detection/module.mk
new file mode 100644
index 0000000000..43211a9832
--- /dev/null
+++ b/engines/gob/detection/module.mk
@@ -0,0 +1,11 @@
+MODULE := engines/gob/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_GOB), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/../dataio.o
+endif
diff --git a/engines/gob/module.mk b/engines/gob/module.mk
index 171c935262..b3980f4d7f 100644
--- a/engines/gob/module.mk
+++ b/engines/gob/module.mk
@@ -133,13 +133,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection/detection.o
-
-# Only include if building as a dynamic module.
-# Static module already has the contents.
-ifeq ($(ENABLE_GOB), DYNAMIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/dataio.o
-endif
diff --git a/engines/griffon/detection.cpp b/engines/griffon/detection/detection.cpp
similarity index 100%
rename from engines/griffon/detection.cpp
rename to engines/griffon/detection/detection.cpp
diff --git a/engines/griffon/detection/module.mk b/engines/griffon/detection/module.mk
new file mode 100644
index 0000000000..7c70709aeb
--- /dev/null
+++ b/engines/griffon/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/griffon/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/griffon/module.mk b/engines/griffon/module.mk
index a3ed512096..503571321b 100644
--- a/engines/griffon/module.mk
+++ b/engines/griffon/module.mk
@@ -26,6 +26,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/groovie/detection.cpp b/engines/groovie/detection/detection.cpp
similarity index 99%
rename from engines/groovie/detection.cpp
rename to engines/groovie/detection/detection.cpp
index c607181551..67d908090c 100644
--- a/engines/groovie/detection.cpp
+++ b/engines/groovie/detection/detection.cpp
@@ -24,8 +24,8 @@
 #include "common/translation.h"
 
 #include "engines/advancedDetector.h"
-#include "groovie/detection_enums.h"
-#include "groovie/detection.h"
+#include "groovie/detection/detection_enums.h"
+#include "groovie/detection/detection.h"
 
 namespace Groovie {
 
diff --git a/engines/groovie/detection.h b/engines/groovie/detection/detection.h
similarity index 100%
rename from engines/groovie/detection.h
rename to engines/groovie/detection/detection.h
diff --git a/engines/groovie/detection_enums.h b/engines/groovie/detection/detection_enums.h
similarity index 100%
rename from engines/groovie/detection_enums.h
rename to engines/groovie/detection/detection_enums.h
diff --git a/engines/groovie/detection/module.mk b/engines/groovie/detection/module.mk
new file mode 100644
index 0000000000..f799e077ac
--- /dev/null
+++ b/engines/groovie/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/groovie/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/groovie/groovie.cpp b/engines/groovie/groovie.cpp
index f44a0a2759..1adb247276 100644
--- a/engines/groovie/groovie.cpp
+++ b/engines/groovie/groovie.cpp
@@ -22,7 +22,7 @@
 
 #include "groovie/groovie.h"
 #include "groovie/cursor.h"
-#include "groovie/detection.h"
+#include "groovie/detection/detection.h"
 #include "groovie/graphics.h"
 #include "groovie/script.h"
 #include "groovie/music.h"
diff --git a/engines/groovie/groovie.h b/engines/groovie/groovie.h
index 4d26552bf8..7c314f6c88 100644
--- a/engines/groovie/groovie.h
+++ b/engines/groovie/groovie.h
@@ -28,7 +28,7 @@
 
 #include "engines/engine.h"
 #include "graphics/pixelformat.h"
-#include "groovie/detection_enums.h"
+#include "groovie/detection/detection_enums.h"
 
 namespace Common {
 class MacResManager;
diff --git a/engines/groovie/metaengine.cpp b/engines/groovie/metaengine.cpp
index 316237f6a7..ac01717257 100644
--- a/engines/groovie/metaengine.cpp
+++ b/engines/groovie/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "common/translation.h"
 
 #include "engines/advancedDetector.h"
-#include "groovie/detection.h"
+#include "groovie/detection/detection.h"
 
 namespace Groovie {
 
diff --git a/engines/groovie/module.mk b/engines/groovie/module.mk
index b01ac47a11..58ae8d8bc8 100644
--- a/engines/groovie/module.mk
+++ b/engines/groovie/module.mk
@@ -29,6 +29,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/groovie/script.h b/engines/groovie/script.h
index 4b82a8ef50..9a8e3a4d51 100644
--- a/engines/groovie/script.h
+++ b/engines/groovie/script.h
@@ -24,7 +24,7 @@
 #define GROOVIE_SCRIPT_H
 
 #include "groovie/groovie.h"
-#include "groovie/detection_enums.h"
+#include "groovie/detection/detection_enums.h"
 
 #include "common/random.h"
 #include "common/rect.h"
diff --git a/engines/hdb/detection.cpp b/engines/hdb/detection/detection.cpp
similarity index 98%
rename from engines/hdb/detection.cpp
rename to engines/hdb/detection/detection.cpp
index 8f995787ae..1df1eb263b 100644
--- a/engines/hdb/detection.cpp
+++ b/engines/hdb/detection/detection.cpp
@@ -24,7 +24,7 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "hdb/detection_enums.h"
+#include "hdb/detection/detection_enums.h"
 
 static const PlainGameDescriptor hdbGames[] = {
 	{"hdb", "Hyperspace Delivery Boy!"},
diff --git a/engines/hdb/detection/detection_enums.h b/engines/hdb/detection/detection_enums.h
new file mode 100644
index 0000000000..ebe2aeff5b
--- /dev/null
+++ b/engines/hdb/detection/detection_enums.h
@@ -0,0 +1,29 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+namespace HDB {
+
+enum HDBGameFeatures {
+	GF_HANDANGO = (1 << 0)
+};
+
+} // End of namespace HDB
diff --git a/engines/hdb/detection/module.mk b/engines/hdb/detection/module.mk
new file mode 100644
index 0000000000..d5388c2fe8
--- /dev/null
+++ b/engines/hdb/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/hdb/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hdb/detection_enums.h b/engines/hdb/detection_enums.h
deleted file mode 100644
index 6ff21969d1..0000000000
--- a/engines/hdb/detection_enums.h
+++ /dev/null
@@ -1,9 +0,0 @@
-
-
-namespace HDB {
-
-enum HDBGameFeatures {
-	GF_HANDANGO = (1 << 0)
-};
-
-} // End of namespace HDB
\ No newline at end of file
diff --git a/engines/hdb/metaengine.cpp b/engines/hdb/metaengine.cpp
index a83a0402fa..f0ae2379c9 100644
--- a/engines/hdb/metaengine.cpp
+++ b/engines/hdb/metaengine.cpp
@@ -34,7 +34,7 @@
 
 #include "hdb/hdb.h"
 #include "hdb/input.h"
-#include "hdb/detection_enums.h"
+#include "hdb/detection/detection_enums.h"
 
 namespace HDB {
 
diff --git a/engines/hdb/module.mk b/engines/hdb/module.mk
index 24cc53bd41..9e78f1e874 100644
--- a/engines/hdb/module.mk
+++ b/engines/hdb/module.mk
@@ -32,6 +32,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hopkins/detection.cpp b/engines/hopkins/detection/detection.cpp
similarity index 96%
rename from engines/hopkins/detection.cpp
rename to engines/hopkins/detection/detection.cpp
index 97fcb86eb9..753d2c9d6f 100644
--- a/engines/hopkins/detection.cpp
+++ b/engines/hopkins/detection/detection.cpp
@@ -24,14 +24,14 @@
 #include "engines/advancedDetector.h"
 #include "common/translation.h"
 
-#include "hopkins/detection.h"
+#include "hopkins/detection/detection.h"
 
 static const PlainGameDescriptor hopkinsGames[] = {
 	{"hopkins", "Hopkins FBI"},
 	{0, 0}
 };
 
-#include "hopkins/detection_tables.h"
+#include "hopkins/detection/detection_tables.h"
 
 static const ADExtraGuiOptionsMap optionsList[] = {
 	{
diff --git a/engines/hopkins/detection.h b/engines/hopkins/detection/detection.h
similarity index 100%
rename from engines/hopkins/detection.h
rename to engines/hopkins/detection/detection.h
diff --git a/engines/hopkins/detection_tables.h b/engines/hopkins/detection/detection_tables.h
similarity index 100%
rename from engines/hopkins/detection_tables.h
rename to engines/hopkins/detection/detection_tables.h
diff --git a/engines/hopkins/detection/module.mk b/engines/hopkins/detection/module.mk
new file mode 100644
index 0000000000..14d10d93a1
--- /dev/null
+++ b/engines/hopkins/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/hopkins/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hopkins/metaengine.cpp b/engines/hopkins/metaengine.cpp
index bc07ba1599..58814f1e1e 100644
--- a/engines/hopkins/metaengine.cpp
+++ b/engines/hopkins/metaengine.cpp
@@ -31,7 +31,7 @@
 #include "common/translation.h"
 #include "graphics/surface.h"
 
-#include "hopkins/detection.h"
+#include "hopkins/detection/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/hopkins/module.mk b/engines/hopkins/module.mk
index 2110a45e2c..67525a05b8 100644
--- a/engines/hopkins/module.mk
+++ b/engines/hopkins/module.mk
@@ -27,6 +27,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hugo/detection.cpp b/engines/hugo/detection/detection.cpp
similarity index 97%
rename from engines/hugo/detection.cpp
rename to engines/hugo/detection/detection.cpp
index 1b261eeb2d..9f6f47135e 100644
--- a/engines/hugo/detection.cpp
+++ b/engines/hugo/detection/detection.cpp
@@ -23,8 +23,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "hugo/detection_enums.h"
-#include "hugo/detection.h"
+#include "hugo/detection/detection_enums.h"
+#include "hugo/detection/detection.h"
 
 namespace Hugo {
 
diff --git a/engines/hugo/detection.h b/engines/hugo/detection/detection.h
similarity index 100%
rename from engines/hugo/detection.h
rename to engines/hugo/detection/detection.h
diff --git a/engines/hugo/detection_enums.h b/engines/hugo/detection/detection_enums.h
similarity index 100%
rename from engines/hugo/detection_enums.h
rename to engines/hugo/detection/detection_enums.h
diff --git a/engines/hugo/detection/module.mk b/engines/hugo/detection/module.mk
new file mode 100644
index 0000000000..ad62659f74
--- /dev/null
+++ b/engines/hugo/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/hugo/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hugo/hugo.h b/engines/hugo/hugo.h
index 288d73b20c..e58caffcc7 100644
--- a/engines/hugo/hugo.h
+++ b/engines/hugo/hugo.h
@@ -27,7 +27,7 @@
 
 // This include is here temporarily while the engine is being refactored.
 #include "hugo/game.h"
-#include "hugo/detection_enums.h"
+#include "hugo/detection/detection_enums.h"
 
 #define HUGO_DAT_VER_MAJ 0                          // 1 byte
 #define HUGO_DAT_VER_MIN 42                         // 1 byte
diff --git a/engines/hugo/metaengine.cpp b/engines/hugo/metaengine.cpp
index 8deb53be2c..0f0290cbcc 100644
--- a/engines/hugo/metaengine.cpp
+++ b/engines/hugo/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "graphics/surface.h"
 
 #include "hugo/hugo.h"
-#include "hugo/detection.h"
+#include "hugo/detection/detection.h"
 
 namespace Hugo {
 
diff --git a/engines/hugo/module.mk b/engines/hugo/module.mk
index 1f5c5f41ec..cdaadd9a23 100644
--- a/engines/hugo/module.mk
+++ b/engines/hugo/module.mk
@@ -38,6 +38,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/illusions/detection.cpp b/engines/illusions/detection/detection.cpp
similarity index 97%
rename from engines/illusions/detection.cpp
rename to engines/illusions/detection/detection.cpp
index 4d04a6f7db..fbbd29bf6c 100644
--- a/engines/illusions/detection.cpp
+++ b/engines/illusions/detection/detection.cpp
@@ -24,8 +24,8 @@
 
 #include "base/plugins.h"
 
-#include "illusions/detection_enums.h"
-#include "illusions/detection.h"
+#include "illusions/detection/detection_enums.h"
+#include "illusions/detection/detection.h"
 
 static const PlainGameDescriptor illusionsGames[] = {
 	{ "bbdou", "Beavis and Butt-head Do U" },
diff --git a/engines/illusions/detection.h b/engines/illusions/detection/detection.h
similarity index 100%
rename from engines/illusions/detection.h
rename to engines/illusions/detection/detection.h
diff --git a/engines/illusions/detection_enums.h b/engines/illusions/detection/detection_enums.h
similarity index 100%
rename from engines/illusions/detection_enums.h
rename to engines/illusions/detection/detection_enums.h
diff --git a/engines/illusions/detection/module.mk b/engines/illusions/detection/module.mk
new file mode 100644
index 0000000000..e3925749b3
--- /dev/null
+++ b/engines/illusions/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/illusions/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/illusions/illusions.h b/engines/illusions/illusions.h
index 73d6eced49..f1945c16d8 100644
--- a/engines/illusions/illusions.h
+++ b/engines/illusions/illusions.h
@@ -38,7 +38,7 @@
 
 #include "engines/engine.h"
 #include "graphics/surface.h"
-#include "illusions/detection_enums.h"
+#include "illusions/detection/detection_enums.h"
 
 namespace Illusions {
 
diff --git a/engines/illusions/metaengine.cpp b/engines/illusions/metaengine.cpp
index b01997b873..45051adf94 100644
--- a/engines/illusions/metaengine.cpp
+++ b/engines/illusions/metaengine.cpp
@@ -31,7 +31,7 @@
 #include "base/plugins.h"
 #include "graphics/thumbnail.h"
 
-#include "illusions/detection.h"
+#include "illusions/detection/detection.h"
 
 namespace Illusions {
 
diff --git a/engines/illusions/module.mk b/engines/illusions/module.mk
index 752cfdbbf6..f134b1eda0 100644
--- a/engines/illusions/module.mk
+++ b/engines/illusions/module.mk
@@ -76,6 +76,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/kingdom/detection.cpp b/engines/kingdom/detection/detection.cpp
similarity index 100%
rename from engines/kingdom/detection.cpp
rename to engines/kingdom/detection/detection.cpp
diff --git a/engines/kingdom/detection/module.mk b/engines/kingdom/detection/module.mk
new file mode 100644
index 0000000000..d98b678e6f
--- /dev/null
+++ b/engines/kingdom/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/kingdom/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/kingdom/module.mk b/engines/kingdom/module.mk
index 82c7dd45b6..c8a948495c 100644
--- a/engines/kingdom/module.mk
+++ b/engines/kingdom/module.mk
@@ -18,6 +18,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/kyra/detection.cpp b/engines/kyra/detection/detection.cpp
similarity index 96%
rename from engines/kyra/detection.cpp
rename to engines/kyra/detection/detection.cpp
index 295ddd7309..d2d88817c8 100644
--- a/engines/kyra/detection.cpp
+++ b/engines/kyra/detection/detection.cpp
@@ -24,9 +24,9 @@
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
 
-#include "kyra/detection_enums.h"
-#include "kyra/detection.h"
-#include "kyra/detection_tables.h"
+#include "kyra/detection/detection_enums.h"
+#include "kyra/detection/detection.h"
+#include "kyra/detection/detection_tables.h"
 
 namespace {
 
diff --git a/engines/kyra/detection.h b/engines/kyra/detection/detection.h
similarity index 100%
rename from engines/kyra/detection.h
rename to engines/kyra/detection/detection.h
diff --git a/engines/kyra/detection_enums.h b/engines/kyra/detection/detection_enums.h
similarity index 100%
rename from engines/kyra/detection_enums.h
rename to engines/kyra/detection/detection_enums.h
diff --git a/engines/kyra/detection_tables.h b/engines/kyra/detection/detection_tables.h
similarity index 100%
rename from engines/kyra/detection_tables.h
rename to engines/kyra/detection/detection_tables.h
diff --git a/engines/kyra/detection/module.mk b/engines/kyra/detection/module.mk
new file mode 100644
index 0000000000..b3866074c4
--- /dev/null
+++ b/engines/kyra/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/kyra/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/kyra/kyra_v1.h b/engines/kyra/kyra_v1.h
index 65d02ebf25..7aef4a2e97 100644
--- a/engines/kyra/kyra_v1.h
+++ b/engines/kyra/kyra_v1.h
@@ -36,7 +36,7 @@
 
 #include "kyra/script/script.h"
 #include "kyra/engine/item.h"
-#include "kyra/detection_enums.h"
+#include "kyra/detection/detection_enums.h"
 
 namespace Common {
 class OutSaveFile;
diff --git a/engines/kyra/metaengine.cpp b/engines/kyra/metaengine.cpp
index 3d6c680693..9c92d204be 100644
--- a/engines/kyra/metaengine.cpp
+++ b/engines/kyra/metaengine.cpp
@@ -36,7 +36,7 @@
 
 #include "base/plugins.h"
 
-#include "kyra/detection.h"
+#include "kyra/detection/detection.h"
 
 class KyraMetaEngineConnect : public AdvancedMetaEngineConnect {
 public:
diff --git a/engines/kyra/module.mk b/engines/kyra/module.mk
index 04e1c3f7b1..9f4b9a7520 100644
--- a/engines/kyra/module.mk
+++ b/engines/kyra/module.mk
@@ -153,9 +153,6 @@ endif
 # Include common rules
 include $(srcdir)/rules.mk
 
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
 ifeq ($(BACKEND), maemo)
 #ugly workaround, screen.cpp crashes gcc version 3.4.4 (CodeSourcery ARM 2005q3-2) with anything but -O3
 $(MODULE)/graphics/screen.o: $(MODULE)/graphics/screen.cpp
diff --git a/engines/lab/detection.cpp b/engines/lab/detection/detection.cpp
similarity index 98%
rename from engines/lab/detection.cpp
rename to engines/lab/detection/detection.cpp
index 8a63ca3604..a944e51e14 100644
--- a/engines/lab/detection.cpp
+++ b/engines/lab/detection/detection.cpp
@@ -29,7 +29,7 @@
  */
 
 #include "engines/advancedDetector.h"
-#include "lab/detection_enums.h"
+#include "lab/detection/detection_enums.h"
 
 static const PlainGameDescriptor lab_setting[] = {
 	{ "lab", "Labyrinth of Time" },
diff --git a/engines/lab/detection_enums.h b/engines/lab/detection/detection_enums.h
similarity index 100%
rename from engines/lab/detection_enums.h
rename to engines/lab/detection/detection_enums.h
diff --git a/engines/lab/detection/module.mk b/engines/lab/detection/module.mk
new file mode 100644
index 0000000000..1c32822a69
--- /dev/null
+++ b/engines/lab/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/lab/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lab/lab.h b/engines/lab/lab.h
index 17667cc70f..496f0b88f8 100644
--- a/engines/lab/lab.h
+++ b/engines/lab/lab.h
@@ -41,7 +41,7 @@
 #include "lab/console.h"
 #include "lab/image.h"
 #include "lab/labsets.h"
-#include "lab/detection_enums.h"
+#include "lab/detection/detection_enums.h"
 
 struct ADGameDescription;
 
diff --git a/engines/lab/module.mk b/engines/lab/module.mk
index 67fd2fd2db..d7dcd58e3e 100644
--- a/engines/lab/module.mk
+++ b/engines/lab/module.mk
@@ -28,6 +28,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lastexpress/detection.cpp b/engines/lastexpress/detection/detection.cpp
similarity index 100%
rename from engines/lastexpress/detection.cpp
rename to engines/lastexpress/detection/detection.cpp
diff --git a/engines/lastexpress/detection/module.mk b/engines/lastexpress/detection/module.mk
new file mode 100644
index 0000000000..d4c7f9d700
--- /dev/null
+++ b/engines/lastexpress/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/lastexpress/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lastexpress/module.mk b/engines/lastexpress/module.mk
index d25a57c581..77a7cf8271 100644
--- a/engines/lastexpress/module.mk
+++ b/engines/lastexpress/module.mk
@@ -81,6 +81,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lilliput/detection.cpp b/engines/lilliput/detection/detection.cpp
similarity index 97%
rename from engines/lilliput/detection.cpp
rename to engines/lilliput/detection/detection.cpp
index 74d582efb7..3a26a60591 100644
--- a/engines/lilliput/detection.cpp
+++ b/engines/lilliput/detection/detection.cpp
@@ -24,8 +24,8 @@
 #include "engines/advancedDetector.h"
 #include "common/textconsole.h"
 
-#include "lilliput/detection_enums.h"
-#include "lilliput/detection.h"
+#include "lilliput/detection/detection_enums.h"
+#include "lilliput/detection/detection.h"
 
 namespace Lilliput {
 
diff --git a/engines/lilliput/detection.h b/engines/lilliput/detection/detection.h
similarity index 100%
rename from engines/lilliput/detection.h
rename to engines/lilliput/detection/detection.h
diff --git a/engines/lilliput/detection_enums.h b/engines/lilliput/detection/detection_enums.h
similarity index 100%
rename from engines/lilliput/detection_enums.h
rename to engines/lilliput/detection/detection_enums.h
diff --git a/engines/lilliput/detection/module.mk b/engines/lilliput/detection/module.mk
new file mode 100644
index 0000000000..a6dbcc6f61
--- /dev/null
+++ b/engines/lilliput/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/lilliput/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lilliput/lilliput.h b/engines/lilliput/lilliput.h
index b4e90a0afb..eac0120ed2 100644
--- a/engines/lilliput/lilliput.h
+++ b/engines/lilliput/lilliput.h
@@ -27,7 +27,7 @@
 #include "lilliput/script.h"
 #include "lilliput/sound.h"
 #include "lilliput/stream.h"
-#include "lilliput/detection_enums.h"
+#include "lilliput/detection/detection_enums.h"
 
 #include "common/file.h"
 #include "common/rect.h"
diff --git a/engines/lilliput/metaengine.cpp b/engines/lilliput/metaengine.cpp
index e6df2bacfb..55c237f59a 100644
--- a/engines/lilliput/metaengine.cpp
+++ b/engines/lilliput/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "graphics/surface.h"
 
 #include "lilliput/lilliput.h"
-#include "lilliput/detection.h"
+#include "lilliput/detection/detection.h"
 
 namespace Lilliput {
 
diff --git a/engines/lilliput/module.mk b/engines/lilliput/module.mk
index 4002907135..8391675b58 100644
--- a/engines/lilliput/module.mk
+++ b/engines/lilliput/module.mk
@@ -18,6 +18,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lure/detection.cpp b/engines/lure/detection/detection.cpp
similarity index 98%
rename from engines/lure/detection.cpp
rename to engines/lure/detection/detection.cpp
index 017b7d9b52..74874418c7 100644
--- a/engines/lure/detection.cpp
+++ b/engines/lure/detection/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "common/translation.h"
 
-#include "lure/detection_enums.h"
-#include "lure/detection.h"
+#include "lure/detection/detection_enums.h"
+#include "lure/detection/detection.h"
 
 static const PlainGameDescriptor lureGames[] = {
 	{"lure", "Lure of the Temptress"},
diff --git a/engines/lure/detection.h b/engines/lure/detection/detection.h
similarity index 100%
rename from engines/lure/detection.h
rename to engines/lure/detection/detection.h
diff --git a/engines/lure/detection_enums.h b/engines/lure/detection/detection_enums.h
similarity index 100%
rename from engines/lure/detection_enums.h
rename to engines/lure/detection/detection_enums.h
diff --git a/engines/lure/detection/module.mk b/engines/lure/detection/module.mk
new file mode 100644
index 0000000000..cacf1641bd
--- /dev/null
+++ b/engines/lure/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/lure/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lure/lure.h b/engines/lure/lure.h
index c2ec5a5328..0c849b46c9 100644
--- a/engines/lure/lure.h
+++ b/engines/lure/lure.h
@@ -40,7 +40,7 @@
 #include "lure/strings.h"
 #include "lure/room.h"
 #include "lure/fights.h"
-#include "lure/detection_enums.h"
+#include "lure/detection/detection_enums.h"
 
 /**
  * This is the namespace of the Lure engine.
diff --git a/engines/lure/metaengine.cpp b/engines/lure/metaengine.cpp
index c6d7171f3b..7a680418ee 100644
--- a/engines/lure/metaengine.cpp
+++ b/engines/lure/metaengine.cpp
@@ -26,7 +26,7 @@
 #include "engines/advancedDetector.h"
 
 #include "lure/lure.h"
-#include "lure/detection.h"
+#include "lure/detection/detection.h"
 
 namespace Lure {
 
diff --git a/engines/lure/module.mk b/engines/lure/module.mk
index 7aae9073ef..efde4c7db7 100644
--- a/engines/lure/module.mk
+++ b/engines/lure/module.mk
@@ -31,6 +31,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/macventure/detection.cpp b/engines/macventure/detection/detection.cpp
similarity index 100%
rename from engines/macventure/detection.cpp
rename to engines/macventure/detection/detection.cpp
diff --git a/engines/macventure/detection/module.mk b/engines/macventure/detection/module.mk
new file mode 100644
index 0000000000..80d08585c9
--- /dev/null
+++ b/engines/macventure/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/macventure/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/macventure/module.mk b/engines/macventure/module.mk
index 0c0cf8b093..79541c69ce 100644
--- a/engines/macventure/module.mk
+++ b/engines/macventure/module.mk
@@ -29,6 +29,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/made/detection.cpp b/engines/made/detection/detection.cpp
similarity index 95%
rename from engines/made/detection.cpp
rename to engines/made/detection/detection.cpp
index 02dbc5763a..ba71394855 100644
--- a/engines/made/detection.cpp
+++ b/engines/made/detection/detection.cpp
@@ -23,8 +23,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "made/detection_enums.h"
-#include "made/detection.h"
+#include "made/detection/detection_enums.h"
+#include "made/detection/detection.h"
 
 static const PlainGameDescriptor madeGames[] = {
 	{"manhole", "The Manhole"},
@@ -34,7 +34,7 @@ static const PlainGameDescriptor madeGames[] = {
 	{0, 0}
 };
 
-#include "made/detection_tables.h"
+#include "made/detection/detection_tables.h"
 
 class MadeMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/made/detection.h b/engines/made/detection/detection.h
similarity index 100%
rename from engines/made/detection.h
rename to engines/made/detection/detection.h
diff --git a/engines/made/detection_enums.h b/engines/made/detection/detection_enums.h
similarity index 100%
rename from engines/made/detection_enums.h
rename to engines/made/detection/detection_enums.h
diff --git a/engines/made/detection_tables.h b/engines/made/detection/detection_tables.h
similarity index 100%
rename from engines/made/detection_tables.h
rename to engines/made/detection/detection_tables.h
diff --git a/engines/made/detection/module.mk b/engines/made/detection/module.mk
new file mode 100644
index 0000000000..e4b2b31d6f
--- /dev/null
+++ b/engines/made/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/made/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/made/made.h b/engines/made/made.h
index 3f7007f24e..7451978142 100644
--- a/engines/made/made.h
+++ b/engines/made/made.h
@@ -24,7 +24,7 @@
 #define MADE_MADE_H
 
 #include "made/sound.h"
-#include "made/detection_enums.h"
+#include "made/detection/detection_enums.h"
 
 #include "engines/engine.h"
 
diff --git a/engines/made/metaengine.cpp b/engines/made/metaengine.cpp
index cacc7b929e..53b283e331 100644
--- a/engines/made/metaengine.cpp
+++ b/engines/made/metaengine.cpp
@@ -22,7 +22,7 @@
 
 #include "engines/advancedDetector.h"
 #include "made/made.h"
-#include "made/detection.h"
+#include "made/detection/detection.h"
 
 
 namespace Made {
diff --git a/engines/made/module.mk b/engines/made/module.mk
index 2717b4d3c4..075ee141b3 100644
--- a/engines/made/module.mk
+++ b/engines/made/module.mk
@@ -24,6 +24,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mads/detection.cpp b/engines/mads/detection/detection.cpp
similarity index 96%
rename from engines/mads/detection.cpp
rename to engines/mads/detection/detection.cpp
index f8c31ab64a..6d992c7730 100644
--- a/engines/mads/detection.cpp
+++ b/engines/mads/detection/detection.cpp
@@ -27,8 +27,8 @@
 #include "common/system.h"
 #include "common/translation.h"
 
-#include "mads/detection_enums.h"
-#include "mads/detection.h"
+#include "mads/detection/detection_enums.h"
+#include "mads/detection/detection.h"
 
 static const PlainGameDescriptor MADSGames[] = {
 	{"dragonsphere", "Dragonsphere"},
@@ -47,7 +47,7 @@ static const PlainGameDescriptor MADSGames[] = {
 #define GAMEOPTION_TTS_NARRATOR 	GUIO_GAMEOPTIONS5
 #endif
 
-#include "mads/detection_tables.h"
+#include "mads/detection/detection_tables.h"
 
 static const ADExtraGuiOptionsMap optionsList[] = {
 	{
diff --git a/engines/mads/detection.h b/engines/mads/detection/detection.h
similarity index 100%
rename from engines/mads/detection.h
rename to engines/mads/detection/detection.h
diff --git a/engines/mads/detection_enums.h b/engines/mads/detection/detection_enums.h
similarity index 100%
rename from engines/mads/detection_enums.h
rename to engines/mads/detection/detection_enums.h
diff --git a/engines/mads/detection_tables.h b/engines/mads/detection/detection_tables.h
similarity index 100%
rename from engines/mads/detection_tables.h
rename to engines/mads/detection/detection_tables.h
diff --git a/engines/mads/detection/module.mk b/engines/mads/detection/module.mk
new file mode 100644
index 0000000000..8309bf143b
--- /dev/null
+++ b/engines/mads/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/mads/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mads/mads.h b/engines/mads/mads.h
index 9cda26e63a..7948f03248 100644
--- a/engines/mads/mads.h
+++ b/engines/mads/mads.h
@@ -40,7 +40,7 @@
 #include "mads/msurface.h"
 #include "mads/resources.h"
 #include "mads/sound.h"
-#include "mads/detection_enums.h"
+#include "mads/detection/detection_enums.h"
 
 /**
  * This is the namespace of the MADS engine.
diff --git a/engines/mads/metaengine.cpp b/engines/mads/metaengine.cpp
index 9ba6633666..bf5239716f 100644
--- a/engines/mads/metaengine.cpp
+++ b/engines/mads/metaengine.cpp
@@ -35,7 +35,7 @@
 
 #include "mads/events.h"
 #include "mads/game.h"
-#include "mads/detection.h"
+#include "mads/detection/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/mads/module.mk b/engines/mads/module.mk
index 2093fcb71f..9d0eda253d 100644
--- a/engines/mads/module.mk
+++ b/engines/mads/module.mk
@@ -68,6 +68,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mohawk/detection.cpp b/engines/mohawk/detection/detection.cpp
similarity index 94%
rename from engines/mohawk/detection.cpp
rename to engines/mohawk/detection/detection.cpp
index add3e96a9c..1548cf5d46 100644
--- a/engines/mohawk/detection.cpp
+++ b/engines/mohawk/detection/detection.cpp
@@ -27,16 +27,11 @@
 #include "common/textconsole.h"
 #include "common/translation.h"
 
-#include "mohawk/detection.h"
-#include "mohawk/detection_enums.h"
+#include "mohawk/detection/detection.h"
+#include "mohawk/detection/detection_enums.h"
 
-#ifdef ENABLE_RIVEN
 #include "mohawk/riven_metaengine/metaengine.h"
-#endif // ENABLE_RIVEN
-
-#ifdef ENABLE_MYST
 #include "mohawk/myst_metaengine/metaengine.h"
-#endif // ENABLE_MYST
 
 
 static const PlainGameDescriptor mohawkGames[] = {
@@ -70,7 +65,7 @@ static const PlainGameDescriptor mohawkGames[] = {
 	{nullptr, nullptr}
 };
 
-#include "mohawk/detection_tables.h"
+#include "mohawk/detection/detection_tables.h"
 
 static const char *directoryGlobs[] = {
 	"all",
@@ -116,7 +111,6 @@ DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) cons
 	// The AdvancedDetector model only allows specifying a single supported
 	// game language. The 25th anniversary edition Myst games are multilanguage.
 	// Here we amend the detected games to set the list of supported languages.
-#ifdef ENABLE_MYST
 	if (game.gameId == "myst"
 			&& Common::checkGameGUIOption(GAMEOPTION_25TH, game.getGUIOptions())
 			&& Common::checkGameGUIOption(GAMEOPTION_ME, game.getGUIOptions())) {
@@ -126,9 +120,7 @@ DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) cons
 			languages++;
 		}
 	}
-#endif
 
-#ifdef ENABLE_RIVEN
 	if (game.gameId == "riven"
 			&& Common::checkGameGUIOption(GAMEOPTION_25TH, game.getGUIOptions())) {
 		const Mohawk::RivenLanguage *languages = Mohawk::MohawkMetaEngine_Riven::listLanguages();
@@ -137,7 +129,6 @@ DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) cons
 			languages++;
 		}
 	}
-#endif
 
 	return game;
 }
@@ -145,16 +136,13 @@ DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) cons
 void MohawkMetaEngine::registerDefaultSettings(const Common::String &target) const {
 	Common::String gameId = ConfMan.get("gameid", target);
 
-#ifdef ENABLE_MYST
 	if (gameId == "myst" || gameId == "makingofmyst") {
 		return Mohawk::MohawkMetaEngine_Myst::registerDefaultSettings();
 	}
-#endif
-#ifdef ENABLE_RIVEN
+
 	if (gameId == "riven") {
 		return Mohawk::MohawkMetaEngine_Riven::registerDefaultSettings();
 	}
-#endif
 
 	return AdvancedMetaEngine::registerDefaultSettings(target);
 }
diff --git a/engines/mohawk/detection.h b/engines/mohawk/detection/detection.h
similarity index 100%
rename from engines/mohawk/detection.h
rename to engines/mohawk/detection/detection.h
diff --git a/engines/mohawk/detection_enums.h b/engines/mohawk/detection/detection_enums.h
similarity index 100%
rename from engines/mohawk/detection_enums.h
rename to engines/mohawk/detection/detection_enums.h
diff --git a/engines/mohawk/detection_tables.h b/engines/mohawk/detection/detection_tables.h
similarity index 100%
rename from engines/mohawk/detection_tables.h
rename to engines/mohawk/detection/detection_tables.h
diff --git a/engines/mohawk/detection/module.mk b/engines/mohawk/detection/module.mk
new file mode 100644
index 0000000000..4f3ca23a28
--- /dev/null
+++ b/engines/mohawk/detection/module.mk
@@ -0,0 +1,15 @@
+MODULE := engines/mohawk/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_MOHAWK), STATIC_PLUGIN)
+#ifndef ENABLE_MYST
+DETECT_OBJS += $(MODULE)/../myst_metaengine/metaengine.o
+#endif
+#ifndef ENABLE_RIVEN
+DETECT_OBJS += $(MODULE)/../riven_metaengine/metaengine.o
+#endif
+endif
diff --git a/engines/mohawk/metaengine.cpp b/engines/mohawk/metaengine.cpp
index 764e2d8c18..d6f5e68f91 100644
--- a/engines/mohawk/metaengine.cpp
+++ b/engines/mohawk/metaengine.cpp
@@ -52,7 +52,7 @@
 #include "mohawk/riven_saveload.h"
 #endif
 
-#include "mohawk/detection.h"
+#include "mohawk/detection/detection.h"
 
 namespace Mohawk {
 
diff --git a/engines/mohawk/module.mk b/engines/mohawk/module.mk
index c0444fadda..a09c9c3807 100644
--- a/engines/mohawk/module.mk
+++ b/engines/mohawk/module.mk
@@ -85,21 +85,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# If we're building a dynamic module, build the relevant
-# submodule. A static part already will have these, so
-# no need to add them again.
-ifeq ($(ENABLE_MOHAWK), DYNAMIC_PLUGIN)
-
-ifdef ENABLE_MYST
-DETECT_OBJS += $(MODULE)/myst_metaengine/metaengine.o
-endif
-
-ifdef ENABLE_RIVEN
-DETECT_OBJS += $(MODULE)/riven_metaengine/metaengine.o
-endif
-
-endif
diff --git a/engines/mohawk/mohawk.h b/engines/mohawk/mohawk.h
index 55a0f667f4..7dcf3b15d4 100644
--- a/engines/mohawk/mohawk.h
+++ b/engines/mohawk/mohawk.h
@@ -28,7 +28,7 @@
 
 #include "engines/engine.h"
 
-#include "mohawk/detection_enums.h"
+#include "mohawk/detection/detection_enums.h"
 
 class OSystem;
 
diff --git a/engines/mortevielle/detection.cpp b/engines/mortevielle/detection/detection.cpp
similarity index 92%
rename from engines/mortevielle/detection.cpp
rename to engines/mortevielle/detection/detection.cpp
index a0d85c7ae0..36e2574532 100644
--- a/engines/mortevielle/detection.cpp
+++ b/engines/mortevielle/detection/detection.cpp
@@ -23,15 +23,15 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "mortevielle/detection.h"
-#include "mortevielle/detection_enums.h"
+#include "mortevielle/detection/detection.h"
+#include "mortevielle/detection/detection_enums.h"
 
 static const PlainGameDescriptor MortevielleGame[] = {
 	{"mortevielle", "Mortville Manor"},
 	{0, 0}
 };
 
-#include "mortevielle/detection_tables.h"
+#include "mortevielle/detection/detection_tables.h"
 
 class MortevielleMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/mortevielle/detection.h b/engines/mortevielle/detection/detection.h
similarity index 100%
rename from engines/mortevielle/detection.h
rename to engines/mortevielle/detection/detection.h
diff --git a/engines/mortevielle/detection_enums.h b/engines/mortevielle/detection/detection_enums.h
similarity index 100%
rename from engines/mortevielle/detection_enums.h
rename to engines/mortevielle/detection/detection_enums.h
diff --git a/engines/mortevielle/detection_tables.h b/engines/mortevielle/detection/detection_tables.h
similarity index 100%
rename from engines/mortevielle/detection_tables.h
rename to engines/mortevielle/detection/detection_tables.h
diff --git a/engines/mortevielle/detection/module.mk b/engines/mortevielle/detection/module.mk
new file mode 100644
index 0000000000..eb10fe101c
--- /dev/null
+++ b/engines/mortevielle/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/mortevielle/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mortevielle/metaengine.cpp b/engines/mortevielle/metaengine.cpp
index 6bc1e23ef2..a9820bacbd 100644
--- a/engines/mortevielle/metaengine.cpp
+++ b/engines/mortevielle/metaengine.cpp
@@ -25,7 +25,7 @@
 
 #include "mortevielle/mortevielle.h"
 #include "mortevielle/saveload.h"
-#include "mortevielle/detection.h"
+#include "mortevielle/detection/detection.h"
 
 namespace Mortevielle {
 
diff --git a/engines/mortevielle/module.mk b/engines/mortevielle/module.mk
index 0c525fefe3..0a1c924920 100644
--- a/engines/mortevielle/module.mk
+++ b/engines/mortevielle/module.mk
@@ -21,6 +21,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mortevielle/mortevielle.h b/engines/mortevielle/mortevielle.h
index 93872c8f43..f1bf9333d7 100644
--- a/engines/mortevielle/mortevielle.h
+++ b/engines/mortevielle/mortevielle.h
@@ -44,7 +44,7 @@
 #include "mortevielle/saveload.h"
 #include "mortevielle/sound.h"
 #include "mortevielle/outtext.h"
-#include "mortevielle/detection_enums.h"
+#include "mortevielle/detection/detection_enums.h"
 
 namespace Mortevielle {
 
diff --git a/engines/mutationofjb/detection.cpp b/engines/mutationofjb/detection/detection.cpp
similarity index 100%
rename from engines/mutationofjb/detection.cpp
rename to engines/mutationofjb/detection/detection.cpp
diff --git a/engines/mutationofjb/detection/module.mk b/engines/mutationofjb/detection/module.mk
new file mode 100644
index 0000000000..f641caa9f3
--- /dev/null
+++ b/engines/mutationofjb/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/mutationofjb/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mutationofjb/module.mk b/engines/mutationofjb/module.mk
index f45acd8db1..948a02ad2c 100644
--- a/engines/mutationofjb/module.mk
+++ b/engines/mutationofjb/module.mk
@@ -68,6 +68,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/neverhood/detection.cpp b/engines/neverhood/detection/detection.cpp
similarity index 99%
rename from engines/neverhood/detection.cpp
rename to engines/neverhood/detection/detection.cpp
index 036b3397a2..4303a39ef0 100644
--- a/engines/neverhood/detection.cpp
+++ b/engines/neverhood/detection/detection.cpp
@@ -26,7 +26,7 @@
 #include "common/file.h"
 #include "common/translation.h"
 
-#include "neverhood/detection.h"
+#include "neverhood/detection/detection.h"
 
 static const PlainGameDescriptor neverhoodGames[] = {
 	{"neverhood", "The Neverhood Chronicles"},
diff --git a/engines/neverhood/detection.h b/engines/neverhood/detection/detection.h
similarity index 100%
rename from engines/neverhood/detection.h
rename to engines/neverhood/detection/detection.h
diff --git a/engines/neverhood/detection/module.mk b/engines/neverhood/detection/module.mk
new file mode 100644
index 0000000000..f5b9e43d80
--- /dev/null
+++ b/engines/neverhood/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/neverhood/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/neverhood/metaengine.cpp b/engines/neverhood/metaengine.cpp
index 239a1955d6..8b3b1f44cb 100644
--- a/engines/neverhood/metaengine.cpp
+++ b/engines/neverhood/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "common/translation.h"
 
 #include "neverhood/neverhood.h"
-#include "neverhood/detection.h"
+#include "neverhood/detection/detection.h"
 
 enum NeverhoodGameFeatures {
 	GF_BIG_DEMO = (1 << 0)
diff --git a/engines/neverhood/module.mk b/engines/neverhood/module.mk
index 2ffef0c3bb..f23f8146ae 100644
--- a/engines/neverhood/module.mk
+++ b/engines/neverhood/module.mk
@@ -75,6 +75,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/pegasus/detection.cpp b/engines/pegasus/detection/detection.cpp
similarity index 97%
rename from engines/pegasus/detection.cpp
rename to engines/pegasus/detection/detection.cpp
index 090f7935d2..e0728f812b 100644
--- a/engines/pegasus/detection.cpp
+++ b/engines/pegasus/detection/detection.cpp
@@ -26,7 +26,8 @@
 #include "common/config-manager.h"
 #include "common/file.h"
 
-#include "pegasus/detection.h"
+#include "pegasus/detection/detection_enums.h"
+#include "pegasus/detection/detection.h"
 
 static const PlainGameDescriptor pegasusGames[] = {
 	{"pegasus", "The Journeyman Project: Pegasus Prime"},
diff --git a/engines/pegasus/detection.h b/engines/pegasus/detection/detection.h
similarity index 97%
rename from engines/pegasus/detection.h
rename to engines/pegasus/detection/detection.h
index f5571fafbb..b8e20fc4d7 100644
--- a/engines/pegasus/detection.h
+++ b/engines/pegasus/detection/detection.h
@@ -26,8 +26,4 @@ struct PegasusGameDescription {
 	ADGameDescription desc;
 };
 
-enum {
-	GF_DVD = (1 << 1)
-};
-
 } // End of namespace Pegasus
diff --git a/engines/pegasus/detection/detection_enums.h b/engines/pegasus/detection/detection_enums.h
new file mode 100644
index 0000000000..9797435940
--- /dev/null
+++ b/engines/pegasus/detection/detection_enums.h
@@ -0,0 +1,37 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * Additional copyright for this file:
+ * Copyright (C) 1995-1997 Presto Studios, Inc.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef PEGASUS_DETECTION_ENUMS_h
+#define PEGASUS_DETECTION_ENUMS_h
+
+namespace Pegasus {
+
+enum {
+	GF_DVD = (1 << 1)
+};
+
+} // End of namespace Pegasus
+
+#endif // PEGASUS_DETECTION_ENUMS_h
diff --git a/engines/pegasus/detection/module.mk b/engines/pegasus/detection/module.mk
new file mode 100644
index 0000000000..8b554b5929
--- /dev/null
+++ b/engines/pegasus/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/pegasus/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/pegasus/metaengine.cpp b/engines/pegasus/metaengine.cpp
index d6616ec67c..16840b4e1c 100644
--- a/engines/pegasus/metaengine.cpp
+++ b/engines/pegasus/metaengine.cpp
@@ -28,7 +28,8 @@
 #include "common/savefile.h"
 
 #include "pegasus/pegasus.h"
-#include "pegasus/detection.h"
+#include "pegasus/detection/detection_enums.h"
+#include "pegasus/detection/detection.h"
 
 namespace Pegasus {
 
diff --git a/engines/pegasus/module.mk b/engines/pegasus/module.mk
index 1fe1963f32..39481cb665 100644
--- a/engines/pegasus/module.mk
+++ b/engines/pegasus/module.mk
@@ -99,6 +99,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/petka/detection.cpp b/engines/petka/detection/detection.cpp
similarity index 97%
rename from engines/petka/detection.cpp
rename to engines/petka/detection/detection.cpp
index b1825a7934..57954a37ee 100644
--- a/engines/petka/detection.cpp
+++ b/engines/petka/detection/detection.cpp
@@ -31,7 +31,7 @@ static const PlainGameDescriptor petkaGames[] = {
 	{0, 0}
 };
 
-#include "detection_tables.h"
+#include "petka/detection/detection_tables.h"
 
 class PetkaMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/petka/detection_tables.h b/engines/petka/detection/detection_tables.h
similarity index 100%
rename from engines/petka/detection_tables.h
rename to engines/petka/detection/detection_tables.h
diff --git a/engines/petka/detection/module.mk b/engines/petka/detection/module.mk
new file mode 100644
index 0000000000..99ab6a67ac
--- /dev/null
+++ b/engines/petka/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/petka/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/petka/module.mk b/engines/petka/module.mk
index 7bcbb03ef3..44d74c22c7 100644
--- a/engines/petka/module.mk
+++ b/engines/petka/module.mk
@@ -35,6 +35,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/pink/detection.cpp b/engines/pink/detection/detection.cpp
similarity index 97%
rename from engines/pink/detection.cpp
rename to engines/pink/detection/detection.cpp
index c6ffafa324..ad21dead52 100644
--- a/engines/pink/detection.cpp
+++ b/engines/pink/detection/detection.cpp
@@ -30,7 +30,7 @@ static const PlainGameDescriptor pinkGames[] = {
 	{0, 0}
 };
 
-#include "pink/detection_tables.h"
+#include "pink/detection/detection_tables.h"
 
 static const char *directoryGlobs[] = {
 	"install",
diff --git a/engines/pink/detection_tables.h b/engines/pink/detection/detection_tables.h
similarity index 100%
rename from engines/pink/detection_tables.h
rename to engines/pink/detection/detection_tables.h
diff --git a/engines/pink/detection/module.mk b/engines/pink/detection/module.mk
new file mode 100644
index 0000000000..26585ca263
--- /dev/null
+++ b/engines/pink/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/pink/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/pink/module.mk b/engines/pink/module.mk
index bc85597e2c..db758c2719 100644
--- a/engines/pink/module.mk
+++ b/engines/pink/module.mk
@@ -57,6 +57,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/plumbers/detection/module.mk b/engines/plumbers/detection/module.mk
index 2bad793b2b..aa4c34686b 100644
--- a/engines/plumbers/detection/module.mk
+++ b/engines/plumbers/detection/module.mk
@@ -1,6 +1,4 @@
 MODULE := engines/plumbers/detection
 
-MODULE_OBJS :=
-
 # Detection objects
 DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/prince/detection.cpp b/engines/prince/detection/detection.cpp
similarity index 97%
rename from engines/prince/detection.cpp
rename to engines/prince/detection/detection.cpp
index f0f9b5984c..65ed046302 100644
--- a/engines/prince/detection.cpp
+++ b/engines/prince/detection/detection.cpp
@@ -22,8 +22,8 @@
 
 #include "engines/advancedDetector.h"
 
-#include "prince/detection_enums.h"
-#include "prince/detection.h"
+#include "prince/detection/detection_enums.h"
+#include "prince/detection/detection.h"
 
 static const PlainGameDescriptor princeGames[] = {
 	{"prince", "The Prince and the Coward"},
diff --git a/engines/prince/detection.h b/engines/prince/detection/detection.h
similarity index 100%
rename from engines/prince/detection.h
rename to engines/prince/detection/detection.h
diff --git a/engines/prince/detection_enums.h b/engines/prince/detection/detection_enums.h
similarity index 100%
rename from engines/prince/detection_enums.h
rename to engines/prince/detection/detection_enums.h
diff --git a/engines/prince/detection/module.mk b/engines/prince/detection/module.mk
new file mode 100644
index 0000000000..9d9d472db4
--- /dev/null
+++ b/engines/prince/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/prince/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/prince/metaengine.cpp b/engines/prince/metaengine.cpp
index 23ea7e7667..1e82802bd1 100644
--- a/engines/prince/metaengine.cpp
+++ b/engines/prince/metaengine.cpp
@@ -22,7 +22,7 @@
 
 #include "engines/advancedDetector.h"
 #include "prince/prince.h"
-#include "prince/detection.h"
+#include "prince/detection/detection.h"
 
 namespace Prince {
 
diff --git a/engines/prince/module.mk b/engines/prince/module.mk
index 0bca0ab5b0..bd93e08a98 100644
--- a/engines/prince/module.mk
+++ b/engines/prince/module.mk
@@ -34,6 +34,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/prince/prince.h b/engines/prince/prince.h
index bbcb97edaa..e58759b959 100644
--- a/engines/prince/prince.h
+++ b/engines/prince/prince.h
@@ -48,7 +48,7 @@
 #include "prince/mob.h"
 #include "prince/object.h"
 #include "prince/pscr.h"
-#include "prince/detection_enums.h"
+#include "prince/detection/detection_enums.h"
 
 namespace Prince {
 
diff --git a/engines/queen/detection.cpp b/engines/queen/detection/detection.cpp
similarity index 99%
rename from engines/queen/detection.cpp
rename to engines/queen/detection/detection.cpp
index ccafc68a47..9ca6f71b4a 100644
--- a/engines/queen/detection.cpp
+++ b/engines/queen/detection/detection.cpp
@@ -28,7 +28,7 @@
 #include "common/file.h"
 #include "common/translation.h"
 
-#include "queen/detection.h"
+#include "queen/detection/detection.h"
 #include "queen/resource.h"
 
 static const PlainGameDescriptor queenGames[] = {
diff --git a/engines/queen/detection.h b/engines/queen/detection/detection.h
similarity index 100%
rename from engines/queen/detection.h
rename to engines/queen/detection/detection.h
diff --git a/engines/queen/detection/module.mk b/engines/queen/detection/module.mk
new file mode 100644
index 0000000000..57e44e76dc
--- /dev/null
+++ b/engines/queen/detection/module.mk
@@ -0,0 +1,12 @@
+MODULE := engines/queen/detection
+
+# Detection objecs
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_QUEEN), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/../resource.o
+DETECT_OBJS += $(MODULE)/../restables.o
+endif
diff --git a/engines/queen/metaengine.cpp b/engines/queen/metaengine.cpp
index 8cdbbecda3..1b0803f10b 100644
--- a/engines/queen/metaengine.cpp
+++ b/engines/queen/metaengine.cpp
@@ -27,7 +27,7 @@
 
 #include "queen/queen.h"
 #include "queen/resource.h"
-#include "queen/detection.h"
+#include "queen/detection/detection.h"
 
 class QueenMetaEngineConnect : public AdvancedMetaEngineConnect {
 public:
diff --git a/engines/queen/module.mk b/engines/queen/module.mk
index 0b5b72b7fb..7e504c587f 100644
--- a/engines/queen/module.mk
+++ b/engines/queen/module.mk
@@ -31,14 +31,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objecs
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Only include if building as a dynamic module.
-# Static module already has the contents.
-ifeq ($(ENABLE_QUEEN), DYNAMIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/resource.o
-DETECT_OBJS += $(MODULE)/restables.o
-endif
diff --git a/engines/saga/detection.cpp b/engines/saga/detection/detection.cpp
similarity index 94%
rename from engines/saga/detection.cpp
rename to engines/saga/detection/detection.cpp
index e58d6689b1..c74f93be17 100644
--- a/engines/saga/detection.cpp
+++ b/engines/saga/detection/detection.cpp
@@ -25,8 +25,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "saga/detection_enums.h"
-#include "saga/detection.h"
+#include "saga/detection/detection_enums.h"
+#include "saga/detection/detection.h"
 
 static const PlainGameDescriptor sagaGames[] = {
 	{"ite", "Inherit the Earth: Quest for the Orb"},
@@ -36,7 +36,7 @@ static const PlainGameDescriptor sagaGames[] = {
 	{0, 0}
 };
 
-#include "saga/detection_tables.h"
+#include "saga/detection/detection_tables.h"
 
 class SagaMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/saga/detection.h b/engines/saga/detection/detection.h
similarity index 100%
rename from engines/saga/detection.h
rename to engines/saga/detection/detection.h
diff --git a/engines/saga/detection_enums.h b/engines/saga/detection/detection_enums.h
similarity index 100%
rename from engines/saga/detection_enums.h
rename to engines/saga/detection/detection_enums.h
diff --git a/engines/saga/detection_tables.h b/engines/saga/detection/detection_tables.h
similarity index 100%
rename from engines/saga/detection_tables.h
rename to engines/saga/detection/detection_tables.h
diff --git a/engines/saga/detection/module.mk b/engines/saga/detection/module.mk
new file mode 100644
index 0000000000..4f32d52de5
--- /dev/null
+++ b/engines/saga/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/saga/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/saga/metaengine.cpp b/engines/saga/metaengine.cpp
index 43d8b6bceb..1a477c7e2f 100644
--- a/engines/saga/metaengine.cpp
+++ b/engines/saga/metaengine.cpp
@@ -37,7 +37,7 @@
 #include "saga/resource.h"
 #include "saga/interface.h"
 #include "saga/scene.h"
-#include "saga/detection.h"
+#include "saga/detection/detection.h"
 
 namespace Saga {
 
diff --git a/engines/saga/module.mk b/engines/saga/module.mk
index 07af31efc0..b4721ca605 100644
--- a/engines/saga/module.mk
+++ b/engines/saga/module.mk
@@ -55,6 +55,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/saga/saga.h b/engines/saga/saga.h
index 59a8ecf202..cbe58b691b 100644
--- a/engines/saga/saga.h
+++ b/engines/saga/saga.h
@@ -31,7 +31,7 @@
 #include "common/textconsole.h"
 
 #include "saga/gfx.h"
-#include "saga/detection_enums.h"
+#include "saga/detection/detection_enums.h"
 
 struct ADGameFileDescription;
 
diff --git a/engines/sci/detection.cpp b/engines/sci/detection/detection.cpp
similarity index 99%
rename from engines/sci/detection.cpp
rename to engines/sci/detection/detection.cpp
index 667c2d3176..ae445defb5 100644
--- a/engines/sci/detection.cpp
+++ b/engines/sci/detection/detection.cpp
@@ -31,8 +31,8 @@
 #include "gui/widget.h"
 #include "gui/widgets/popup.h"
 
-#include "sci/detection_enums.h"
-#include "sci/detection_defines.h"
+#include "sci/detection/detection_enums.h"
+#include "sci/detection/detection_defines.h"
 #include "sci/graphics/helpers_detection_enums.h"
 
 namespace Sci {
@@ -133,7 +133,7 @@ static const PlainGameDescriptor s_sciGameTitles[] = {
 
 } // End of namespace Sci
 
-#include "sci/detection_tables.h"
+#include "sci/detection/detection_tables.h"
 
 namespace Sci {
 
diff --git a/engines/sci/detection_defines.h b/engines/sci/detection/detection_defines.h
similarity index 100%
rename from engines/sci/detection_defines.h
rename to engines/sci/detection/detection_defines.h
diff --git a/engines/sci/detection_enums.h b/engines/sci/detection/detection_enums.h
similarity index 100%
rename from engines/sci/detection_enums.h
rename to engines/sci/detection/detection_enums.h
diff --git a/engines/sci/detection_tables.h b/engines/sci/detection/detection_tables.h
similarity index 100%
rename from engines/sci/detection_tables.h
rename to engines/sci/detection/detection_tables.h
diff --git a/engines/sci/detection/module.mk b/engines/sci/detection/module.mk
new file mode 100644
index 0000000000..26de2b20f0
--- /dev/null
+++ b/engines/sci/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/sci/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sci/module.mk b/engines/sci/module.mk
index 4e2724cede..8ec7ea5714 100644
--- a/engines/sci/module.mk
+++ b/engines/sci/module.mk
@@ -113,6 +113,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sci/sci.h b/engines/sci/sci.h
index 7ea28b38f7..144700e1a8 100644
--- a/engines/sci/sci.h
+++ b/engines/sci/sci.h
@@ -29,8 +29,8 @@
 #include "common/random.h"
 #include "sci/engine/vm_types.h"	// for Selector
 #include "sci/debug.h"	// for DebugState
-#include "sci/detection_enums.h" // for shared enums between detection/engine
-#include "sci/detection_defines.h" // for shared defines between detection/engine
+#include "sci/detection/detection_enums.h" // for shared enums between detection/engine
+#include "sci/detection/detection_defines.h" // for shared defines between detection/engine
 
 struct ADGameDescription;
 
diff --git a/engines/scumm/detection.cpp b/engines/scumm/detection/detection.cpp
similarity index 97%
rename from engines/scumm/detection.cpp
rename to engines/scumm/detection/detection.cpp
index 0b316898b7..ca36ad094e 100644
--- a/engines/scumm/detection.cpp
+++ b/engines/scumm/detection/detection.cpp
@@ -33,8 +33,8 @@
 
 #include "audio/mididrv.h"
 
-#include "scumm/detection.h"
-#include "scumm/detection_tables.h"
+#include "scumm/detection/detection.h"
+#include "scumm/detection/detection_tables.h"
 #include "scumm/file.h"
 #include "scumm/file_nes.h"
 
@@ -44,7 +44,7 @@
 
 
 // Various methods to help in core detection.
-#include "scumm/detection_internal.h"
+#include "scumm/detection/detection_internal.h"
 
 
 #pragma mark -
diff --git a/engines/scumm/detection.h b/engines/scumm/detection/detection.h
similarity index 100%
rename from engines/scumm/detection.h
rename to engines/scumm/detection/detection.h
diff --git a/engines/scumm/detection_internal.h b/engines/scumm/detection/detection_internal.h
similarity index 99%
rename from engines/scumm/detection_internal.h
rename to engines/scumm/detection/detection_internal.h
index 8e6c1116c3..2baf3a0021 100644
--- a/engines/scumm/detection_internal.h
+++ b/engines/scumm/detection/detection_internal.h
@@ -26,7 +26,7 @@
 // Includes some shared functionalities, which is required by multiple TU's.
 // Mark it as static in the header, so visibility for function is limited by the TU, and we can use it whereever required.
 // This is being done, because it's necessary in detection, creating an instance, as well as in initiliasing the ScummEngine.
-#include "scumm/detection_steam.h"
+#include "scumm/detection/detection_steam.h"
 
 namespace Scumm {
 
diff --git a/engines/scumm/detection_steam.h b/engines/scumm/detection/detection_steam.h
similarity index 100%
rename from engines/scumm/detection_steam.h
rename to engines/scumm/detection/detection_steam.h
diff --git a/engines/scumm/detection_tables.h b/engines/scumm/detection/detection_tables.h
similarity index 99%
rename from engines/scumm/detection_tables.h
rename to engines/scumm/detection/detection_tables.h
index 50bc9755ff..ed057bb1c5 100644
--- a/engines/scumm/detection_tables.h
+++ b/engines/scumm/detection/detection_tables.h
@@ -28,7 +28,7 @@
 #include "common/rect.h"
 #include "common/util.h"
 
-#include "scumm/detection.h"
+#include "scumm/detection/detection.h"
 #include "scumm/scumm.h"
 
 #include "scumm/scumm-md5.h"
diff --git a/engines/scumm/detection/module.mk b/engines/scumm/detection/module.mk
new file mode 100644
index 0000000000..e8ee8168b2
--- /dev/null
+++ b/engines/scumm/detection/module.mk
@@ -0,0 +1,11 @@
+MODULE := engines/scumm/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_SCUMM), STATIC_PLUGIN)
+DETECT_OBJS += $(MODULE)/../file.o
+DETECT_OBJS += $(MODULE)/../file_nes.o
+endif
diff --git a/engines/scumm/file.h b/engines/scumm/file.h
index e367190d2d..feacfbe65f 100644
--- a/engines/scumm/file.h
+++ b/engines/scumm/file.h
@@ -26,7 +26,7 @@
 #include "common/file.h"
 #include "common/stream.h"
 
-#include "scumm/detection.h"
+#include "scumm/detection/detection.h"
 
 namespace Scumm {
 
diff --git a/engines/scumm/metaengine.cpp b/engines/scumm/metaengine.cpp
index 18a76618d1..bbcb0a66f5 100644
--- a/engines/scumm/metaengine.cpp
+++ b/engines/scumm/metaengine.cpp
@@ -37,8 +37,8 @@
 
 // Files related for detection.
 #include "scumm/metaengine.h"
-#include "scumm/detection.h"
-#include "scumm/detection_tables.h"
+#include "scumm/detection/detection.h"
+#include "scumm/detection/detection_tables.h"
 #include "scumm/file.h"
 #include "scumm/file_nes.h"
 
@@ -206,7 +206,7 @@ bool ScummEngine::isMacM68kIMuse() const {
 
 
 // Various methods to help in core detection.
-#include "scumm/detection_internal.h"
+#include "scumm/detection/detection_internal.h"
 
 
 #pragma mark -
diff --git a/engines/scumm/module.mk b/engines/scumm/module.mk
index 4f8322885c..da4c0e4c0d 100644
--- a/engines/scumm/module.mk
+++ b/engines/scumm/module.mk
@@ -168,15 +168,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# If this module is being built as a dynamic plugin,
-# add the additional dependencies of detection.
-# Otherwise, these are not added because they're already
-# present in the module objects.
-ifeq ($(ENABLE_SCUMM), DYNAMIC_PLUGIN)
-DETECT_OBJS += $(MODULE)/file.o
-DETECT_OBJS += $(MODULE)/file_nes.o
-endif
diff --git a/engines/scumm/scumm.cpp b/engines/scumm/scumm.cpp
index 6bc433fa51..1cffbf1edc 100644
--- a/engines/scumm/scumm.cpp
+++ b/engines/scumm/scumm.cpp
@@ -80,7 +80,7 @@
 #include "scumm/imuse/drivers/mac_m68k.h"
 #include "scumm/imuse/drivers/amiga.h"
 #include "scumm/imuse/drivers/fmtowns.h"
-#include "scumm/detection_steam.h"
+#include "scumm/detection/detection_steam.h"
 
 #include "backends/audiocd/audiocd.h"
 
diff --git a/engines/scumm/scumm.h b/engines/scumm/scumm.h
index 550ae0f6b1..1a9f03f723 100644
--- a/engines/scumm/scumm.h
+++ b/engines/scumm/scumm.h
@@ -40,7 +40,7 @@
 #include "graphics/sjis.h"
 
 #include "scumm/gfx.h"
-#include "scumm/detection.h"
+#include "scumm/detection/detection.h"
 #include "scumm/script.h"
 
 #ifdef __DS__
diff --git a/engines/sherlock/detection.cpp b/engines/sherlock/detection/detection.cpp
similarity index 96%
rename from engines/sherlock/detection.cpp
rename to engines/sherlock/detection/detection.cpp
index 2454b54899..40fc76a3b0 100644
--- a/engines/sherlock/detection.cpp
+++ b/engines/sherlock/detection/detection.cpp
@@ -23,8 +23,8 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "sherlock/detection_enums.h"
-#include "sherlock/detection.h"
+#include "sherlock/detection/detection_enums.h"
+#include "sherlock/detection/detection.h"
 
 static const PlainGameDescriptor sherlockGames[] = {
 	{ "scalpel", "The Case of the Serrated Scalpel" },
@@ -120,7 +120,7 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 };
 
 
-#include "sherlock/detection_tables.h"
+#include "sherlock/detection/detection_tables.h"
 
 class SherlockMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/sherlock/detection.h b/engines/sherlock/detection/detection.h
similarity index 100%
rename from engines/sherlock/detection.h
rename to engines/sherlock/detection/detection.h
diff --git a/engines/sherlock/detection_enums.h b/engines/sherlock/detection/detection_enums.h
similarity index 100%
rename from engines/sherlock/detection_enums.h
rename to engines/sherlock/detection/detection_enums.h
diff --git a/engines/sherlock/detection_tables.h b/engines/sherlock/detection/detection_tables.h
similarity index 100%
rename from engines/sherlock/detection_tables.h
rename to engines/sherlock/detection/detection_tables.h
diff --git a/engines/sherlock/detection/module.mk b/engines/sherlock/detection/module.mk
new file mode 100644
index 0000000000..2290606a55
--- /dev/null
+++ b/engines/sherlock/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/sherlock/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sherlock/metaengine.cpp b/engines/sherlock/metaengine.cpp
index e5fa0f1ea6..3167b697ec 100644
--- a/engines/sherlock/metaengine.cpp
+++ b/engines/sherlock/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "sherlock/detection.h"
+#include "sherlock/detection/detection.h"
 
 namespace Sherlock {
 
diff --git a/engines/sherlock/module.mk b/engines/sherlock/module.mk
index 265053a080..9a8b35c722 100644
--- a/engines/sherlock/module.mk
+++ b/engines/sherlock/module.mk
@@ -77,6 +77,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sherlock/sherlock.h b/engines/sherlock/sherlock.h
index 06a28af8bb..4c7a19f6a5 100644
--- a/engines/sherlock/sherlock.h
+++ b/engines/sherlock/sherlock.h
@@ -50,7 +50,7 @@
 #include "sherlock/sound.h"
 #include "sherlock/talk.h"
 #include "sherlock/user_interface.h"
-#include "sherlock/detection_enums.h"
+#include "sherlock/detection/detection_enums.h"
 
 namespace Sherlock {
 
diff --git a/engines/sky/detection.cpp b/engines/sky/detection/detection.cpp
similarity index 100%
rename from engines/sky/detection.cpp
rename to engines/sky/detection/detection.cpp
diff --git a/engines/sky/detection/module.mk b/engines/sky/detection/module.mk
new file mode 100644
index 0000000000..77bae631c1
--- /dev/null
+++ b/engines/sky/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/sky/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sky/module.mk b/engines/sky/module.mk
index 4dd4d20b0b..2a9a12c92b 100644
--- a/engines/sky/module.mk
+++ b/engines/sky/module.mk
@@ -31,6 +31,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sludge/detection.cpp b/engines/sludge/detection/detection.cpp
similarity index 98%
rename from engines/sludge/detection.cpp
rename to engines/sludge/detection/detection.cpp
index 8ab37da31c..aecb0688fe 100644
--- a/engines/sludge/detection.cpp
+++ b/engines/sludge/detection/detection.cpp
@@ -25,7 +25,7 @@
 
 #include "engines/advancedDetector.h"
 
-#include "sludge/detection.h"
+#include "sludge/detection/detection.h"
 
 static const PlainGameDescriptor sludgeGames[] = {
 	{ "sludge",			"Sludge Game" },
@@ -47,7 +47,7 @@ static const PlainGameDescriptor sludgeGames[] = {
 	{ 0, 0 }
 };
 
-#include "sludge/detection_tables.h"
+#include "sludge/detection/detection_tables.h"
 
 static Sludge::SludgeGameDescription s_fallbackDesc =
 {
diff --git a/engines/sludge/detection.h b/engines/sludge/detection/detection.h
similarity index 100%
rename from engines/sludge/detection.h
rename to engines/sludge/detection/detection.h
diff --git a/engines/sludge/detection_tables.h b/engines/sludge/detection/detection_tables.h
similarity index 100%
rename from engines/sludge/detection_tables.h
rename to engines/sludge/detection/detection_tables.h
diff --git a/engines/sludge/detection/module.mk b/engines/sludge/detection/module.mk
new file mode 100644
index 0000000000..c0177ea565
--- /dev/null
+++ b/engines/sludge/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/sludge/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sludge/metaengine.cpp b/engines/sludge/metaengine.cpp
index 96385daea5..2ea4d4eda3 100644
--- a/engines/sludge/metaengine.cpp
+++ b/engines/sludge/metaengine.cpp
@@ -26,7 +26,7 @@
 #include "engines/advancedDetector.h"
 
 #include "sludge/sludge.h"
-#include "sludge/detection.h"
+#include "sludge/detection/detection.h"
 
 namespace Sludge {
 
diff --git a/engines/sludge/module.mk b/engines/sludge/module.mk
index 19435b559d..accc922643 100644
--- a/engines/sludge/module.mk
+++ b/engines/sludge/module.mk
@@ -50,6 +50,3 @@ endif
  
 # Include common rules 
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/startrek/detection.cpp b/engines/startrek/detection/detection.cpp
similarity index 98%
rename from engines/startrek/detection.cpp
rename to engines/startrek/detection/detection.cpp
index 26480182a3..6121bd1194 100644
--- a/engines/startrek/detection.cpp
+++ b/engines/startrek/detection/detection.cpp
@@ -27,8 +27,8 @@
 #include "common/config-manager.h"
 #include "common/file.h"
 
-#include "startrek/detection.h"
-#include "startrek/detection_enums.h"
+#include "startrek/detection/detection.h"
+#include "startrek/detection/detection_enums.h"
 
 static const PlainGameDescriptor starTrekGames[] = {
 	{"st25", "Star Trek: 25th Anniversary"},
diff --git a/engines/startrek/detection.h b/engines/startrek/detection/detection.h
similarity index 100%
rename from engines/startrek/detection.h
rename to engines/startrek/detection/detection.h
diff --git a/engines/startrek/detection_enums.h b/engines/startrek/detection/detection_enums.h
similarity index 100%
rename from engines/startrek/detection_enums.h
rename to engines/startrek/detection/detection_enums.h
diff --git a/engines/startrek/detection/module.mk b/engines/startrek/detection/module.mk
new file mode 100644
index 0000000000..c258375e84
--- /dev/null
+++ b/engines/startrek/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/startrek/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/startrek/metaengine.cpp b/engines/startrek/metaengine.cpp
index f7c5007a62..9bc75174af 100644
--- a/engines/startrek/metaengine.cpp
+++ b/engines/startrek/metaengine.cpp
@@ -32,7 +32,7 @@
 
 #include "startrek/startrek.h"
 
-#include "startrek/detection.h"
+#include "startrek/detection/detection.h"
 
 namespace StarTrek {
 
diff --git a/engines/startrek/module.mk b/engines/startrek/module.mk
index b169b15fef..922ffa2edf 100644
--- a/engines/startrek/module.mk
+++ b/engines/startrek/module.mk
@@ -88,6 +88,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/startrek/startrek.h b/engines/startrek/startrek.h
index 804878da59..f3d59fa3db 100644
--- a/engines/startrek/startrek.h
+++ b/engines/startrek/startrek.h
@@ -48,7 +48,7 @@
 #include "startrek/object.h"
 #include "startrek/sound.h"
 #include "startrek/space.h"
-#include "startrek/detection_enums.h"
+#include "startrek/detection/detection_enums.h"
 
 
 using Common::SharedPtr;
diff --git a/engines/supernova/detection.cpp b/engines/supernova/detection/detection.cpp
similarity index 100%
rename from engines/supernova/detection.cpp
rename to engines/supernova/detection/detection.cpp
diff --git a/engines/supernova/detection/module.mk b/engines/supernova/detection/module.mk
new file mode 100644
index 0000000000..6300f2866d
--- /dev/null
+++ b/engines/supernova/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/supernova/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/supernova/module.mk b/engines/supernova/module.mk
index 22db249658..311f87aa38 100644
--- a/engines/supernova/module.mk
+++ b/engines/supernova/module.mk
@@ -25,6 +25,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword1/detection.cpp b/engines/sword1/detection/detection.cpp
similarity index 100%
rename from engines/sword1/detection.cpp
rename to engines/sword1/detection/detection.cpp
diff --git a/engines/sword1/detection/module.mk b/engines/sword1/detection/module.mk
new file mode 100644
index 0000000000..f11dba72dc
--- /dev/null
+++ b/engines/sword1/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/sword1/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword1/module.mk b/engines/sword1/module.mk
index a2b38fc75a..143cb20a0b 100644
--- a/engines/sword1/module.mk
+++ b/engines/sword1/module.mk
@@ -28,6 +28,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword2/detection.cpp b/engines/sword2/detection/detection.cpp
similarity index 97%
rename from engines/sword2/detection.cpp
rename to engines/sword2/detection/detection.cpp
index c7b7134155..1fd9547d96 100644
--- a/engines/sword2/detection.cpp
+++ b/engines/sword2/detection/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "engines/metaengine.h"
 
-#include "sword2/detection_enums.h"
-#include "sword2/detection_internal.h"
+#include "sword2/detection/detection_enums.h"
+#include "sword2/detection/detection_internal.h"
 
 static const ExtraGuiOption sword2ExtraGuiOption = {
 	_s("Show object labels"),
diff --git a/engines/sword2/detection_enums.h b/engines/sword2/detection/detection_enums.h
similarity index 100%
rename from engines/sword2/detection_enums.h
rename to engines/sword2/detection/detection_enums.h
diff --git a/engines/sword2/detection_internal.h b/engines/sword2/detection/detection_internal.h
similarity index 98%
rename from engines/sword2/detection_internal.h
rename to engines/sword2/detection/detection_internal.h
index 02861d6fb0..9ba2769c77 100644
--- a/engines/sword2/detection_internal.h
+++ b/engines/sword2/detection/detection_internal.h
@@ -27,7 +27,7 @@
 
 #include "engines/metaengine.h"
 #include "common/gui_options.h"
-#include "sword2/detection_enums.h"
+#include "sword2/detection/detection_enums.h"
 
 /**
  * The contents of this file are helpful in detecting games, 
diff --git a/engines/sword2/detection/module.mk b/engines/sword2/detection/module.mk
new file mode 100644
index 0000000000..8217bc1a33
--- /dev/null
+++ b/engines/sword2/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/sword2/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword2/metaengine.cpp b/engines/sword2/metaengine.cpp
index cee3d1011e..5d1000dc48 100644
--- a/engines/sword2/metaengine.cpp
+++ b/engines/sword2/metaengine.cpp
@@ -34,7 +34,7 @@
 
 #include "sword2/sword2.h"
 #include "sword2/saveload.h"
-#include "sword2/detection_internal.h"
+#include "sword2/detection/detection_internal.h"
 
 class Sword2MetaEngineConnect : public MetaEngineConnect {
 public:
diff --git a/engines/sword2/module.mk b/engines/sword2/module.mk
index a7d3255788..613a95c794 100644
--- a/engines/sword2/module.mk
+++ b/engines/sword2/module.mk
@@ -42,6 +42,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword2/sword2.h b/engines/sword2/sword2.h
index 044f0d4032..241d6088a1 100644
--- a/engines/sword2/sword2.h
+++ b/engines/sword2/sword2.h
@@ -39,7 +39,7 @@
 #include "common/events.h"
 #include "common/util.h"
 #include "common/random.h"
-#include "sword2/detection_enums.h"
+#include "sword2/detection/detection_enums.h"
 
 #define	MAX_starts	100
 #define	MAX_description	100
diff --git a/engines/sword25/detection.cpp b/engines/sword25/detection/detection.cpp
similarity index 96%
rename from engines/sword25/detection.cpp
rename to engines/sword25/detection/detection.cpp
index 7825fa9977..b4e07a2d39 100644
--- a/engines/sword25/detection.cpp
+++ b/engines/sword25/detection/detection.cpp
@@ -24,8 +24,8 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "sword25/detection_enums.h"
-#include "sword25/detection_tables.h"
+#include "sword25/detection/detection_enums.h"
+#include "sword25/detection/detection_tables.h"
 
 static const PlainGameDescriptor sword25Game[] = {
 	{"sword25", "Broken Sword 2.5"},
diff --git a/engines/sword25/detection_enums.h b/engines/sword25/detection/detection_enums.h
similarity index 100%
rename from engines/sword25/detection_enums.h
rename to engines/sword25/detection/detection_enums.h
diff --git a/engines/sword25/detection_tables.h b/engines/sword25/detection/detection_tables.h
similarity index 100%
rename from engines/sword25/detection_tables.h
rename to engines/sword25/detection/detection_tables.h
diff --git a/engines/sword25/detection/module.mk b/engines/sword25/detection/module.mk
new file mode 100644
index 0000000000..598c9008a3
--- /dev/null
+++ b/engines/sword25/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/sword25/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword25/module.mk b/engines/sword25/module.mk
index def48b42ad..28f224dafd 100644
--- a/engines/sword25/module.mk
+++ b/engines/sword25/module.mk
@@ -62,6 +62,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword25/sword25.h b/engines/sword25/sword25.h
index ead4c28fcf..e4bad15d86 100644
--- a/engines/sword25/sword25.h
+++ b/engines/sword25/sword25.h
@@ -27,7 +27,7 @@
 #include "engines/engine.h"
 
 #include "sword25/console.h"
-#include "sword25/detection_enums.h"
+#include "sword25/detection/detection_enums.h"
 
 namespace Common {
 class Error;
diff --git a/engines/teenagent/detection.cpp b/engines/teenagent/detection/detection.cpp
similarity index 100%
rename from engines/teenagent/detection.cpp
rename to engines/teenagent/detection/detection.cpp
diff --git a/engines/teenagent/detection/module.mk b/engines/teenagent/detection/module.mk
new file mode 100644
index 0000000000..e617a5d087
--- /dev/null
+++ b/engines/teenagent/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/teenagent/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/teenagent/module.mk b/engines/teenagent/module.mk
index 8deb130f57..174887687b 100644
--- a/engines/teenagent/module.mk
+++ b/engines/teenagent/module.mk
@@ -26,6 +26,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/testbed/detection.cpp b/engines/testbed/detection/detection.cpp
similarity index 100%
rename from engines/testbed/detection.cpp
rename to engines/testbed/detection/detection.cpp
diff --git a/engines/testbed/detection/module.mk b/engines/testbed/detection/module.mk
new file mode 100644
index 0000000000..0b8aec5b1c
--- /dev/null
+++ b/engines/testbed/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/testbed/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/testbed/module.mk b/engines/testbed/module.mk
index f63cb70efa..02dbcd260e 100644
--- a/engines/testbed/module.mk
+++ b/engines/testbed/module.mk
@@ -44,6 +44,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tinsel/detection.cpp b/engines/tinsel/detection/detection.cpp
similarity index 97%
rename from engines/tinsel/detection.cpp
rename to engines/tinsel/detection/detection.cpp
index e4e364539a..454e0e48c0 100644
--- a/engines/tinsel/detection.cpp
+++ b/engines/tinsel/detection/detection.cpp
@@ -26,8 +26,8 @@
 #include "common/file.h"
 #include "common/md5.h"
 
-#include "tinsel/detection.h"
-#include "tinsel/detection_enums.h"
+#include "tinsel/detection/detection.h"
+#include "tinsel/detection/detection_enums.h"
 
 static const PlainGameDescriptor tinselGames[] = {
 	{"dw", "Discworld"},
@@ -35,7 +35,7 @@ static const PlainGameDescriptor tinselGames[] = {
 	{0, 0}
 };
 
-#include "tinsel/detection_tables.h"
+#include "tinsel/detection/detection_tables.h"
 
 class TinselMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/tinsel/detection.h b/engines/tinsel/detection/detection.h
similarity index 100%
rename from engines/tinsel/detection.h
rename to engines/tinsel/detection/detection.h
diff --git a/engines/tinsel/detection_enums.h b/engines/tinsel/detection/detection_enums.h
similarity index 100%
rename from engines/tinsel/detection_enums.h
rename to engines/tinsel/detection/detection_enums.h
diff --git a/engines/tinsel/detection_tables.h b/engines/tinsel/detection/detection_tables.h
similarity index 100%
rename from engines/tinsel/detection_tables.h
rename to engines/tinsel/detection/detection_tables.h
diff --git a/engines/tinsel/detection/module.mk b/engines/tinsel/detection/module.mk
new file mode 100644
index 0000000000..582856d47b
--- /dev/null
+++ b/engines/tinsel/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/tinsel/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tinsel/metaengine.cpp b/engines/tinsel/metaengine.cpp
index a5a5eb3c67..f167dfdc5f 100644
--- a/engines/tinsel/metaengine.cpp
+++ b/engines/tinsel/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "tinsel/tinsel.h"
 #include "tinsel/savescn.h"	// needed by TinselMetaEngine::
 
-#include "tinsel/detection.h"
+#include "tinsel/detection/detection.h"
 
 namespace Tinsel {
 
diff --git a/engines/tinsel/module.mk b/engines/tinsel/module.mk
index 1a76fd192d..cd7a0cc533 100644
--- a/engines/tinsel/module.mk
+++ b/engines/tinsel/module.mk
@@ -54,6 +54,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tinsel/tinsel.h b/engines/tinsel/tinsel.h
index ad529d15ef..d2e07a4e87 100644
--- a/engines/tinsel/tinsel.h
+++ b/engines/tinsel/tinsel.h
@@ -38,7 +38,7 @@
 #include "tinsel/graphics.h"
 #include "tinsel/sound.h"
 #include "tinsel/dw.h"
-#include "tinsel/detection_enums.h"
+#include "tinsel/detection/detection_enums.h"
 
 /**
  * This is the namespace of the Tinsel engine.
diff --git a/engines/titanic/detection.cpp b/engines/titanic/detection/detection.cpp
similarity index 95%
rename from engines/titanic/detection.cpp
rename to engines/titanic/detection/detection.cpp
index c3aaf829b2..9ba686844e 100644
--- a/engines/titanic/detection.cpp
+++ b/engines/titanic/detection/detection.cpp
@@ -25,14 +25,14 @@
 #include "common/memstream.h"
 #include "engines/advancedDetector.h"
 
-#include "titanic/detection.h"
+#include "titanic/detection/detection.h"
 
 static const PlainGameDescriptor TitanicGames[] = {
 	{"titanic", "Starship Titanic"},
 	{0, 0}
 };
 
-#include "titanic/detection_tables.h"
+#include "titanic/detection/detection_tables.h"
 
 class TitanicMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/titanic/detection.h b/engines/titanic/detection/detection.h
similarity index 100%
rename from engines/titanic/detection.h
rename to engines/titanic/detection/detection.h
diff --git a/engines/titanic/detection_tables.h b/engines/titanic/detection/detection_tables.h
similarity index 100%
rename from engines/titanic/detection_tables.h
rename to engines/titanic/detection/detection_tables.h
diff --git a/engines/titanic/detection/module.mk b/engines/titanic/detection/module.mk
new file mode 100644
index 0000000000..32bd415152
--- /dev/null
+++ b/engines/titanic/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/titanic/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/titanic/metaengine.cpp b/engines/titanic/metaengine.cpp
index 1883f04e2c..7eba0badf2 100644
--- a/engines/titanic/metaengine.cpp
+++ b/engines/titanic/metaengine.cpp
@@ -31,7 +31,7 @@
 #include "engines/advancedDetector.h"
 #include "common/system.h"
 #include "graphics/surface.h"
-#include "titanic/detection.h"
+#include "titanic/detection/detection.h"
 
 namespace Titanic {
 
diff --git a/engines/titanic/module.mk b/engines/titanic/module.mk
index 92cb2a6cd6..551296479a 100644
--- a/engines/titanic/module.mk
+++ b/engines/titanic/module.mk
@@ -531,6 +531,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/toltecs/detection.cpp b/engines/toltecs/detection/detection.cpp
similarity index 99%
rename from engines/toltecs/detection.cpp
rename to engines/toltecs/detection/detection.cpp
index 201d6aba02..abad76da9f 100644
--- a/engines/toltecs/detection.cpp
+++ b/engines/toltecs/detection/detection.cpp
@@ -30,7 +30,7 @@
 #include "common/system.h"
 
 #include "toltecs/toltecs.h"
-#include "toltecs/detection.h"
+#include "toltecs/detection/detection.h"
 
 
 static const PlainGameDescriptor toltecsGames[] = {
diff --git a/engines/toltecs/detection.h b/engines/toltecs/detection/detection.h
similarity index 100%
rename from engines/toltecs/detection.h
rename to engines/toltecs/detection/detection.h
diff --git a/engines/toltecs/detection/module.mk b/engines/toltecs/detection/module.mk
new file mode 100644
index 0000000000..f7067d006d
--- /dev/null
+++ b/engines/toltecs/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/toltecs/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/toltecs/metaengine.cpp b/engines/toltecs/metaengine.cpp
index e3dda22ed2..9ae5ef03db 100644
--- a/engines/toltecs/metaengine.cpp
+++ b/engines/toltecs/metaengine.cpp
@@ -30,7 +30,7 @@
 #include "common/system.h"
 
 #include "toltecs/toltecs.h"
-#include "toltecs/detection.h"
+#include "toltecs/detection/detection.h"
 
 namespace Toltecs {
 
diff --git a/engines/toltecs/module.mk b/engines/toltecs/module.mk
index 146de8caa6..338eb39542 100644
--- a/engines/toltecs/module.mk
+++ b/engines/toltecs/module.mk
@@ -27,6 +27,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tony/detection.cpp b/engines/tony/detection/detection.cpp
similarity index 95%
rename from engines/tony/detection.cpp
rename to engines/tony/detection/detection.cpp
index d02ddea22c..725b55a2e8 100644
--- a/engines/tony/detection.cpp
+++ b/engines/tony/detection/detection.cpp
@@ -24,14 +24,14 @@
 
 #include "engines/advancedDetector.h"
 
-#include "tony/detection.h"
+#include "tony/detection/detection.h"
 
 static const PlainGameDescriptor tonyGames[] = {
 	{"tony", "Tony Tough and the Night of Roasted Moths"},
 	{0, 0}
 };
 
-#include "tony/detection_tables.h"
+#include "tony/detection/detection_tables.h"
 
 class TonyMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/tony/detection.h b/engines/tony/detection/detection.h
similarity index 100%
rename from engines/tony/detection.h
rename to engines/tony/detection/detection.h
diff --git a/engines/tony/detection_tables.h b/engines/tony/detection/detection_tables.h
similarity index 100%
rename from engines/tony/detection_tables.h
rename to engines/tony/detection/detection_tables.h
diff --git a/engines/tony/detection/module.mk b/engines/tony/detection/module.mk
new file mode 100644
index 0000000000..fddb4e8cad
--- /dev/null
+++ b/engines/tony/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/tony/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tony/metaengine.cpp b/engines/tony/metaengine.cpp
index 8c2f6949de..0ca928cb82 100644
--- a/engines/tony/metaengine.cpp
+++ b/engines/tony/metaengine.cpp
@@ -29,7 +29,7 @@
 
 #include "tony/tony.h"
 #include "tony/game.h"
-#include "tony/detection.h"
+#include "tony/detection/detection.h"
 
 namespace Tony {
 
diff --git a/engines/tony/module.mk b/engines/tony/module.mk
index f9f2b1c019..2f99d65b8f 100644
--- a/engines/tony/module.mk
+++ b/engines/tony/module.mk
@@ -31,6 +31,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/toon/detection.cpp b/engines/toon/detection/detection.cpp
similarity index 100%
rename from engines/toon/detection.cpp
rename to engines/toon/detection/detection.cpp
diff --git a/engines/toon/detection/module.mk b/engines/toon/detection/module.mk
new file mode 100644
index 0000000000..c48eb17963
--- /dev/null
+++ b/engines/toon/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/toon/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/toon/module.mk b/engines/toon/module.mk
index c07fceae83..e017ef5abd 100644
--- a/engines/toon/module.mk
+++ b/engines/toon/module.mk
@@ -30,6 +30,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/touche/detection.cpp b/engines/touche/detection/detection.cpp
similarity index 100%
rename from engines/touche/detection.cpp
rename to engines/touche/detection/detection.cpp
diff --git a/engines/touche/detection/module.mk b/engines/touche/detection/module.mk
new file mode 100644
index 0000000000..6bd8004936
--- /dev/null
+++ b/engines/touche/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/touche/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/touche/module.mk b/engines/touche/module.mk
index 7bedba30dc..782c37f3f9 100644
--- a/engines/touche/module.mk
+++ b/engines/touche/module.mk
@@ -19,6 +19,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tsage/detection.cpp b/engines/tsage/detection/detection.cpp
similarity index 93%
rename from engines/tsage/detection.cpp
rename to engines/tsage/detection/detection.cpp
index 129572ac21..b983980b46 100644
--- a/engines/tsage/detection.cpp
+++ b/engines/tsage/detection/detection.cpp
@@ -24,8 +24,8 @@
 
 #include "base/plugins.h"
 
-#include "tsage/detection.h"
-#include "tsage/detection_enums.h"
+#include "tsage/detection/detection.h"
+#include "tsage/detection/detection_enums.h"
 
 static const PlainGameDescriptor tSageGameTitles[] = {
 	{ "ringworld", "Ringworld: Revenge of the Patriarch" },
@@ -35,7 +35,7 @@ static const PlainGameDescriptor tSageGameTitles[] = {
 	{ 0, 0 }
 };
 
-#include "engines/tsage/detection_tables.h"
+#include "tsage/detection/detection_tables.h"
 
 class TSageMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/tsage/detection.h b/engines/tsage/detection/detection.h
similarity index 100%
rename from engines/tsage/detection.h
rename to engines/tsage/detection/detection.h
diff --git a/engines/tsage/detection_enums.h b/engines/tsage/detection/detection_enums.h
similarity index 100%
rename from engines/tsage/detection_enums.h
rename to engines/tsage/detection/detection_enums.h
diff --git a/engines/tsage/detection_tables.h b/engines/tsage/detection/detection_tables.h
similarity index 100%
rename from engines/tsage/detection_tables.h
rename to engines/tsage/detection/detection_tables.h
diff --git a/engines/tsage/detection/module.mk b/engines/tsage/detection/module.mk
new file mode 100644
index 0000000000..9e5e72d952
--- /dev/null
+++ b/engines/tsage/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/tsage/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tsage/metaengine.cpp b/engines/tsage/metaengine.cpp
index a3dd011fa1..eb895ac5e1 100644
--- a/engines/tsage/metaengine.cpp
+++ b/engines/tsage/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "base/plugins.h"
 
 #include "tsage/tsage.h"
-#include "tsage/detection.h"
+#include "tsage/detection/detection.h"
 
 namespace TsAGE {
 
diff --git a/engines/tsage/module.mk b/engines/tsage/module.mk
index 222932b223..ced8967e78 100644
--- a/engines/tsage/module.mk
+++ b/engines/tsage/module.mk
@@ -61,6 +61,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tsage/tsage.h b/engines/tsage/tsage.h
index 06b6f53ae3..18c682ce32 100644
--- a/engines/tsage/tsage.h
+++ b/engines/tsage/tsage.h
@@ -32,7 +32,7 @@
 #include "tsage/events.h"
 #include "tsage/graphics.h"
 #include "tsage/resources.h"
-#include "tsage/detection_enums.h"
+#include "tsage/detection/detection_enums.h"
 
 
 namespace TsAGE {
diff --git a/engines/tucker/detection.cpp b/engines/tucker/detection/detection.cpp
similarity index 98%
rename from engines/tucker/detection.cpp
rename to engines/tucker/detection/detection.cpp
index 50d618721e..a3f5671173 100644
--- a/engines/tucker/detection.cpp
+++ b/engines/tucker/detection/detection.cpp
@@ -23,7 +23,7 @@
 #include "common/config-manager.h"
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
-#include "tucker/detection_enums.h"
+#include "tucker/detection/detection_enums.h"
 
 static const PlainGameDescriptor tuckerGames[] = {
 	{ "tucker", "Bud Tucker in Double Trouble" },
diff --git a/engines/tucker/detection_enums.h b/engines/tucker/detection/detection_enums.h
similarity index 100%
rename from engines/tucker/detection_enums.h
rename to engines/tucker/detection/detection_enums.h
diff --git a/engines/tucker/detection/module.mk b/engines/tucker/detection/module.mk
new file mode 100644
index 0000000000..8633063520
--- /dev/null
+++ b/engines/tucker/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/tucker/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tucker/module.mk b/engines/tucker/module.mk
index df02f313e2..b727879bd0 100644
--- a/engines/tucker/module.mk
+++ b/engines/tucker/module.mk
@@ -18,6 +18,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tucker/tucker.h b/engines/tucker/tucker.h
index 9340d9a3cf..3077a35ec9 100644
--- a/engines/tucker/tucker.h
+++ b/engines/tucker/tucker.h
@@ -38,7 +38,7 @@
 #include "engines/engine.h"
 
 #include "tucker/console.h"
-#include "tucker/detection_enums.h"
+#include "tucker/detection/detection_enums.h"
 
 namespace Audio {
 class RewindableAudioStream;
diff --git a/engines/ultima/detection.cpp b/engines/ultima/detection/detection.cpp
similarity index 97%
rename from engines/ultima/detection.cpp
rename to engines/ultima/detection/detection.cpp
index 8f62f6fe46..3103c5ad55 100644
--- a/engines/ultima/detection.cpp
+++ b/engines/ultima/detection/detection.cpp
@@ -47,7 +47,7 @@ static const PlainGameDescriptor ULTIMA_GAMES[] = {
 
 } // End of namespace Ultima
 
-#include "ultima/detection_tables.h"
+#include "ultima/detection/detection_tables.h"
 
 UltimaMetaEngine::UltimaMetaEngine() : AdvancedMetaEngine(Ultima::GAME_DESCRIPTIONS,
 	        sizeof(Ultima::UltimaGameDescription), Ultima::ULTIMA_GAMES) {
diff --git a/engines/ultima/detection_tables.h b/engines/ultima/detection/detection_tables.h
similarity index 100%
rename from engines/ultima/detection_tables.h
rename to engines/ultima/detection/detection_tables.h
diff --git a/engines/ultima/detection/module.mk b/engines/ultima/detection/module.mk
new file mode 100644
index 0000000000..6130a554fc
--- /dev/null
+++ b/engines/ultima/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/ultima/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/ultima/module.mk b/engines/ultima/module.mk
index 59822cf863..1e324a2937 100644
--- a/engines/ultima/module.mk
+++ b/engines/ultima/module.mk
@@ -591,6 +591,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/voyeur/detection.cpp b/engines/voyeur/detection/detection.cpp
similarity index 95%
rename from engines/voyeur/detection.cpp
rename to engines/voyeur/detection/detection.cpp
index 1afa7bec50..252dca1a74 100644
--- a/engines/voyeur/detection.cpp
+++ b/engines/voyeur/detection/detection.cpp
@@ -25,14 +25,14 @@
 #include "common/str-array.h"
 #include "common/memstream.h"
 #include "engines/advancedDetector.h"
-#include "voyeur/detection.h"
+#include "voyeur/detection/detection.h"
 
 static const PlainGameDescriptor voyeurGames[] = {
 	{"voyeur", "Voyeur"},
 	{0, 0}
 };
 
-#include "voyeur/detection_tables.h"
+#include "voyeur/detection/detection_tables.h"
 
 class VoyeurMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/voyeur/detection.h b/engines/voyeur/detection/detection.h
similarity index 100%
rename from engines/voyeur/detection.h
rename to engines/voyeur/detection/detection.h
diff --git a/engines/voyeur/detection_tables.h b/engines/voyeur/detection/detection_tables.h
similarity index 100%
rename from engines/voyeur/detection_tables.h
rename to engines/voyeur/detection/detection_tables.h
diff --git a/engines/voyeur/detection/module.mk b/engines/voyeur/detection/module.mk
new file mode 100644
index 0000000000..f792114359
--- /dev/null
+++ b/engines/voyeur/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/voyeur/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/voyeur/metaengine.cpp b/engines/voyeur/metaengine.cpp
index ee145ef19f..66792f678c 100644
--- a/engines/voyeur/metaengine.cpp
+++ b/engines/voyeur/metaengine.cpp
@@ -29,7 +29,7 @@
 
 #include "graphics/surface.h"
 
-#include "voyeur/detection.h"
+#include "voyeur/detection/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/voyeur/module.mk b/engines/voyeur/module.mk
index ae6b7625b5..0408d27c01 100644
--- a/engines/voyeur/module.mk
+++ b/engines/voyeur/module.mk
@@ -21,6 +21,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wage/detection.cpp b/engines/wage/detection/detection.cpp
similarity index 97%
rename from engines/wage/detection.cpp
rename to engines/wage/detection/detection.cpp
index 6a1b243745..e877bce602 100644
--- a/engines/wage/detection.cpp
+++ b/engines/wage/detection/detection.cpp
@@ -37,7 +37,7 @@ static const PlainGameDescriptor wageGames[] = {
 	{0, 0}
 };
 
-#include "wage/detection_tables.h"
+#include "wage/detection/detection_tables.h"
 
 class WageMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/wage/detection_tables.h b/engines/wage/detection/detection_tables.h
similarity index 100%
rename from engines/wage/detection_tables.h
rename to engines/wage/detection/detection_tables.h
diff --git a/engines/wage/detection/module.mk b/engines/wage/detection/module.mk
new file mode 100644
index 0000000000..188d75bc8e
--- /dev/null
+++ b/engines/wage/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/wage/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wage/module.mk b/engines/wage/module.mk
index 86b4b86c8c..dd66b59bcb 100644
--- a/engines/wage/module.mk
+++ b/engines/wage/module.mk
@@ -26,6 +26,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wintermute/base/base_sprite.cpp b/engines/wintermute/base/base_sprite.cpp
index eb88e3de09..3e826ceeda 100644
--- a/engines/wintermute/base/base_sprite.cpp
+++ b/engines/wintermute/base/base_sprite.cpp
@@ -41,7 +41,7 @@
 #include "engines/wintermute/base/scriptables/script_value.h"
 #include "engines/wintermute/base/scriptables/script.h"
 #include "engines/wintermute/base/scriptables/script_stack.h"
-#include "engines/wintermute/detection.h"
+#include "engines/wintermute/detection/detection.h"
 
 namespace Wintermute {
 
diff --git a/engines/wintermute/detection.cpp b/engines/wintermute/detection/detection.cpp
similarity index 96%
rename from engines/wintermute/detection.cpp
rename to engines/wintermute/detection/detection.cpp
index a02ed8038f..af82afe9e4 100644
--- a/engines/wintermute/detection.cpp
+++ b/engines/wintermute/detection/detection.cpp
@@ -31,9 +31,9 @@
 #include "engines/metaengine.h"
 
 #include "wintermute/base/base_detection_enums.h"
-#include "wintermute/detection_enums.h"
-#include "engines/wintermute/detection.h"
-#include "engines/wintermute/detection_tables.h"
+#include "wintermute/detection/detection_enums.h"
+#include "wintermute/detection/detection.h"
+#include "wintermute/detection/detection_tables.h"
 
 namespace Wintermute {
 
diff --git a/engines/wintermute/detection.h b/engines/wintermute/detection/detection.h
similarity index 100%
rename from engines/wintermute/detection.h
rename to engines/wintermute/detection/detection.h
diff --git a/engines/wintermute/detection_enums.h b/engines/wintermute/detection/detection_enums.h
similarity index 100%
rename from engines/wintermute/detection_enums.h
rename to engines/wintermute/detection/detection_enums.h
diff --git a/engines/wintermute/detection_tables.h b/engines/wintermute/detection/detection_tables.h
similarity index 100%
rename from engines/wintermute/detection_tables.h
rename to engines/wintermute/detection/detection_tables.h
diff --git a/engines/wintermute/detection/module.mk b/engines/wintermute/detection/module.mk
new file mode 100644
index 0000000000..47672db167
--- /dev/null
+++ b/engines/wintermute/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/wintermute/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wintermute/metaengine.cpp b/engines/wintermute/metaengine.cpp
index 03c717dc5d..7b9461379a 100644
--- a/engines/wintermute/metaengine.cpp
+++ b/engines/wintermute/metaengine.cpp
@@ -30,8 +30,8 @@
 
 // Detection related files.
 #include "wintermute/base/base_detection_enums.h"
-#include "wintermute/detection.h"
-#include "engines/wintermute/detection_tables.h"
+#include "wintermute/detection/detection.h"
+#include "wintermute/detection/detection_tables.h"
 
 namespace Wintermute {
 
diff --git a/engines/wintermute/module.mk b/engines/wintermute/module.mk
index 9a701fbd12..8dbe0ab3ff 100644
--- a/engines/wintermute/module.mk
+++ b/engines/wintermute/module.mk
@@ -154,6 +154,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wintermute/wintermute.cpp b/engines/wintermute/wintermute.cpp
index 579fd54bfc..130fed3fb6 100644
--- a/engines/wintermute/wintermute.cpp
+++ b/engines/wintermute/wintermute.cpp
@@ -37,7 +37,7 @@
 #include "engines/wintermute/debugger.h"
 #include "engines/wintermute/platform_osystem.h"
 #include "engines/wintermute/base/base_engine.h"
-#include "engines/wintermute/detection.h"
+#include "engines/wintermute/detection/detection.h"
 
 #include "engines/wintermute/base/sound/base_sound_manager.h"
 #include "engines/wintermute/base/base_file_manager.h"
diff --git a/engines/wintermute/wintermute.h b/engines/wintermute/wintermute.h
index 08bfa4f6e8..8ba0f05021 100644
--- a/engines/wintermute/wintermute.h
+++ b/engines/wintermute/wintermute.h
@@ -26,7 +26,7 @@
 #include "engines/engine.h"
 #include "gui/debugger.h"
 #include "common/fs.h"
-#include "wintermute/detection_enums.h"
+#include "wintermute/detection/detection_enums.h"
 
 namespace Wintermute {
 
diff --git a/engines/xeen/detection.cpp b/engines/xeen/detection/detection.cpp
similarity index 95%
rename from engines/xeen/detection.cpp
rename to engines/xeen/detection/detection.cpp
index 79343db575..a73bf9d1e8 100644
--- a/engines/xeen/detection.cpp
+++ b/engines/xeen/detection/detection.cpp
@@ -24,8 +24,8 @@
 #include "engines/advancedDetector.h"
 #include "common/translation.h"
 
-#include "xeen/detection.h"
-#include "xeen/detection_enums.h"
+#include "xeen/detection/detection.h"
+#include "xeen/detection/detection_enums.h"
 
 static const PlainGameDescriptor XeenGames[] = {
 	{ "cloudsofxeen", "Might and Magic IV: Clouds of Xeen" },
@@ -38,7 +38,7 @@ static const PlainGameDescriptor XeenGames[] = {
 #define GAMEOPTION_SHOW_ITEM_COSTS	GUIO_GAMEOPTIONS1
 #define GAMEOPTION_DURABLE_ARMOR	GUIO_GAMEOPTIONS2
 
-#include "xeen/detection_tables.h"
+#include "xeen/detection/detection_tables.h"
 
 
 static const ADExtraGuiOptionsMap optionsList[] = {
diff --git a/engines/xeen/detection.h b/engines/xeen/detection/detection.h
similarity index 100%
rename from engines/xeen/detection.h
rename to engines/xeen/detection/detection.h
diff --git a/engines/xeen/detection_enums.h b/engines/xeen/detection/detection_enums.h
similarity index 100%
rename from engines/xeen/detection_enums.h
rename to engines/xeen/detection/detection_enums.h
diff --git a/engines/xeen/detection_tables.h b/engines/xeen/detection/detection_tables.h
similarity index 100%
rename from engines/xeen/detection_tables.h
rename to engines/xeen/detection/detection_tables.h
diff --git a/engines/xeen/detection/module.mk b/engines/xeen/detection/module.mk
new file mode 100644
index 0000000000..f940a4abc6
--- /dev/null
+++ b/engines/xeen/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/xeen/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/xeen/metaengine.cpp b/engines/xeen/metaengine.cpp
index bbeca61390..ef2c824f16 100644
--- a/engines/xeen/metaengine.cpp
+++ b/engines/xeen/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "engines/advancedDetector.h"
 #include "common/system.h"
 #include "common/translation.h"
-#include "xeen/detection.h"
+#include "xeen/detection/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/xeen/module.mk b/engines/xeen/module.mk
index 71afe7762d..f2468df3fd 100644
--- a/engines/xeen/module.mk
+++ b/engines/xeen/module.mk
@@ -68,6 +68,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/xeen/xeen.h b/engines/xeen/xeen.h
index 503d6a5a99..628cc57d25 100644
--- a/engines/xeen/xeen.h
+++ b/engines/xeen/xeen.h
@@ -47,7 +47,7 @@
 #include "xeen/sound.h"
 #include "xeen/spells.h"
 #include "xeen/window.h"
-#include "xeen/detection_enums.h"
+#include "xeen/detection/detection_enums.h"
 
 /**
  * This is the namespace of the Xeen engine.
diff --git a/engines/zvision/detection.cpp b/engines/zvision/detection/detection.cpp
similarity index 92%
rename from engines/zvision/detection.cpp
rename to engines/zvision/detection/detection.cpp
index 25a9c2ca18..290aba42f5 100644
--- a/engines/zvision/detection.cpp
+++ b/engines/zvision/detection/detection.cpp
@@ -29,9 +29,9 @@
 #include "common/translation.h"
 #include "common/str-array.h"
 
-#include "zvision/detection_enums.h"
-#include "zvision/detection.h"
-#include "zvision/detection_tables.h"
+#include "zvision/detection/detection_enums.h"
+#include "zvision/detection/detection.h"
+#include "zvision/detection/detection_tables.h"
 
 class ZVisionMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/zvision/detection.h b/engines/zvision/detection/detection.h
similarity index 100%
rename from engines/zvision/detection.h
rename to engines/zvision/detection/detection.h
diff --git a/engines/zvision/detection_enums.h b/engines/zvision/detection/detection_enums.h
similarity index 100%
rename from engines/zvision/detection_enums.h
rename to engines/zvision/detection/detection_enums.h
diff --git a/engines/zvision/detection_tables.h b/engines/zvision/detection/detection_tables.h
similarity index 100%
rename from engines/zvision/detection_tables.h
rename to engines/zvision/detection/detection_tables.h
diff --git a/engines/zvision/detection/module.mk b/engines/zvision/detection/module.mk
new file mode 100644
index 0000000000..ce2ddb62d7
--- /dev/null
+++ b/engines/zvision/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/zvision/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/zvision/metaengine.cpp b/engines/zvision/metaengine.cpp
index 1732a0e5ed..bf3169fa6e 100644
--- a/engines/zvision/metaengine.cpp
+++ b/engines/zvision/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "zvision/zvision.h"
 #include "zvision/file/save_manager.h"
 #include "zvision/scripting/script_manager.h"
-#include "zvision/detection.h"
+#include "zvision/detection/detection.h"
 
 #include "backends/keymapper/action.h"
 #include "backends/keymapper/keymapper.h"
diff --git a/engines/zvision/module.mk b/engines/zvision/module.mk
index 70728e39dc..89265adf49 100644
--- a/engines/zvision/module.mk
+++ b/engines/zvision/module.mk
@@ -60,6 +60,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/zvision/zvision.h b/engines/zvision/zvision.h
index 5cdb4ea9cb..0677abe562 100644
--- a/engines/zvision/zvision.h
+++ b/engines/zvision/zvision.h
@@ -26,7 +26,7 @@
 
 #include "zvision/core/clock.h"
 #include "zvision/file/search_manager.h"
-#include "zvision/detection_enums.h"
+#include "zvision/detection/detection_enums.h"
 
 #include "common/random.h"
 #include "common/events.h"


Commit: 78dd712a1c6b4f1474da26c2c55ef74c3ba16861
    https://github.com/scummvm/scummvm/commit/78dd712a1c6b4f1474da26c2c55ef74c3ba16861
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PARALLACTION: Adapt to new detection modules and misc changes.

- Move common enums into detection_enums.h
- Make a new module for detection. See previous commit notes for more info.

Changed paths:
  A engines/parallaction/detection/detection.cpp
  A engines/parallaction/detection/detection.h
  A engines/parallaction/detection/detection_enums.h
  A engines/parallaction/detection/module.mk
  R engines/parallaction/detection.cpp
  R engines/parallaction/detection.h
    engines/parallaction/metaengine.cpp
    engines/parallaction/module.mk
    engines/parallaction/parallaction.h


diff --git a/engines/parallaction/detection.cpp b/engines/parallaction/detection/detection.cpp
similarity index 98%
rename from engines/parallaction/detection.cpp
rename to engines/parallaction/detection/detection.cpp
index 9351c247ba..ad1462260b 100644
--- a/engines/parallaction/detection.cpp
+++ b/engines/parallaction/detection/detection.cpp
@@ -27,8 +27,8 @@
 #include "common/system.h"
 #include "common/textconsole.h"
 
-#include "parallaction/parallaction.h"
-#include "parallaction/detection.h"
+#include "parallaction/detection/detection_enums.h"
+#include "parallaction/detection/detection.h"
 
 static const PlainGameDescriptor parallactionGames[] = {
 	{"nippon", "Nippon Safes Inc."},
diff --git a/engines/parallaction/detection.h b/engines/parallaction/detection/detection.h
similarity index 100%
rename from engines/parallaction/detection.h
rename to engines/parallaction/detection/detection.h
diff --git a/engines/parallaction/detection/detection_enums.h b/engines/parallaction/detection/detection_enums.h
new file mode 100644
index 0000000000..9ab631a916
--- /dev/null
+++ b/engines/parallaction/detection/detection_enums.h
@@ -0,0 +1,44 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef PARALLACTION_DETECTION_ENUMS_H
+#define PARALLACTION_DETECTION_ENUMS_H
+
+namespace Parallaction {
+
+enum {
+	GF_DEMO = 1 << 0,
+	GF_LANG_EN = 1 << 1,
+	GF_LANG_FR = 1 << 2,
+	GF_LANG_DE = 1 << 3,
+	GF_LANG_IT = 1 << 4,
+	GF_LANG_MULT = 1 << 5
+};
+
+enum ParallactionGameType {
+	GType_Nippon = 1,
+	GType_BRA
+};
+
+} // End of namespace Parallaction
+
+#endif // PARALLACTION_DETECTION_ENUMS_H
diff --git a/engines/parallaction/detection/module.mk b/engines/parallaction/detection/module.mk
new file mode 100644
index 0000000000..ce4c2ad427
--- /dev/null
+++ b/engines/parallaction/detection/module.mk
@@ -0,0 +1,4 @@
+MODULE := engines/parallaction/detection
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/parallaction/metaengine.cpp b/engines/parallaction/metaengine.cpp
index 42ec7d6520..41be04b0e0 100644
--- a/engines/parallaction/metaengine.cpp
+++ b/engines/parallaction/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "common/textconsole.h"
 
 #include "parallaction/parallaction.h"
-#include "parallaction/detection.h"
+#include "parallaction/detection/detection.h"
 
 namespace Parallaction {
 
diff --git a/engines/parallaction/module.mk b/engines/parallaction/module.mk
index 3ad5b48b05..7dba9f9a2b 100644
--- a/engines/parallaction/module.mk
+++ b/engines/parallaction/module.mk
@@ -41,6 +41,3 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/parallaction/parallaction.h b/engines/parallaction/parallaction.h
index 49eadd839b..54ccf06241 100644
--- a/engines/parallaction/parallaction.h
+++ b/engines/parallaction/parallaction.h
@@ -37,6 +37,7 @@
 #include "parallaction/inventory.h"
 #include "parallaction/objects.h"
 #include "parallaction/disk.h"
+#include "parallaction/detection/detection_enums.h"
 
 #define PATH_LEN	200
 
@@ -65,16 +66,6 @@ enum {
 	kDebugInventory = 1 << 9
 };
 
-enum {
-	GF_DEMO = 1 << 0,
-	GF_LANG_EN = 1 << 1,
-	GF_LANG_FR = 1 << 2,
-	GF_LANG_DE = 1 << 3,
-	GF_LANG_IT = 1 << 4,
-	GF_LANG_MULT = 1 << 5
-};
-
-
 enum EngineFlags {
 	kEnginePauseJobs	= (1 << 1),
 	kEngineWalking		= (1 << 3),
@@ -94,11 +85,6 @@ enum {
 	kEvIngameMenu   = 8000
 };
 
-enum ParallactionGameType {
-	GType_Nippon = 1,
-	GType_BRA
-};
-
 struct PARALLACTIONGameDescription;
 
 


Commit: 2ee4cd287840d6f75b2f27821ff24b2d9202e57e
    https://github.com/scummvm/scummvm/commit/2ee4cd287840d6f75b2f27821ff24b2d9202e57e
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CONFIGURE: Add functionality for detection modules for each engine

- In engines.mk, add another module "enginename/detection"
- This module is always added, regardless if the engine is enabled or not.
- Remove the array which helped out when each individual engine port was being added over.

Changed paths:
    configure


diff --git a/configure b/configure
index 7de4a9b85b..cf42dd7fde 100755
--- a/configure
+++ b/configure
@@ -6176,41 +6176,27 @@ MODULES += detection
 EOF
 fi
 
-declare -a static_detect_engines=("PLUMBERS" "AGI" "SCUMM" "SKY" "DREAMWEB" "DRASCULA" "LURE"
-								  "SWORD1" "SWORD2" "SWORD25" "ADL" "QUEEN" "CGE" "CGE2" "ACCESS"
-								  "ZVISION" "AGOS" "GOB" "COMPOSER" "DM" "DRACI" "DRAGONS" "GNAP"
-								  "GRIFFON" "GROOVIE" "HDB" "HOPKINS" "HUGO" "ILLUSIONS" "KINGDOM"
-								  "KYRA" "LAB" "LASTEXPRESS" "LILLIPUT" "MACVENTURE" "MADE" "MADS"
-								  "MORTEVIELLE" "MUTATIONOFJB" "NEVERHOOD" "PARALLACTION" "PEGASUS"
-								  "PETKA" "PINK" "PRINCE" "SHERLOCK" "SLUDGE" "STARTREK" "SUPERNOVA"
-								  "TEENAGENT" "TESTBED" "TINSEL" "TITANIC" "TOLTECS" "TONY" "TOON"
-								  "TOUCHE" "TSAGE" "TUCKER" "VOYEUR" "WAGE" "AVALANCHE" "BBVS"
-								  "BLADERUNNER" "CHEWY" "CINE" "CRUISE" "CRYO" "CRYOMNI3D" "DIRECTOR"
-								  "FULLPIPE" "SAGA" "XEEN" "WINTERMUTE" "SCI" "MOHAWK" "ULTIMA" "GLK")
+# Name which is suffixed to each detection plugin
 detectId="_DETECTION"
 
-##################################################
-
-declare -a engi=("AGI" "PLUMBERS")
-
 echo "Creating detection/detection_table.h"
 cat > detection/detection_table.h << EOF
 /* This file is automatically generated by configure */
 /* DO NOT EDIT MANUALLY */
-// This file is being included by "detection/detection.cpp"
+// This file is being included by "detection/detection.cpp" and "base/plugins.cpp"
 EOF
 
-# Below line, we'll have for each engine in sorted engines: LINK_PLUGIN-detection.
-# Temporary to see, we have 2 engines.
-# Once each engine's modules are shifted in the same way as these 2, we can remove the array
-# and do it for all engines.
-for engine in "${engi[@]}"; do
-cat >> detection/detection_table.h << EOF
-LINK_PLUGIN(${engine}${detectId})
+for engine in $_sorted_engines; do
+	if test "`get_engine_sub $engine`" = "no" ; then
+		j=`echo $engine | tr '[:lower:]' '[:upper:]'`
+		detectEngine="${j}${detectId}"
+		cat >> detection/detection_table.h << EOF
+LINK_PLUGIN($detectEngine)
+
 EOF
+	fi
 done
 
-##################################################
 
 echo "Creating engines/plugins_table.h"
 cat > engines/plugins_table.h << EOF
@@ -6222,22 +6208,6 @@ EOF
 for engine in $_sorted_engines; do
 	if test "`get_engine_sub $engine`" = "no" ; then
 		j=`echo $engine | tr '[:lower:]' '[:upper:]'`
-		for eng in "${static_detect_engines[@]}"; do
-			if [ $j == $eng ]; then
-				cat >> engines/plugins_table.h << EOF
-#if PLUGIN_ENABLED($j)
-//LINK_PLUGIN(${j}${detectId})
-#endif
-EOF
-				cat >> engines/plugins_table.h << EOF
-#if PLUGIN_ENABLED_STATIC($j)
-LINK_PLUGIN($j)
-#endif
-EOF
-				continue 2
-			fi
-		done
-
 		cat >> engines/plugins_table.h << EOF
 #if PLUGIN_ENABLED_STATIC($j)
 LINK_PLUGIN($j)


Commit: 11f46399b678608f29e80cda892950d12897b6f7
    https://github.com/scummvm/scummvm/commit/11f46399b678608f29e80cda892950d12897b6f7
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GIT: Add detection_tables header to .gitignore

- It is generated by configure and works similiarly to plugins_table.

Changed paths:
    .gitignore


diff --git a/.gitignore b/.gitignore
index 9782830c91..2f2a32423e 100644
--- a/.gitignore
+++ b/.gitignore
@@ -121,6 +121,7 @@ project.xcworkspace
 
 /plugins
 
+/detection/detection_table.h
 /engines/plugins_table.h
 /engines/engines.mk
 


Commit: 7615f37698d185ee980cdfb7014b4b528f055eb6
    https://github.com/scummvm/scummvm/commit/7615f37698d185ee980cdfb7014b4b528f055eb6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Add detection tables header file when getting static plugins.

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index fdaa94cd6b..7456ab02df 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -96,6 +96,11 @@ public:
 		// Engine plugins
 		#include "engines/plugins_table.h"
 
+		#ifndef UNCACHED_PLUGINS
+		// Engine-detection plugins are included if we don't use uncached plugins.
+		#include "detection/detection_table.h"
+		#endif
+
 		// Music plugins
 		// TODO: Use defines to disable or enable each MIDI driver as a
 		// static/dynamic plugin, like it's done for the engines


Commit: fea29b04ac6c2a7fade9850ff60e5eadb9602571
    https://github.com/scummvm/scummvm/commit/fea29b04ac6c2a7fade9850ff60e5eadb9602571
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Add a plugin suffix only if it is available

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index 7456ab02df..cd68e2be40 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -344,7 +344,9 @@ void PluginManagerUncached::init() {
 	unloadPluginsExcept(PLUGIN_TYPE_ENGINE, NULL, false); // empty the engine plugins
 
 	Common::String detectPluginName = "detection";
+#ifdef PLUGIN_SUFFIX
 	detectPluginName += PLUGIN_SUFFIX;
+#endif
 
 	bool foundDetectPlugin = false;
 


Commit: f3b9477893b7d10b0b196863a53cec38e04c0f91
    https://github.com/scummvm/scummvm/commit/f3b9477893b7d10b0b196863a53cec38e04c0f91
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: ALL: Add header guards for the new detection-header files.

Changed paths:
    engines/access/detection/detection.h
    engines/access/detection/detection_enums.h
    engines/agos/detection/detection.h
    engines/agos/detection/detection_enums.h
    engines/avalanche/detection/detection.h
    engines/bbvs/detection/detection_enums.h
    engines/chewy/detection/detection.h
    engines/cine/detection/detection.h
    engines/cine/detection/detection_enums.h
    engines/composer/detection/detection.h
    engines/composer/detection/detection_enums.h
    engines/cruise/detection/detection.h
    engines/cryomni3d/detection/detection.cpp
    engines/cryomni3d/detection/detection.h
    engines/cryomni3d/detection/detection_enums.h
    engines/cryomni3d/detection/detection_tables.h
    engines/director/detection/detection.h
    engines/director/detection/detection_enums.h
    engines/dm/detection/detection.h
    engines/dm/detection/detection_enums.h
    engines/dragons/detection/detection.h
    engines/dragons/detection/detection_enums.h
    engines/gob/detection/detection.h
    engines/gob/detection/detection_enums.h
    engines/hdb/detection/detection_enums.h
    engines/hopkins/detection/detection.h
    engines/hugo/detection/detection.h
    engines/hugo/detection/detection_enums.h
    engines/illusions/detection/detection.h
    engines/illusions/detection/detection_enums.h
    engines/kyra/detection/detection.h
    engines/kyra/detection/detection_enums.h
    engines/lab/detection/detection_enums.h
    engines/lilliput/detection/detection.h
    engines/lilliput/detection/detection_enums.h
    engines/lure/detection/detection.h
    engines/lure/detection/detection_enums.h
    engines/made/detection/detection.h
    engines/made/detection/detection_enums.h
    engines/mads/detection/detection.h
    engines/mads/detection/detection_enums.h
    engines/mortevielle/detection/detection.h
    engines/mortevielle/detection/detection_enums.h
    engines/neverhood/detection/detection.h
    engines/parallaction/detection/detection.h
    engines/pegasus/detection/detection.h
    engines/prince/detection/detection.h
    engines/prince/detection/detection_enums.h
    engines/queen/detection/detection.h
    engines/saga/detection/detection.h
    engines/saga/detection/detection_enums.h
    engines/sherlock/detection/detection.h
    engines/sherlock/detection/detection_enums.h
    engines/sludge/detection/detection.h
    engines/startrek/detection/detection.h
    engines/startrek/detection/detection_enums.h
    engines/sword25/detection/detection_enums.h
    engines/tinsel/detection/detection.h
    engines/tinsel/detection/detection_enums.h
    engines/titanic/detection/detection.h
    engines/toltecs/detection/detection.h
    engines/tsage/detection/detection.h
    engines/tsage/detection/detection_enums.h
    engines/tucker/detection/detection_enums.h
    engines/voyeur/detection/detection.h
    engines/wintermute/detection/detection_enums.h
    engines/xeen/detection/detection.h
    engines/xeen/detection/detection_enums.h
    engines/zvision/detection/detection.h
    engines/zvision/detection/detection_enums.h


diff --git a/engines/access/detection/detection.h b/engines/access/detection/detection.h
index bd69c92dc1..67ee624ac2 100644
--- a/engines/access/detection/detection.h
+++ b/engines/access/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef ACCESS_DETECTION_H
+#define ACCESS_DETECTION_H
+
 namespace Access {
 
 struct AccessGameDescription {
@@ -30,3 +33,5 @@ struct AccessGameDescription {
 };
 
 } // End of namespace Access
+
+#endif // ACCESS_DETECTION_H
diff --git a/engines/access/detection/detection_enums.h b/engines/access/detection/detection_enums.h
index 06bb295b65..805bde83cc 100644
--- a/engines/access/detection/detection_enums.h
+++ b/engines/access/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef ACCESS_DETECTION_ENUMS_H
+#define ACCESS_DETECTION_ENUMS_H
+
 namespace Access {
 
 enum {
@@ -29,3 +32,5 @@ enum {
 };
 
 } // End of namespace Access
+
+#endif // ACCESS_DETECTION_ENUMS_H
diff --git a/engines/agos/detection/detection.h b/engines/agos/detection/detection.h
index 304d7fc4ef..fde741c438 100644
--- a/engines/agos/detection/detection.h
+++ b/engines/agos/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef AGOS_DETECTION_H
+#define AGOS_DETECTION_H
+
 namespace AGOS {
 
 struct AGOSGameDescription {
@@ -31,3 +34,5 @@ struct AGOSGameDescription {
 };
 
 } // End of namespace AGOS
+
+#endif // AGOS_DETECTION_H
diff --git a/engines/agos/detection/detection_enums.h b/engines/agos/detection/detection_enums.h
index ce0e9792c8..3dee3df101 100644
--- a/engines/agos/detection/detection_enums.h
+++ b/engines/agos/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef AGOS_DETECTION_ENUMS_H
+#define AGOS_DETECTION_ENUMS_H
+
 namespace AGOS {
 
 // Enums related to detection, from the main agos/agos.h file.
@@ -35,3 +38,5 @@ enum SIMONGameType {
 };
 
 } // End of namespace AGOS
+
+#endif // AGOS_DETECTION_ENUMS_H
diff --git a/engines/avalanche/detection/detection.h b/engines/avalanche/detection/detection.h
index 01512a0558..a458d33f47 100644
--- a/engines/avalanche/detection/detection.h
+++ b/engines/avalanche/detection/detection.h
@@ -25,6 +25,8 @@
  * Copyright (c) 1994-1995 Mike, Mark and Thomas Thurman.
  */
 
+#ifndef AVALANCHE_DETECTION_H
+#define AVALANCHE_DETECTION_H
 
 namespace Avalanche {
 
@@ -33,3 +35,5 @@ struct AvalancheGameDescription {
 };
 
 } // End of namespace Avalanche
+
+#endif // AVALANCHE_DETECTION_H
diff --git a/engines/bbvs/detection/detection_enums.h b/engines/bbvs/detection/detection_enums.h
index 70bef6ec10..919327cfd7 100644
--- a/engines/bbvs/detection/detection_enums.h
+++ b/engines/bbvs/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef BBVS_DETECTION_ENUMS_H
+#define BBVS_DETECTION_ENUMS_H
+
 namespace Bbvs {
 
 enum {
@@ -27,3 +30,5 @@ enum {
 };
 
 } // End of namespace Bbvs
+
+#endif // BBVS_DETECTION_ENUMS_H
diff --git a/engines/chewy/detection/detection.h b/engines/chewy/detection/detection.h
index 6d9a4e8937..0d90725084 100644
--- a/engines/chewy/detection/detection.h
+++ b/engines/chewy/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef CHEWY_DETECTION_H
+#define CHEWY_DETECTION_H
+
 namespace Chewy {
 
 struct ChewyGameDescription {
@@ -27,3 +30,5 @@ struct ChewyGameDescription {
 };
 
 } // End of namespace Chewy
+
+#endif // CHEWY_DETECTION_H
diff --git a/engines/cine/detection/detection.h b/engines/cine/detection/detection.h
index 5021d69934..fa0573a5aa 100644
--- a/engines/cine/detection/detection.h
+++ b/engines/cine/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef CINE_DETECTION_H
+#define CINE_DETECTION_H
+
 namespace Cine {
 
 struct CINEGameDescription {
@@ -30,3 +33,5 @@ struct CINEGameDescription {
 };
 
 } // End of namespace Cine
+
+#endif // CINE_DETECTION_H
diff --git a/engines/cine/detection/detection_enums.h b/engines/cine/detection/detection_enums.h
index 3acc17b12b..2d37a005fe 100644
--- a/engines/cine/detection/detection_enums.h
+++ b/engines/cine/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef CINE_DETECTION_ENUMS_H
+#define CINE_DETECTION_ENUMS_H
+
 namespace Cine {
 
 enum CineGameType {
@@ -35,3 +38,5 @@ enum CineGameFeatures {
 };
 
 } // End of namespace Cine
+
+#endif // CINE_DETECTION_ENUMS_H
diff --git a/engines/composer/detection/detection.h b/engines/composer/detection/detection.h
index 91271c7ad5..d1871f3c9f 100644
--- a/engines/composer/detection/detection.h
+++ b/engines/composer/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef COMPOSER_DETECTION_H
+#define COMPOSER_DETECTION_H
+
 namespace Composer {
 
 struct ComposerGameDescription {
@@ -29,3 +32,5 @@ struct ComposerGameDescription {
 };
 
 } // End of namespace Composer
+
+#endif // COMPOSER_DETECTION_H
diff --git a/engines/composer/detection/detection_enums.h b/engines/composer/detection/detection_enums.h
index 7dee54a1d8..981435b681 100644
--- a/engines/composer/detection/detection_enums.h
+++ b/engines/composer/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef COMPOSER_DETECTION_ENUMS_H
+#define COMPOSER_DETECTION_ENUMS_H
+
 namespace Composer {
 
 enum GameType {
@@ -34,3 +37,5 @@ enum GameFileTypes {
 };
 
 } // End of namespace Composer
+
+#endif // COMPOSER_DETECTION_ENUMS_H
diff --git a/engines/cruise/detection/detection.h b/engines/cruise/detection/detection.h
index 6953a3a0b6..104d3e764a 100644
--- a/engines/cruise/detection/detection.h
+++ b/engines/cruise/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef CRUISE_DETECTION_H
+#define CRUISE_DETECTION_H
+
 namespace Cruise {
 
 struct CRUISEGameDescription {
@@ -27,3 +30,5 @@ struct CRUISEGameDescription {
 };
 
 } // End of namespace Cruise
+
+#endif // CRUISE_DETECTION_H
diff --git a/engines/cryomni3d/detection/detection.cpp b/engines/cryomni3d/detection/detection.cpp
index b3f7467a2f..6a77e5039e 100644
--- a/engines/cryomni3d/detection/detection.cpp
+++ b/engines/cryomni3d/detection/detection.cpp
@@ -37,8 +37,12 @@ static const PlainGameDescriptor cryomni3DGames[] = {
 	{0, 0}
 };
 
+} // End of namespace CryOmni3D
+
 #include "cryomni3d/detection/detection_tables.h"
 
+namespace CryOmni3D {
+
 static const ADExtraGuiOptionsMap optionsList[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
diff --git a/engines/cryomni3d/detection/detection.h b/engines/cryomni3d/detection/detection.h
index 4d3684b6ea..dba8dc8788 100644
--- a/engines/cryomni3d/detection/detection.h
+++ b/engines/cryomni3d/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef CRYOMNI3D_DETECTION_H
+#define CRYOMNI3D_DETECTION_H
+
 namespace CryOmni3D {
 
 struct CryOmni3DGameDescription {
@@ -30,3 +33,5 @@ struct CryOmni3DGameDescription {
 };
 
 } // End of namespace CryOmni3D
+
+#endif // CRYOMNI3D_DETECTION_H
diff --git a/engines/cryomni3d/detection/detection_enums.h b/engines/cryomni3d/detection/detection_enums.h
index cf6ea30ef2..b619443c99 100644
--- a/engines/cryomni3d/detection/detection_enums.h
+++ b/engines/cryomni3d/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef CRYOMNI3D_DETECTION_ENUMS_H
+#define CRYOMNI3D_DETECTION_ENUMS_H
+
 namespace CryOmni3D {
 
 enum CryOmni3DGameType {
@@ -41,3 +44,5 @@ enum CryOmni3DGameFeatures {
 };
 
 } // End of namespace CryOmni3D
+
+#endif // CRYOMNI3D_DETECTION_ENUMS_H
diff --git a/engines/cryomni3d/detection/detection_tables.h b/engines/cryomni3d/detection/detection_tables.h
index dab0bcef0c..bf42e3e02f 100644
--- a/engines/cryomni3d/detection/detection_tables.h
+++ b/engines/cryomni3d/detection/detection_tables.h
@@ -20,7 +20,7 @@
  *
  */
 
-// This file is included in CryOmni3D namespace
+namespace CryOmni3D {
 
 #define GUI_OPTIONS_VERSAILLES                   GUIO3(GUIO_NOMIDI, GUIO_NOSFX, GUIO_NOASPECT)
 
@@ -579,3 +579,5 @@ static const ADFileBasedFallback fileBased[] = {
 	{ &fallbackDescs[0].desc,  { "11D_LEB1.HNM", "COFBOUM.HNM", "Versailles", 0 } },
 	{ 0, { 0 } }
 };
+
+} // End of namespace CryOmni3D
diff --git a/engines/director/detection/detection.h b/engines/director/detection/detection.h
index 2f15963e2b..7f4b7441c5 100644
--- a/engines/director/detection/detection.h
+++ b/engines/director/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef DIRECTOR_DETECTION_H
+#define DIRECTOR_DETECTION_H
+
 namespace Director {
 
 struct DirectorGameDescription {
@@ -30,3 +33,5 @@ struct DirectorGameDescription {
 };
 
 } // End of namespace Director
+
+#endif // DIRECTOR_DETECTION_H
diff --git a/engines/director/detection/detection_enums.h b/engines/director/detection/detection_enums.h
index 0be492a98a..21630a4fcd 100644
--- a/engines/director/detection/detection_enums.h
+++ b/engines/director/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef DIRECTOR_DETECTION_ENUMS_H
+#define DIRECTOR_DETECTION_ENUMS_H
+
 namespace Director {
 
 enum DirectorGameGID {
@@ -29,3 +32,5 @@ enum DirectorGameGID {
 };
 
 } // End of namespace Director
+
+#endif // DIRECTOR_DETECTION_ENUMS_H
diff --git a/engines/dm/detection/detection.h b/engines/dm/detection/detection.h
index f2b106be5c..9cc1e4f09a 100644
--- a/engines/dm/detection/detection.h
+++ b/engines/dm/detection/detection.h
@@ -25,6 +25,9 @@
 * maintainer of the Dungeon Master Encyclopaedia (http://dmweb.free.fr/)
 */
 
+#ifndef DM_DETECTION_H
+#define DM_DETECTION_H
+
 namespace DM {
 
 struct DMADGameDescription {
@@ -40,3 +43,5 @@ struct DMADGameDescription {
 };
 
 } // End of namespace DM
+
+#endif // DM_DETECTION_H
diff --git a/engines/dm/detection/detection_enums.h b/engines/dm/detection/detection_enums.h
index 6c20025210..ae9978b691 100644
--- a/engines/dm/detection/detection_enums.h
+++ b/engines/dm/detection/detection_enums.h
@@ -25,6 +25,9 @@
 * maintainer of the Dungeon Master Encyclopaedia (http://dmweb.free.fr/)
 */
 
+#ifndef DM_DETECTION_ENUMS_H
+#define DM_DETECTION_ENUMS_H
+
 namespace DM {
 
 enum OriginalSaveFormat {
@@ -64,3 +67,5 @@ enum SaveTarget {
 };
 
 } // End of namespace DM
+
+#endif // DM_DETECTION_ENUMS_H
diff --git a/engines/dragons/detection/detection.h b/engines/dragons/detection/detection.h
index aee353b6ec..958b4c4c50 100644
--- a/engines/dragons/detection/detection.h
+++ b/engines/dragons/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef DRAGONS_DETECTION_H
+#define DRAGONS_DETECTION_H
+
 namespace Dragons {
 
 struct DragonsGameDescription {
@@ -28,3 +31,5 @@ struct DragonsGameDescription {
 };
 
 } // End of namespace Dragons
+
+#endif // DRAGONS_DETECTION_H
diff --git a/engines/dragons/detection/detection_enums.h b/engines/dragons/detection/detection_enums.h
index 8f595b2616..5822ad99ba 100644
--- a/engines/dragons/detection/detection_enums.h
+++ b/engines/dragons/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef DRAGONS_DETECTION_ENUMS_H
+#define DRAGONS_DETECTION_ENUMS_H
+
 namespace Dragons {
 
 enum {
@@ -28,3 +31,5 @@ enum {
 };
 
 } // End of namespace Dragons
+
+#endif // DRAGONS_DETECTION_ENUMS_H
diff --git a/engines/gob/detection/detection.h b/engines/gob/detection/detection.h
index 0166116730..073b04a65e 100644
--- a/engines/gob/detection/detection.h
+++ b/engines/gob/detection/detection.h
@@ -20,6 +20,8 @@
  *
  */
 
+#ifndef GOB_DETECTION_H
+#define GOB_DETECTION_H
 
 namespace Gob {
 
@@ -34,3 +36,5 @@ struct GOBGameDescription {
 };
 
 } // End of namespace Gob
+
+#endif // GOB_DETECTION_H
diff --git a/engines/gob/detection/detection_enums.h b/engines/gob/detection/detection_enums.h
index 212258a693..d3cb3c55b6 100644
--- a/engines/gob/detection/detection_enums.h
+++ b/engines/gob/detection/detection_enums.h
@@ -20,8 +20,9 @@
  *
  */
 
+#ifndef GOB_DETECTION_ENUMS_H
+#define GOB_DETECTION_ENUMS_H
 
-// Taken from gob/gob.h
 namespace Gob {
 
 // WARNING: Reordering these will invalidate save games!
@@ -67,3 +68,5 @@ enum Features {
 };
 
 } // End of namespace Gob
+
+#endif // GOB_DETECTION_ENUMS_H
diff --git a/engines/hdb/detection/detection_enums.h b/engines/hdb/detection/detection_enums.h
index ebe2aeff5b..ad5ddf47d5 100644
--- a/engines/hdb/detection/detection_enums.h
+++ b/engines/hdb/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef HDB_DETECTION_H
+#define HDB_DETECTION_H
+
 namespace HDB {
 
 enum HDBGameFeatures {
@@ -27,3 +30,5 @@ enum HDBGameFeatures {
 };
 
 } // End of namespace HDB
+
+#endif // HDB_DETECTION_H
diff --git a/engines/hopkins/detection/detection.h b/engines/hopkins/detection/detection.h
index 678b570022..c9b84c92fb 100644
--- a/engines/hopkins/detection/detection.h
+++ b/engines/hopkins/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef HOPKINS_DETECTION_H
+#define HOPKINS_DETECTION_H
+
 namespace Hopkins {
 
 struct HopkinsGameDescription {
@@ -27,3 +30,5 @@ struct HopkinsGameDescription {
 };
 
 } // End of namespace Hopkins
+
+#endif // HOPKINS_DETECTION_H
diff --git a/engines/hugo/detection/detection.h b/engines/hugo/detection/detection.h
index d457ec5279..ef12c47312 100644
--- a/engines/hugo/detection/detection.h
+++ b/engines/hugo/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef HUGO_DETECTION_H
+#define HUGO_DETECTION_H
+
 namespace Hugo {
 
 struct HugoGameDescription {
@@ -28,3 +31,5 @@ struct HugoGameDescription {
 };
 
 } // End of namespace Hugo
+
+#endif // HUGO_DETECTION_H
diff --git a/engines/hugo/detection/detection_enums.h b/engines/hugo/detection/detection_enums.h
index f8ce67ca84..5e051f4388 100644
--- a/engines/hugo/detection/detection_enums.h
+++ b/engines/hugo/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef HUGO_DETECTION_ENUMS_H
+#define HUGO_DETECTION_ENUMS_H
+
 namespace Hugo {
 
 enum HugoGameFeatures {
@@ -44,3 +47,5 @@ enum GameVariant {
 };
 
 } // End of namespace Hugo
+
+#endif // HUGO_DETECTION_ENUMS_H
diff --git a/engines/illusions/detection/detection.h b/engines/illusions/detection/detection.h
index f1d1c30b54..7a3164298d 100644
--- a/engines/illusions/detection/detection.h
+++ b/engines/illusions/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef ILLUSIONS_DETECTION_H
+#define ILLUSIONS_DETECTION_H
+
 namespace Illusions {
 
 struct IllusionsGameDescription {
@@ -29,3 +32,4 @@ struct IllusionsGameDescription {
 
 } // End of namespace Illusions
 
+#endif // ILLUSIONS_DETECTION_H
diff --git a/engines/illusions/detection/detection_enums.h b/engines/illusions/detection/detection_enums.h
index c8691d7551..7a61817c4d 100644
--- a/engines/illusions/detection/detection_enums.h
+++ b/engines/illusions/detection/detection_enums.h
@@ -20,6 +20,8 @@
  *
  */
 
+#ifndef ILLUSIONS_DETECTION_ENUMS_H
+#define ILLUSIONS_DETECTION_ENUMS_H
 
 namespace Illusions {
 
@@ -29,3 +31,5 @@ enum {
 };
 
 } // End of namespace Illusions
+
+#endif // ILLUSIONS_DETECTION_ENUMS_H
diff --git a/engines/kyra/detection/detection.h b/engines/kyra/detection/detection.h
index fcc6e077f6..18a3b7b563 100644
--- a/engines/kyra/detection/detection.h
+++ b/engines/kyra/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef KYRA_DETECTION_H
+#define KYRA_DETECTION_H
+
 namespace {
 
 struct KYRAGameDescription {
@@ -29,3 +32,5 @@ struct KYRAGameDescription {
 };
 
 } // End of anonymous namespace
+
+#endif // KYRA_DETECTION_H
diff --git a/engines/kyra/detection/detection_enums.h b/engines/kyra/detection/detection_enums.h
index 6212099183..2f603aed84 100644
--- a/engines/kyra/detection/detection_enums.h
+++ b/engines/kyra/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef KYRA_DETECTION_ENUMS_H
+#define KYRA_DETECTION_ENUMS_H
+
 namespace Kyra {
 
 enum {
@@ -54,3 +57,5 @@ struct GameFlags {
 };
 
 } // End of namespace Kyra
+
+#endif // KYRA_DETECTION_ENUMS_H
diff --git a/engines/lab/detection/detection_enums.h b/engines/lab/detection/detection_enums.h
index f9c0b8830e..a6ce1cbeec 100644
--- a/engines/lab/detection/detection_enums.h
+++ b/engines/lab/detection/detection_enums.h
@@ -20,6 +20,8 @@
  *
  */
 
+#ifndef LAB_DETECTION_ENUMS_H
+#define LAB_DETECTION_ENUMS_H
 
 namespace Lab {
 
@@ -29,3 +31,5 @@ enum GameFeatures {
 };
 
 } // End of namespace Lab
+
+#endif // LAB_DETECTION_ENUMS_H
diff --git a/engines/lilliput/detection/detection.h b/engines/lilliput/detection/detection.h
index 74b2e956b3..c86f97a219 100644
--- a/engines/lilliput/detection/detection.h
+++ b/engines/lilliput/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef LILLIPUT_DETECTION_H
+#define LILLIPUT_DETECTION_H
+
 namespace Lilliput {
 
 struct LilliputGameDescription {
@@ -29,3 +32,4 @@ struct LilliputGameDescription {
 
 } // End of namespace Lilliput
 
+#endif // LILLIPUT_DETECTION_H
diff --git a/engines/lilliput/detection/detection_enums.h b/engines/lilliput/detection/detection_enums.h
index c040e09ddd..4de4ec857e 100644
--- a/engines/lilliput/detection/detection_enums.h
+++ b/engines/lilliput/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef LILLIPUT_DETECTION_ENUMS_H
+#define LILLIPUT_DETECTION_ENUMS_H
+
 namespace Lilliput {
 
 enum GameType {
@@ -29,3 +32,5 @@ enum GameType {
 };
 
 } // End of namespace Lilliput
+
+#endif // LILLIPUT_DETECTION_ENUMS_H
diff --git a/engines/lure/detection/detection.h b/engines/lure/detection/detection.h
index 75f7e4c973..e35f578a1c 100644
--- a/engines/lure/detection/detection.h
+++ b/engines/lure/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef LURE_DETECTION_H
+#define LURE_DETECTION_H
+
 namespace Lure {
 
 struct LureGameDescription {
@@ -29,3 +32,5 @@ struct LureGameDescription {
 };
 
 } // End of namespace Lure
+
+#endif // LURE_DETECTION_H
diff --git a/engines/lure/detection/detection_enums.h b/engines/lure/detection/detection_enums.h
index 90c3eba374..bfa8d641b8 100644
--- a/engines/lure/detection/detection_enums.h
+++ b/engines/lure/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef LURE_DETECTION_ENUMS_H
+#define LURE_DETECTION_ENUMS_H
+
 namespace Lure {
 
 enum {
@@ -29,3 +32,5 @@ enum {
 };
 
 } // End of namespace Lure
+
+#endif // LURE_DETECTION_ENUMS_H
diff --git a/engines/made/detection/detection.h b/engines/made/detection/detection.h
index d13abfbb44..39dfacaf05 100644
--- a/engines/made/detection/detection.h
+++ b/engines/made/detection/detection.h
@@ -20,6 +20,8 @@
  *
  */
 
+#ifndef MADE_DETECTION_H
+#define MADE_DETECTION_H
 
 namespace Made {
 
@@ -34,3 +36,4 @@ struct MadeGameDescription {
 
 } // End of namespace Made
 
+#endif // MADE_DETECTION_H
diff --git a/engines/made/detection/detection_enums.h b/engines/made/detection/detection_enums.h
index bb26d2c5b1..050efe08be 100644
--- a/engines/made/detection/detection_enums.h
+++ b/engines/made/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef MADE_DETECTION_ENUMS_H
+#define MADE_DETECTION_ENUMS_H
+
 namespace Made {
 
 enum MadeGameID {
@@ -37,3 +40,5 @@ enum MadeGameFeatures {
 };
 
 } // End of namespace Made
+
+#endif // MADE_DETECTION_ENUMS_H
diff --git a/engines/mads/detection/detection.h b/engines/mads/detection/detection.h
index 5e36dfb6f0..1dc2d5ef13 100644
--- a/engines/mads/detection/detection.h
+++ b/engines/mads/detection/detection.h
@@ -21,6 +21,8 @@
  *
  */
 
+#ifndef MADS_DETECTION_H
+#define MADS_DETECTION_H
 
 namespace MADS {
 
@@ -32,3 +34,5 @@ struct MADSGameDescription {
 };
 
 } // End of namespace MADS
+
+#endif // MADS_DETECTION_H
diff --git a/engines/mads/detection/detection_enums.h b/engines/mads/detection/detection_enums.h
index a0fd396cba..3e595e8f86 100644
--- a/engines/mads/detection/detection_enums.h
+++ b/engines/mads/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef MADS_DETECTION_ENUMS_H
+#define MADS_DETECTION_ENUMS_H
+
 namespace MADS {
 
 enum {
@@ -29,3 +32,5 @@ enum {
 };
 
 } // End of namespace MADS
+
+#endif // MADS_DETECTION_ENUMS_H
diff --git a/engines/mortevielle/detection/detection.h b/engines/mortevielle/detection/detection.h
index 0855afe14d..d86daca3bd 100644
--- a/engines/mortevielle/detection/detection.h
+++ b/engines/mortevielle/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef MORTEVIELLE_DETECTION_H
+#define MORTEVIELLE_DETECTION_H
+
 namespace Mortevielle {
 
 struct MortevielleGameDescription {
@@ -29,3 +32,5 @@ struct MortevielleGameDescription {
 };
 
 } // End of namespace Mortevielle
+
+#endif // MORTEVIELLE_DETECTION_H
diff --git a/engines/mortevielle/detection/detection_enums.h b/engines/mortevielle/detection/detection_enums.h
index a1c5bd8ba2..43f28e8bb7 100644
--- a/engines/mortevielle/detection/detection_enums.h
+++ b/engines/mortevielle/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef MORTEVIELLE_DETECTION_ENUMS_H
+#define MORTEVIELLE_DETECTION_ENUMS_H
+
 namespace Mortevielle {
 
 enum {
@@ -28,3 +31,5 @@ enum {
 };
 
 } // End of namespace Mortevielle
+
+#endif // MORTEVIELLE_DETECTION_ENUMS_H
diff --git a/engines/neverhood/detection/detection.h b/engines/neverhood/detection/detection.h
index 369050894f..143165b720 100644
--- a/engines/neverhood/detection/detection.h
+++ b/engines/neverhood/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef NEVERHOOD_DETECTION_H
+#define NEVERHOOD_DETECTION_H
+
 namespace Neverhood {
 
 struct NeverhoodGameDescription {
@@ -32,3 +35,5 @@ struct NeverhoodGameDescription {
 };
 
 } // End of namespace Neverhood
+
+#endif // NEVERHOOD_DETECTION_H
diff --git a/engines/parallaction/detection/detection.h b/engines/parallaction/detection/detection.h
index d6b7c29f71..99ba602969 100644
--- a/engines/parallaction/detection/detection.h
+++ b/engines/parallaction/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef PARALLACTION_DETECTION_H
+#define PARALLACTION_DETECTION_H
+
 namespace Parallaction {
 
 struct PARALLACTIONGameDescription {
@@ -30,3 +33,5 @@ struct PARALLACTIONGameDescription {
 };
 
 } // End of namespace Parallaction
+
+#endif // PARALLACTION_DETECTION_H
diff --git a/engines/pegasus/detection/detection.h b/engines/pegasus/detection/detection.h
index b8e20fc4d7..2ca5ec6c81 100644
--- a/engines/pegasus/detection/detection.h
+++ b/engines/pegasus/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef PEGASUS_DETECTION_H
+#define PEGASUS_DETECTION_H
+
 namespace Pegasus {
 
 struct PegasusGameDescription {
@@ -27,3 +30,5 @@ struct PegasusGameDescription {
 };
 
 } // End of namespace Pegasus
+
+#endif // PEGASUS_DETECTION_H
diff --git a/engines/prince/detection/detection.h b/engines/prince/detection/detection.h
index 33d076d5aa..5f7bcc897f 100644
--- a/engines/prince/detection/detection.h
+++ b/engines/prince/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef PRINCE_DETECTION_H
+#define PRINCE_DETECTION_H
+
 namespace Prince {
 
 struct PrinceGameDescription {
@@ -28,3 +31,5 @@ struct PrinceGameDescription {
 };
 
 } // End of namespace Prince
+
+#endif // PRINCE_DETECTION_H
diff --git a/engines/prince/detection/detection_enums.h b/engines/prince/detection/detection_enums.h
index 5596371901..b381ede907 100644
--- a/engines/prince/detection/detection_enums.h
+++ b/engines/prince/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef PRINCE_DETECTION_ENUMS_H
+#define PRINCE_DETECTION_ENUMS_H
+
 namespace Prince {
 
 enum PrinceGameType {
@@ -35,3 +38,5 @@ enum {
 };
 
 } // End of namespace Prince
+
+#endif // PRINCE_DETECTION_ENUMS_H
diff --git a/engines/queen/detection/detection.h b/engines/queen/detection/detection.h
index 40820312ee..663c6fb262 100644
--- a/engines/queen/detection/detection.h
+++ b/engines/queen/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef QUEEN_DETECTION_H
+#define QUEEN_DETECTION_H
+
 namespace Queen {
 
 struct QueenGameDescription {
@@ -27,3 +30,5 @@ struct QueenGameDescription {
 };
 
 } // End of namespace Queen
+
+#endif // QUEEN_DETECTION_H
diff --git a/engines/saga/detection/detection.h b/engines/saga/detection/detection.h
index 29034f70a4..b8a4700d71 100644
--- a/engines/saga/detection/detection.h
+++ b/engines/saga/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef SAGA_DETECTION_H
+#define SAGA_DETECTION_H
+
 namespace Saga {
 
 struct SAGAGameDescription {
@@ -35,3 +38,5 @@ struct SAGAGameDescription {
 };
 
 } // End of namespace Saga
+
+#endif // SAGA_DETECTION_H
diff --git a/engines/saga/detection/detection_enums.h b/engines/saga/detection/detection_enums.h
index fc1a50b668..25e8c7d589 100644
--- a/engines/saga/detection/detection_enums.h
+++ b/engines/saga/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef SAGA_DETECTION_ENUMS_H
+#define SAGA_DETECTION_ENUMS_H
+
 namespace Saga {
 
 struct GameResourceDescription {
@@ -88,3 +91,5 @@ enum GameFileTypes {
 };
 
 } // End of namespace Saga
+
+#endif // SAGA_DETECTION_ENUMS_H
diff --git a/engines/sherlock/detection/detection.h b/engines/sherlock/detection/detection.h
index d9ccc800c6..00ee8199dd 100644
--- a/engines/sherlock/detection/detection.h
+++ b/engines/sherlock/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef SHERLOCK_DETECTION_H
+#define SHERLOCK_DETECTION_H
+
 namespace Sherlock {
 
 struct SherlockGameDescription {
@@ -29,3 +32,5 @@ struct SherlockGameDescription {
 };
 
 } // End of namespace Sherlock
+
+#endif // SHERLOCK_DETECTION_H
diff --git a/engines/sherlock/detection/detection_enums.h b/engines/sherlock/detection/detection_enums.h
index bd33256d5e..9a4a04c156 100644
--- a/engines/sherlock/detection/detection_enums.h
+++ b/engines/sherlock/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef SHERLOCK_DETECTION_ENUMS_H
+#define SHERLOCK_DETECTION_ENUMS_H
+
 namespace Sherlock {
 
 enum GameType {
@@ -28,3 +31,5 @@ enum GameType {
 };
 
 } // End of namespace Sherlock
+
+#endif // SHERLOCK_DETECTION_ENUMS_H
diff --git a/engines/sludge/detection/detection.h b/engines/sludge/detection/detection.h
index be57defc5d..7b7a59d29b 100644
--- a/engines/sludge/detection/detection.h
+++ b/engines/sludge/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef SLUDGE_DETECTION_H
+#define SLUDGE_DETECTION_H
+
 namespace Sludge {
 
 struct SludgeGameDescription {
@@ -28,3 +31,5 @@ struct SludgeGameDescription {
 };
 
 } // End of namespace Sludge
+
+#endif // SLUDGE_DETECTION_H
diff --git a/engines/startrek/detection/detection.h b/engines/startrek/detection/detection.h
index d7db1a09b7..998860039b 100644
--- a/engines/startrek/detection/detection.h
+++ b/engines/startrek/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef STARTTREK_DETECTION_H
+#define STARTTREK_DETECTION_H
+
 namespace StarTrek {
 
 struct StarTrekGameDescription {
@@ -29,4 +32,6 @@ struct StarTrekGameDescription {
 	uint32 features;
 };
 
-} // End of Namespace StarTrek
\ No newline at end of file
+} // End of Namespace StarTrek
+
+#endif // STARTTREK_DETECTION_H
diff --git a/engines/startrek/detection/detection_enums.h b/engines/startrek/detection/detection_enums.h
index f58701a694..f1aa1f30c7 100644
--- a/engines/startrek/detection/detection_enums.h
+++ b/engines/startrek/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef STARTTREK_DETECTION_ENUMS_H
+#define STARTTREK_DETECTION_ENUMS_H
+
 namespace StarTrek {
 
 enum StarTrekGameType {
@@ -33,3 +36,5 @@ enum StarTrekGameFeatures {
 };
 
 } // End of namespace StarTrek
+
+#endif // STARTTREK_DETECTION_ENUMS_H
diff --git a/engines/sword25/detection/detection_enums.h b/engines/sword25/detection/detection_enums.h
index f1c51a4f6f..e4e21ffecd 100644
--- a/engines/sword25/detection/detection_enums.h
+++ b/engines/sword25/detection/detection_enums.h
@@ -20,6 +20,8 @@
  *
  */
 
+#ifndef SWORD25_DETECTION_ENUMS_H
+#define SWORD25_DETECTION_ENUMS_H
 
 namespace Sword25 {
 
@@ -28,3 +30,5 @@ enum GameFlags {
 };
 
 } // End of namespace Sword25
+
+#endif // SWORD25_DETECTION_ENUMS_H
diff --git a/engines/tinsel/detection/detection.h b/engines/tinsel/detection/detection.h
index 797b928296..50010c810a 100644
--- a/engines/tinsel/detection/detection.h
+++ b/engines/tinsel/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef TINSEL_DETECTION_H
+#define TINSEL_DETECTION_H
+
 namespace Tinsel {
 
 struct TinselGameDescription {
@@ -32,3 +35,5 @@ struct TinselGameDescription {
 };
 
 } // End of namespace Tinsel
+
+#endif // TINSEL_DETECTION_H
diff --git a/engines/tinsel/detection/detection_enums.h b/engines/tinsel/detection/detection_enums.h
index 9134ecb0e4..46f5ef0659 100644
--- a/engines/tinsel/detection/detection_enums.h
+++ b/engines/tinsel/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef TINSEL_DETECTION_ENUMS_H
+#define TINSEL_DETECTION_ENUMS_H
+
 namespace Tinsel {
 
 enum TinselGameID {
@@ -58,3 +61,5 @@ enum TinselEngineVersion {
 };
 
 } // End of namespace Tinsel
+
+#endif // TINSEL_DETECTION_ENUMS_H
diff --git a/engines/titanic/detection/detection.h b/engines/titanic/detection/detection.h
index 2febb57538..71fb9dd07b 100644
--- a/engines/titanic/detection/detection.h
+++ b/engines/titanic/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef TITANIC_DETECTION_H
+#define TITANIC_DETECTION_H
+
 namespace Titanic {
 
 struct TitanicGameDescription {
@@ -27,3 +30,5 @@ struct TitanicGameDescription {
 };
 
 } // End of namespace Titanic
+
+#endif // TITANIC_DETECTION_H
diff --git a/engines/toltecs/detection/detection.h b/engines/toltecs/detection/detection.h
index 982a997d4c..c41c4febe3 100644
--- a/engines/toltecs/detection/detection.h
+++ b/engines/toltecs/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef TOLTECS_DETECTION_H
+#define TOLTECS_DETECTION_H
+
 namespace Toltecs {
 
 struct ToltecsGameDescription {
@@ -27,3 +30,5 @@ struct ToltecsGameDescription {
 };
 
 } // End of namespace Toltecs
+
+#endif // TOLTECS_DETECTION_H
diff --git a/engines/tsage/detection/detection.h b/engines/tsage/detection/detection.h
index 07a6fe8020..ed0e9fb9db 100644
--- a/engines/tsage/detection/detection.h
+++ b/engines/tsage/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef TSAGE_DETECTION_H
+#define TSAGE_DETECTION_H
+
 namespace TsAGE {
 
 struct tSageGameDescription {
@@ -30,3 +33,5 @@ struct tSageGameDescription {
 };
 
 } // End of namespace TsAGE
+
+#endif // TSAGE_DETECTION_H
diff --git a/engines/tsage/detection/detection_enums.h b/engines/tsage/detection/detection_enums.h
index d7c7a76b47..fbd055dd6f 100644
--- a/engines/tsage/detection/detection_enums.h
+++ b/engines/tsage/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef TSAGE_DETECTION_ENUMS_H
+#define TSAGE_DETECTION_ENUMS_H
+
 namespace TsAGE {
 
 enum {
@@ -37,3 +40,5 @@ enum {
 };
 
 } // End of namespace TsAGE
+
+#endif // TSAGE_DETECTION_ENUMS_H
diff --git a/engines/tucker/detection/detection_enums.h b/engines/tucker/detection/detection_enums.h
index 0d59b4a191..7b39c546af 100644
--- a/engines/tucker/detection/detection_enums.h
+++ b/engines/tucker/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef TUCKER_DETECTION_ENUMS_H
+#define TUCKER_DETECTION_ENUMS_H
+
 namespace Tucker {
 
 enum GameFlag {
@@ -30,3 +33,5 @@ enum GameFlag {
 };
 
 } // End of namespace Tucker
+
+#endif // TUCKER_DETECTION_ENUMS_H
diff --git a/engines/voyeur/detection/detection.h b/engines/voyeur/detection/detection.h
index fb030d0aea..48f57b995a 100644
--- a/engines/voyeur/detection/detection.h
+++ b/engines/voyeur/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef VOYEUR_DETECTION_H
+#define VOYEUR_DETECTION_H
+
 namespace Voyeur {
 
 struct VoyeurGameDescription {
@@ -27,3 +30,5 @@ struct VoyeurGameDescription {
 };
 
 } // End of namespace Voyeur
+
+#endif // VOYEUR_DETECTION_H
diff --git a/engines/wintermute/detection/detection_enums.h b/engines/wintermute/detection/detection_enums.h
index 0781988426..3b3bf05e32 100644
--- a/engines/wintermute/detection/detection_enums.h
+++ b/engines/wintermute/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef WINTERMUTE_DETECTION_ENUMS_H
+#define WINTERMUTE_DETECTION_ENUMS_H
+
 namespace Wintermute {
 
 enum WintermuteGameFeatures {
@@ -31,3 +34,5 @@ enum WintermuteGameFeatures {
 };
 
 } // End of namespace Wintermute
+
+#endif // WINTERMUTE_DETECTION_ENUMS_H
diff --git a/engines/xeen/detection/detection.h b/engines/xeen/detection/detection.h
index 0c7a014966..bb9f06cffd 100644
--- a/engines/xeen/detection/detection.h
+++ b/engines/xeen/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef XEEN_DETECTION_H
+#define XEEN_DETECTION_H
+
 namespace Xeen {
 
 struct XeenGameDescription {
@@ -30,3 +33,5 @@ struct XeenGameDescription {
 };
 
 } // End of namespace Xeen
+
+#endif // XEEN_DETECTION_H
diff --git a/engines/xeen/detection/detection_enums.h b/engines/xeen/detection/detection_enums.h
index 90076adaa6..f173db1713 100644
--- a/engines/xeen/detection/detection_enums.h
+++ b/engines/xeen/detection/detection_enums.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef XEEN_DETECTION_ENUMS_H
+#define XEEN_DETECTION_ENUMS_H
+
 namespace Xeen {
 
 enum {
@@ -30,3 +33,5 @@ enum {
 };
 
 } // End of namespace Xeen
+
+#endif // XEEN_DETECTION_ENUMS_H
diff --git a/engines/zvision/detection/detection.h b/engines/zvision/detection/detection.h
index 1b32a5c024..c47243a912 100644
--- a/engines/zvision/detection/detection.h
+++ b/engines/zvision/detection/detection.h
@@ -20,6 +20,9 @@
  *
  */
 
+#ifndef ZVISION_DETECTION_H
+#define ZVISION_DETECTION_H
+
 namespace ZVision {
 
 struct ZVisionGameDescription {
@@ -28,3 +31,5 @@ struct ZVisionGameDescription {
 };
 
 } // End of namespace ZVision
+
+#endif // ZVISION_DETECTION_H
diff --git a/engines/zvision/detection/detection_enums.h b/engines/zvision/detection/detection_enums.h
index 79a0fc2986..47553aa340 100644
--- a/engines/zvision/detection/detection_enums.h
+++ b/engines/zvision/detection/detection_enums.h
@@ -21,6 +21,9 @@
  *
  */
 
+#ifndef ZVISION_DETECTION_ENUMS_H
+#define ZVISION_DETECTION_ENUMS_H
+
 namespace ZVision {
 
 enum ZVisionGameId {
@@ -34,3 +37,5 @@ enum ZVisionFeatures {
 };
 
 } // End of namespace ZVision
+
+#endif // ZVISION_DETECTION_ENUMS_H


Commit: 274b8a51a179dd20b02d1d6b13a15586881bdfa6
    https://github.com/scummvm/scummvm/commit/274b8a51a179dd20b02d1d6b13a15586881bdfa6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
TONY: Match consistency with other engines & move enums to new header.

Changed paths:
  A engines/tony/detection/detection_enums.h
    engines/tony/detection/detection.cpp
    engines/tony/detection/detection.h
    engines/tony/metaengine.cpp


diff --git a/engines/tony/detection/detection.cpp b/engines/tony/detection/detection.cpp
index 725b55a2e8..594f873402 100644
--- a/engines/tony/detection/detection.cpp
+++ b/engines/tony/detection/detection.cpp
@@ -25,6 +25,7 @@
 #include "engines/advancedDetector.h"
 
 #include "tony/detection/detection.h"
+#include "tony/detection/detection_enums.h"
 
 static const PlainGameDescriptor tonyGames[] = {
 	{"tony", "Tony Tough and the Night of Roasted Moths"},
diff --git a/engines/tony/detection/detection.h b/engines/tony/detection/detection.h
index 561bb22590..608c921201 100644
--- a/engines/tony/detection/detection.h
+++ b/engines/tony/detection/detection.h
@@ -20,14 +20,15 @@
  *
  */
 
-namespace Tony {
+#ifndef TONY_DETECTION_H
+#define TONY_DETECTION_H
 
-enum {
-	GF_COMPRESSED = (1 << 0)
-};
+namespace Tony {
 
 struct TonyGameDescription {
 	ADGameDescription desc;
 };
 
 } // End of namespace Tony
+
+#endif // TONY_DETECTION_H
diff --git a/engines/tony/detection/detection_enums.h b/engines/tony/detection/detection_enums.h
new file mode 100644
index 0000000000..c04308b4ca
--- /dev/null
+++ b/engines/tony/detection/detection_enums.h
@@ -0,0 +1,34 @@
+/* ScummVM - Graphic Adventure Engine
+ *
+ * ScummVM is the legal property of its developers, whose names
+ * are too numerous to list here. Please refer to the COPYRIGHT
+ * file distributed with this source distribution.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ */
+
+#ifndef TONY_DETECTION_ENUMS_H
+#define TONY_DETECTION_ENUMS_H
+
+namespace Tony {
+
+enum {
+	GF_COMPRESSED = (1 << 0)
+};
+
+} // End of namespace Tony
+
+#endif // TONY_DETECTION_ENUMS_H
diff --git a/engines/tony/metaengine.cpp b/engines/tony/metaengine.cpp
index 0ca928cb82..3beea77996 100644
--- a/engines/tony/metaengine.cpp
+++ b/engines/tony/metaengine.cpp
@@ -30,6 +30,7 @@
 #include "tony/tony.h"
 #include "tony/game.h"
 #include "tony/detection/detection.h"
+#include "tony/detection/detection_enums.h"
 
 namespace Tony {
 


Commit: 29ceb079595fa4bff586c53b4cf49119f5e6ecf4
    https://github.com/scummvm/scummvm/commit/29ceb079595fa4bff586c53b4cf49119f5e6ecf4
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: ALL: Revert detection submodule to be directly present in the engine directory

- DETECT_OBJS are present and added inside an engine's modules.mk file.

Changed paths:
  A engines/access/detection.cpp
  A engines/access/detection.h
  A engines/access/detection_enums.h
  A engines/access/detection_tables.h
  A engines/adl/detection.cpp
  A engines/adl/detection.h
  A engines/adl/detection_enums.h
  A engines/agi/detection.cpp
  A engines/agi/detection.h
  A engines/agi/detection_tables.h
  A engines/agi/wagparser.cpp
  A engines/agi/wagparser.h
  A engines/agos/detection.cpp
  A engines/agos/detection.h
  A engines/agos/detection_enums.h
  A engines/agos/detection_tables.h
  A engines/avalanche/detection.cpp
  A engines/avalanche/detection.h
  A engines/bbvs/detection.cpp
  A engines/bbvs/detection_enums.h
  A engines/bladerunner/detection.cpp
  A engines/bladerunner/detection_tables.h
  A engines/cge/detection.cpp
  A engines/cge2/detection.cpp
  A engines/chewy/detection.cpp
  A engines/chewy/detection.h
  A engines/cine/detection.cpp
  A engines/cine/detection.h
  A engines/cine/detection_enums.h
  A engines/cine/detection_tables.h
  A engines/composer/detection.cpp
  A engines/composer/detection.h
  A engines/composer/detection_enums.h
  A engines/composer/detection_tables.h
  A engines/cruise/detection.cpp
  A engines/cruise/detection.h
  A engines/cryo/detection.cpp
  A engines/cryomni3d/detection.cpp
  A engines/cryomni3d/detection.h
  A engines/cryomni3d/detection_enums.h
  A engines/cryomni3d/detection_tables.h
  A engines/director/detection.cpp
  A engines/director/detection.h
  A engines/director/detection_enums.h
  A engines/director/detection_tables.h
  A engines/dm/detection.cpp
  A engines/dm/detection.h
  A engines/dm/detection_enums.h
  A engines/draci/detection.cpp
  A engines/dragons/detection.cpp
  A engines/dragons/detection.h
  A engines/dragons/detection_enums.h
  A engines/drascula/detection.cpp
  A engines/drascula/detection.h
  A engines/drascula/detection_enums.h
  A engines/dreamweb/detection.cpp
  A engines/dreamweb/detection.h
  A engines/dreamweb/detection_tables.h
  A engines/fullpipe/detection.cpp
  A engines/glk/detection.cpp
  A engines/gnap/detection.cpp
  A engines/griffon/detection.cpp
  A engines/groovie/detection.cpp
  A engines/groovie/detection.h
  A engines/groovie/detection_enums.h
  A engines/hdb/detection.cpp
  A engines/hdb/detection_enums.h
  A engines/hopkins/detection.cpp
  A engines/hopkins/detection.h
  A engines/hopkins/detection_tables.h
  A engines/hugo/detection.cpp
  A engines/hugo/detection.h
  A engines/hugo/detection_enums.h
  A engines/illusions/detection.cpp
  A engines/illusions/detection.h
  A engines/illusions/detection_enums.h
  A engines/kingdom/detection.cpp
  A engines/kyra/detection.cpp
  A engines/kyra/detection.h
  A engines/kyra/detection_enums.h
  A engines/kyra/detection_tables.h
  A engines/lab/detection.cpp
  A engines/lab/detection_enums.h
  A engines/lastexpress/detection.cpp
  A engines/lilliput/detection.cpp
  A engines/lilliput/detection.h
  A engines/lilliput/detection_enums.h
  A engines/lure/detection.cpp
  A engines/lure/detection.h
  A engines/lure/detection_enums.h
  A engines/macventure/detection.cpp
  A engines/made/detection.cpp
  A engines/made/detection.h
  A engines/made/detection_enums.h
  A engines/made/detection_tables.h
  A engines/mads/detection.cpp
  A engines/mads/detection.h
  A engines/mads/detection_enums.h
  A engines/mads/detection_tables.h
  A engines/mohawk/detection.cpp
  A engines/mohawk/detection.h
  A engines/mohawk/detection_enums.h
  A engines/mohawk/detection_tables.h
  A engines/mortevielle/detection.cpp
  A engines/mortevielle/detection.h
  A engines/mortevielle/detection_enums.h
  A engines/mortevielle/detection_tables.h
  A engines/mutationofjb/detection.cpp
  A engines/neverhood/detection.cpp
  A engines/neverhood/detection.h
  A engines/parallaction/detection.cpp
  A engines/parallaction/detection.h
  A engines/parallaction/detection_enums.h
  A engines/pegasus/detection.cpp
  A engines/pegasus/detection.h
  A engines/pegasus/detection_enums.h
  A engines/petka/detection.cpp
  A engines/petka/detection_tables.h
  A engines/pink/detection.cpp
  A engines/pink/detection_tables.h
  A engines/plumbers/detection.cpp
  A engines/prince/detection.cpp
  A engines/prince/detection.h
  A engines/prince/detection_enums.h
  A engines/queen/detection.cpp
  A engines/queen/detection.h
  A engines/saga/detection.cpp
  A engines/saga/detection.h
  A engines/saga/detection_enums.h
  A engines/saga/detection_tables.h
  A engines/sci/detection.cpp
  A engines/sci/detection_defines.h
  A engines/sci/detection_enums.h
  A engines/sci/detection_tables.h
  A engines/scumm/detection.cpp
  A engines/scumm/detection.h
  A engines/scumm/detection_internal.h
  A engines/scumm/detection_steam.h
  A engines/scumm/detection_tables.h
  A engines/sherlock/detection.cpp
  A engines/sherlock/detection.h
  A engines/sherlock/detection_enums.h
  A engines/sherlock/detection_tables.h
  A engines/sky/detection.cpp
  A engines/sludge/detection.cpp
  A engines/sludge/detection.h
  A engines/sludge/detection_tables.h
  A engines/startrek/detection.cpp
  A engines/startrek/detection.h
  A engines/startrek/detection_enums.h
  A engines/supernova/detection.cpp
  A engines/sword1/detection.cpp
  A engines/sword2/detection.cpp
  A engines/sword2/detection_enums.h
  A engines/sword2/detection_internal.h
  A engines/sword25/detection.cpp
  A engines/sword25/detection_enums.h
  A engines/sword25/detection_tables.h
  A engines/teenagent/detection.cpp
  A engines/testbed/detection.cpp
  A engines/tinsel/detection.cpp
  A engines/tinsel/detection.h
  A engines/tinsel/detection_enums.h
  A engines/tinsel/detection_tables.h
  A engines/titanic/detection.cpp
  A engines/titanic/detection.h
  A engines/titanic/detection_tables.h
  A engines/toltecs/detection.cpp
  A engines/toltecs/detection.h
  A engines/tony/detection.cpp
  A engines/tony/detection.h
  A engines/tony/detection_enums.h
  A engines/tony/detection_tables.h
  A engines/toon/detection.cpp
  A engines/touche/detection.cpp
  A engines/tsage/detection.cpp
  A engines/tsage/detection.h
  A engines/tsage/detection_enums.h
  A engines/tsage/detection_tables.h
  A engines/tucker/detection.cpp
  A engines/tucker/detection_enums.h
  A engines/ultima/detection.cpp
  A engines/ultima/detection_tables.h
  A engines/voyeur/detection.cpp
  A engines/voyeur/detection.h
  A engines/voyeur/detection_tables.h
  A engines/wage/detection.cpp
  A engines/wage/detection_tables.h
  A engines/wintermute/detection.cpp
  A engines/wintermute/detection.h
  A engines/wintermute/detection_enums.h
  A engines/wintermute/detection_tables.h
  A engines/xeen/detection.cpp
  A engines/xeen/detection.h
  A engines/xeen/detection_enums.h
  A engines/xeen/detection_tables.h
  A engines/zvision/detection.cpp
  A engines/zvision/detection.h
  A engines/zvision/detection_enums.h
  A engines/zvision/detection_tables.h
  R engines/access/detection/detection.cpp
  R engines/access/detection/detection.h
  R engines/access/detection/detection_enums.h
  R engines/access/detection/detection_tables.h
  R engines/access/detection/module.mk
  R engines/adl/detection/detection.cpp
  R engines/adl/detection/detection.h
  R engines/adl/detection/detection_enums.h
  R engines/adl/detection/module.mk
  R engines/agi/detection/detection.cpp
  R engines/agi/detection/detection.h
  R engines/agi/detection/detection_tables.h
  R engines/agi/detection/module.mk
  R engines/agi/detection/wagparser.cpp
  R engines/agi/detection/wagparser.h
  R engines/agos/detection/detection.cpp
  R engines/agos/detection/detection.h
  R engines/agos/detection/detection_enums.h
  R engines/agos/detection/detection_tables.h
  R engines/agos/detection/module.mk
  R engines/avalanche/detection/detection.cpp
  R engines/avalanche/detection/detection.h
  R engines/avalanche/detection/module.mk
  R engines/bbvs/detection/detection.cpp
  R engines/bbvs/detection/detection_enums.h
  R engines/bbvs/detection/module.mk
  R engines/bladerunner/detection/detection.cpp
  R engines/bladerunner/detection/detection_tables.h
  R engines/bladerunner/detection/module.mk
  R engines/cge/detection/detection.cpp
  R engines/cge/detection/module.mk
  R engines/cge2/detection/detection.cpp
  R engines/cge2/detection/module.mk
  R engines/chewy/detection/detection.cpp
  R engines/chewy/detection/detection.h
  R engines/chewy/detection/module.mk
  R engines/cine/detection/detection.cpp
  R engines/cine/detection/detection.h
  R engines/cine/detection/detection_enums.h
  R engines/cine/detection/detection_tables.h
  R engines/cine/detection/module.mk
  R engines/composer/detection/detection.cpp
  R engines/composer/detection/detection.h
  R engines/composer/detection/detection_enums.h
  R engines/composer/detection/detection_tables.h
  R engines/composer/detection/module.mk
  R engines/cruise/detection/detection.cpp
  R engines/cruise/detection/detection.h
  R engines/cruise/detection/module.mk
  R engines/cryo/detection/detection.cpp
  R engines/cryo/detection/module.mk
  R engines/cryomni3d/detection/detection.cpp
  R engines/cryomni3d/detection/detection.h
  R engines/cryomni3d/detection/detection_enums.h
  R engines/cryomni3d/detection/detection_tables.h
  R engines/cryomni3d/detection/module.mk
  R engines/director/detection/detection.cpp
  R engines/director/detection/detection.h
  R engines/director/detection/detection_enums.h
  R engines/director/detection/detection_tables.h
  R engines/director/detection/module.mk
  R engines/dm/detection/detection.cpp
  R engines/dm/detection/detection.h
  R engines/dm/detection/detection_enums.h
  R engines/dm/detection/module.mk
  R engines/draci/detection/detection.cpp
  R engines/draci/detection/module.mk
  R engines/dragons/detection/detection.cpp
  R engines/dragons/detection/detection.h
  R engines/dragons/detection/detection_enums.h
  R engines/dragons/detection/module.mk
  R engines/drascula/detection/detection.cpp
  R engines/drascula/detection/detection.h
  R engines/drascula/detection/detection_enums.h
  R engines/drascula/detection/module.mk
  R engines/dreamweb/detection/detection.cpp
  R engines/dreamweb/detection/detection.h
  R engines/dreamweb/detection/detection_tables.h
  R engines/dreamweb/detection/module.mk
  R engines/fullpipe/detection/detection.cpp
  R engines/fullpipe/detection/module.mk
  R engines/glk/detection/detection.cpp
  R engines/glk/detection/module.mk
  R engines/gnap/detection/detection.cpp
  R engines/gnap/detection/module.mk
  R engines/gob/detection/module.mk
  R engines/griffon/detection/detection.cpp
  R engines/griffon/detection/module.mk
  R engines/groovie/detection/detection.cpp
  R engines/groovie/detection/detection.h
  R engines/groovie/detection/detection_enums.h
  R engines/groovie/detection/module.mk
  R engines/hdb/detection/detection.cpp
  R engines/hdb/detection/detection_enums.h
  R engines/hdb/detection/module.mk
  R engines/hopkins/detection/detection.cpp
  R engines/hopkins/detection/detection.h
  R engines/hopkins/detection/detection_tables.h
  R engines/hopkins/detection/module.mk
  R engines/hugo/detection/detection.cpp
  R engines/hugo/detection/detection.h
  R engines/hugo/detection/detection_enums.h
  R engines/hugo/detection/module.mk
  R engines/illusions/detection/detection.cpp
  R engines/illusions/detection/detection.h
  R engines/illusions/detection/detection_enums.h
  R engines/illusions/detection/module.mk
  R engines/kingdom/detection/detection.cpp
  R engines/kingdom/detection/module.mk
  R engines/kyra/detection/detection.cpp
  R engines/kyra/detection/detection.h
  R engines/kyra/detection/detection_enums.h
  R engines/kyra/detection/detection_tables.h
  R engines/kyra/detection/module.mk
  R engines/lab/detection/detection.cpp
  R engines/lab/detection/detection_enums.h
  R engines/lab/detection/module.mk
  R engines/lastexpress/detection/detection.cpp
  R engines/lastexpress/detection/module.mk
  R engines/lilliput/detection/detection.cpp
  R engines/lilliput/detection/detection.h
  R engines/lilliput/detection/detection_enums.h
  R engines/lilliput/detection/module.mk
  R engines/lure/detection/detection.cpp
  R engines/lure/detection/detection.h
  R engines/lure/detection/detection_enums.h
  R engines/lure/detection/module.mk
  R engines/macventure/detection/detection.cpp
  R engines/macventure/detection/module.mk
  R engines/made/detection/detection.cpp
  R engines/made/detection/detection.h
  R engines/made/detection/detection_enums.h
  R engines/made/detection/detection_tables.h
  R engines/made/detection/module.mk
  R engines/mads/detection/detection.cpp
  R engines/mads/detection/detection.h
  R engines/mads/detection/detection_enums.h
  R engines/mads/detection/detection_tables.h
  R engines/mads/detection/module.mk
  R engines/mohawk/detection/detection.cpp
  R engines/mohawk/detection/detection.h
  R engines/mohawk/detection/detection_enums.h
  R engines/mohawk/detection/detection_tables.h
  R engines/mohawk/detection/module.mk
  R engines/mortevielle/detection/detection.cpp
  R engines/mortevielle/detection/detection.h
  R engines/mortevielle/detection/detection_enums.h
  R engines/mortevielle/detection/detection_tables.h
  R engines/mortevielle/detection/module.mk
  R engines/mutationofjb/detection/detection.cpp
  R engines/mutationofjb/detection/module.mk
  R engines/neverhood/detection/detection.cpp
  R engines/neverhood/detection/detection.h
  R engines/neverhood/detection/module.mk
  R engines/parallaction/detection/detection.cpp
  R engines/parallaction/detection/detection.h
  R engines/parallaction/detection/detection_enums.h
  R engines/parallaction/detection/module.mk
  R engines/pegasus/detection/detection.cpp
  R engines/pegasus/detection/detection.h
  R engines/pegasus/detection/detection_enums.h
  R engines/pegasus/detection/module.mk
  R engines/petka/detection/detection.cpp
  R engines/petka/detection/detection_tables.h
  R engines/petka/detection/module.mk
  R engines/pink/detection/detection.cpp
  R engines/pink/detection/detection_tables.h
  R engines/pink/detection/module.mk
  R engines/plumbers/detection/detection.cpp
  R engines/plumbers/detection/module.mk
  R engines/prince/detection/detection.cpp
  R engines/prince/detection/detection.h
  R engines/prince/detection/detection_enums.h
  R engines/prince/detection/module.mk
  R engines/queen/detection/detection.cpp
  R engines/queen/detection/detection.h
  R engines/queen/detection/module.mk
  R engines/saga/detection/detection.cpp
  R engines/saga/detection/detection.h
  R engines/saga/detection/detection_enums.h
  R engines/saga/detection/detection_tables.h
  R engines/saga/detection/module.mk
  R engines/sci/detection/detection.cpp
  R engines/sci/detection/detection_defines.h
  R engines/sci/detection/detection_enums.h
  R engines/sci/detection/detection_tables.h
  R engines/sci/detection/module.mk
  R engines/scumm/detection/detection.cpp
  R engines/scumm/detection/detection.h
  R engines/scumm/detection/detection_internal.h
  R engines/scumm/detection/detection_steam.h
  R engines/scumm/detection/detection_tables.h
  R engines/scumm/detection/module.mk
  R engines/sherlock/detection/detection.cpp
  R engines/sherlock/detection/detection.h
  R engines/sherlock/detection/detection_enums.h
  R engines/sherlock/detection/detection_tables.h
  R engines/sherlock/detection/module.mk
  R engines/sky/detection/detection.cpp
  R engines/sky/detection/module.mk
  R engines/sludge/detection/detection.cpp
  R engines/sludge/detection/detection.h
  R engines/sludge/detection/detection_tables.h
  R engines/sludge/detection/module.mk
  R engines/startrek/detection/detection.cpp
  R engines/startrek/detection/detection.h
  R engines/startrek/detection/detection_enums.h
  R engines/startrek/detection/module.mk
  R engines/supernova/detection/detection.cpp
  R engines/supernova/detection/module.mk
  R engines/sword1/detection/detection.cpp
  R engines/sword1/detection/module.mk
  R engines/sword2/detection/detection.cpp
  R engines/sword2/detection/detection_enums.h
  R engines/sword2/detection/detection_internal.h
  R engines/sword2/detection/module.mk
  R engines/sword25/detection/detection.cpp
  R engines/sword25/detection/detection_enums.h
  R engines/sword25/detection/detection_tables.h
  R engines/sword25/detection/module.mk
  R engines/teenagent/detection/detection.cpp
  R engines/teenagent/detection/module.mk
  R engines/testbed/detection/detection.cpp
  R engines/testbed/detection/module.mk
  R engines/tinsel/detection/detection.cpp
  R engines/tinsel/detection/detection.h
  R engines/tinsel/detection/detection_enums.h
  R engines/tinsel/detection/detection_tables.h
  R engines/tinsel/detection/module.mk
  R engines/titanic/detection/detection.cpp
  R engines/titanic/detection/detection.h
  R engines/titanic/detection/detection_tables.h
  R engines/titanic/detection/module.mk
  R engines/toltecs/detection/detection.cpp
  R engines/toltecs/detection/detection.h
  R engines/toltecs/detection/module.mk
  R engines/tony/detection/detection.cpp
  R engines/tony/detection/detection.h
  R engines/tony/detection/detection_enums.h
  R engines/tony/detection/detection_tables.h
  R engines/tony/detection/module.mk
  R engines/toon/detection/detection.cpp
  R engines/toon/detection/module.mk
  R engines/touche/detection/detection.cpp
  R engines/touche/detection/module.mk
  R engines/tsage/detection/detection.cpp
  R engines/tsage/detection/detection.h
  R engines/tsage/detection/detection_enums.h
  R engines/tsage/detection/detection_tables.h
  R engines/tsage/detection/module.mk
  R engines/tucker/detection/detection.cpp
  R engines/tucker/detection/detection_enums.h
  R engines/tucker/detection/module.mk
  R engines/ultima/detection/detection.cpp
  R engines/ultima/detection/detection_tables.h
  R engines/ultima/detection/module.mk
  R engines/voyeur/detection/detection.cpp
  R engines/voyeur/detection/detection.h
  R engines/voyeur/detection/detection_tables.h
  R engines/voyeur/detection/module.mk
  R engines/wage/detection/detection.cpp
  R engines/wage/detection/detection_tables.h
  R engines/wage/detection/module.mk
  R engines/wintermute/detection/detection.cpp
  R engines/wintermute/detection/detection.h
  R engines/wintermute/detection/detection_enums.h
  R engines/wintermute/detection/detection_tables.h
  R engines/wintermute/detection/module.mk
  R engines/xeen/detection/detection.cpp
  R engines/xeen/detection/detection.h
  R engines/xeen/detection/detection_enums.h
  R engines/xeen/detection/detection_tables.h
  R engines/xeen/detection/module.mk
  R engines/zvision/detection/detection.cpp
  R engines/zvision/detection/detection.h
  R engines/zvision/detection/detection_enums.h
  R engines/zvision/detection/detection_tables.h
  R engines/zvision/detection/module.mk
    engines/access/access.h
    engines/access/metaengine.cpp
    engines/access/module.mk
    engines/adl/adl.h
    engines/adl/adl_v2.cpp
    engines/adl/hires4.cpp
    engines/adl/hires5.cpp
    engines/adl/metaengine.cpp
    engines/adl/module.mk
    engines/agi/metaengine.cpp
    engines/agi/module.mk
    engines/agos/agos.h
    engines/agos/metaengine.cpp
    engines/agos/module.mk
    engines/avalanche/metaengine.cpp
    engines/avalanche/module.mk
    engines/bbvs/bbvs.h
    engines/bbvs/module.mk
    engines/bladerunner/module.mk
    engines/cge/module.mk
    engines/cge2/module.mk
    engines/chewy/metaengine.cpp
    engines/chewy/module.mk
    engines/cine/cine.h
    engines/cine/metaengine.cpp
    engines/cine/module.mk
    engines/composer/composer.h
    engines/composer/metaengine.cpp
    engines/composer/module.mk
    engines/cruise/metaengine.cpp
    engines/cruise/module.mk
    engines/cryo/module.mk
    engines/cryomni3d/cryomni3d.h
    engines/cryomni3d/metaengine.cpp
    engines/cryomni3d/module.mk
    engines/director/director.h
    engines/director/metaengine.cpp
    engines/director/module.mk
    engines/dm/dm.h
    engines/dm/module.mk
    engines/draci/module.mk
    engines/dragons/dragons.h
    engines/dragons/module.mk
    engines/drascula/drascula.h
    engines/drascula/metaengine.cpp
    engines/drascula/module.mk
    engines/dreamweb/metaengine.cpp
    engines/dreamweb/module.mk
    engines/fullpipe/module.mk
    engines/glk/module.mk
    engines/gnap/module.mk
    engines/gob/module.mk
    engines/griffon/module.mk
    engines/groovie/groovie.cpp
    engines/groovie/groovie.h
    engines/groovie/metaengine.cpp
    engines/groovie/module.mk
    engines/groovie/script.h
    engines/hdb/metaengine.cpp
    engines/hdb/module.mk
    engines/hopkins/metaengine.cpp
    engines/hopkins/module.mk
    engines/hugo/hugo.h
    engines/hugo/metaengine.cpp
    engines/hugo/module.mk
    engines/illusions/illusions.h
    engines/illusions/metaengine.cpp
    engines/illusions/module.mk
    engines/kingdom/module.mk
    engines/kyra/kyra_v1.h
    engines/kyra/metaengine.cpp
    engines/kyra/module.mk
    engines/lab/lab.h
    engines/lab/module.mk
    engines/lastexpress/module.mk
    engines/lilliput/lilliput.h
    engines/lilliput/metaengine.cpp
    engines/lilliput/module.mk
    engines/lure/lure.h
    engines/lure/metaengine.cpp
    engines/lure/module.mk
    engines/macventure/module.mk
    engines/made/made.h
    engines/made/metaengine.cpp
    engines/made/module.mk
    engines/mads/mads.h
    engines/mads/metaengine.cpp
    engines/mads/module.mk
    engines/mohawk/metaengine.cpp
    engines/mohawk/module.mk
    engines/mohawk/mohawk.h
    engines/mortevielle/metaengine.cpp
    engines/mortevielle/module.mk
    engines/mortevielle/mortevielle.h
    engines/mutationofjb/module.mk
    engines/neverhood/metaengine.cpp
    engines/neverhood/module.mk
    engines/parallaction/metaengine.cpp
    engines/parallaction/module.mk
    engines/parallaction/parallaction.h
    engines/pegasus/metaengine.cpp
    engines/pegasus/module.mk
    engines/petka/module.mk
    engines/pink/module.mk
    engines/plumbers/module.mk
    engines/prince/metaengine.cpp
    engines/prince/module.mk
    engines/prince/prince.h
    engines/queen/metaengine.cpp
    engines/queen/module.mk
    engines/saga/metaengine.cpp
    engines/saga/module.mk
    engines/saga/saga.h
    engines/sci/module.mk
    engines/sci/sci.h
    engines/scumm/file.h
    engines/scumm/metaengine.cpp
    engines/scumm/module.mk
    engines/scumm/scumm.cpp
    engines/scumm/scumm.h
    engines/sherlock/metaengine.cpp
    engines/sherlock/module.mk
    engines/sherlock/sherlock.h
    engines/sky/module.mk
    engines/sludge/metaengine.cpp
    engines/sludge/module.mk
    engines/startrek/metaengine.cpp
    engines/startrek/module.mk
    engines/startrek/startrek.h
    engines/supernova/module.mk
    engines/sword1/module.mk
    engines/sword2/metaengine.cpp
    engines/sword2/module.mk
    engines/sword2/sword2.h
    engines/sword25/module.mk
    engines/sword25/sword25.h
    engines/teenagent/module.mk
    engines/testbed/module.mk
    engines/tinsel/metaengine.cpp
    engines/tinsel/module.mk
    engines/tinsel/tinsel.h
    engines/titanic/metaengine.cpp
    engines/titanic/module.mk
    engines/toltecs/metaengine.cpp
    engines/toltecs/module.mk
    engines/tony/metaengine.cpp
    engines/tony/module.mk
    engines/toon/module.mk
    engines/touche/module.mk
    engines/tsage/metaengine.cpp
    engines/tsage/module.mk
    engines/tsage/tsage.h
    engines/tucker/module.mk
    engines/tucker/tucker.h
    engines/ultima/module.mk
    engines/voyeur/metaengine.cpp
    engines/voyeur/module.mk
    engines/wage/module.mk
    engines/wintermute/base/base_sprite.cpp
    engines/wintermute/metaengine.cpp
    engines/wintermute/module.mk
    engines/wintermute/wintermute.cpp
    engines/wintermute/wintermute.h
    engines/xeen/metaengine.cpp
    engines/xeen/module.mk
    engines/xeen/xeen.h
    engines/zvision/metaengine.cpp
    engines/zvision/module.mk
    engines/zvision/zvision.h


diff --git a/engines/access/access.h b/engines/access/access.h
index 43d5af19b2..26cf6f4f4d 100644
--- a/engines/access/access.h
+++ b/engines/access/access.h
@@ -50,7 +50,7 @@
 #include "access/scripts.h"
 #include "access/sound.h"
 #include "access/video.h"
-#include "access/detection/detection_enums.h"
+#include "access/detection_enums.h"
 
 /**
  * This is the namespace of the Access engine.
diff --git a/engines/access/detection/detection.cpp b/engines/access/detection.cpp
similarity index 92%
rename from engines/access/detection/detection.cpp
rename to engines/access/detection.cpp
index 9b596223c4..e76bc9f163 100644
--- a/engines/access/detection/detection.cpp
+++ b/engines/access/detection.cpp
@@ -22,8 +22,8 @@
 
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
-#include "access/detection/detection.h"
-#include "access/detection/detection_enums.h"
+#include "access/detection.h"
+#include "access/detection_enums.h"
 
 static const PlainGameDescriptor AccessGames[] = {
 	{"amazon", "Amazon: Guardians of Eden"},
@@ -31,7 +31,7 @@ static const PlainGameDescriptor AccessGames[] = {
 	{0, 0}
 };
 
-#include "access/detection/detection_tables.h"
+#include "access/detection_tables.h"
 
 class AccessMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/access/detection/detection.h b/engines/access/detection.h
similarity index 100%
rename from engines/access/detection/detection.h
rename to engines/access/detection.h
diff --git a/engines/access/detection/module.mk b/engines/access/detection/module.mk
deleted file mode 100644
index e9ed99f685..0000000000
--- a/engines/access/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/access/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/access/detection/detection_enums.h b/engines/access/detection_enums.h
similarity index 100%
rename from engines/access/detection/detection_enums.h
rename to engines/access/detection_enums.h
diff --git a/engines/access/detection/detection_tables.h b/engines/access/detection_tables.h
similarity index 100%
rename from engines/access/detection/detection_tables.h
rename to engines/access/detection_tables.h
diff --git a/engines/access/metaengine.cpp b/engines/access/metaengine.cpp
index 8264a563ba..3ed66d49f1 100644
--- a/engines/access/metaengine.cpp
+++ b/engines/access/metaengine.cpp
@@ -32,7 +32,7 @@
 #include "access/amazon/amazon_game.h"
 #include "access/martian/martian_game.h"
 
-#include "access/detection/detection.h"
+#include "access/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/access/module.mk b/engines/access/module.mk
index db336ec3e2..03465dd715 100644
--- a/engines/access/module.mk
+++ b/engines/access/module.mk
@@ -41,3 +41,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/adl/adl.h b/engines/adl/adl.h
index f60e3bd987..1035b41028 100644
--- a/engines/adl/adl.h
+++ b/engines/adl/adl.h
@@ -41,7 +41,7 @@
 #include "adl/console.h"
 #include "adl/disk.h"
 #include "adl/sound.h"
-#include "adl/detection/detection_enums.h"
+#include "adl/detection_enums.h"
 
 namespace Common {
 class ReadStream;
diff --git a/engines/adl/adl_v2.cpp b/engines/adl/adl_v2.cpp
index c3baef35f8..d13455c353 100644
--- a/engines/adl/adl_v2.cpp
+++ b/engines/adl/adl_v2.cpp
@@ -26,7 +26,7 @@
 #include "adl/adl_v2.h"
 #include "adl/display.h"
 #include "adl/graphics.h"
-#include "adl/detection/detection_enums.h"
+#include "adl/detection_enums.h"
 
 namespace Adl {
 
diff --git a/engines/adl/detection/detection.cpp b/engines/adl/detection.cpp
similarity index 99%
rename from engines/adl/detection/detection.cpp
rename to engines/adl/detection.cpp
index 86a345449e..fcb5b2bcd4 100644
--- a/engines/adl/detection/detection.cpp
+++ b/engines/adl/detection.cpp
@@ -27,8 +27,8 @@
 
 #include "engines/advancedDetector.h"
 
-#include "adl/detection/detection_enums.h"
-#include "adl/detection/detection.h"
+#include "adl/detection_enums.h"
+#include "adl/detection.h"
 #include "adl/disk.h"
 #include "adl/disk_image_helpers.h"
 
diff --git a/engines/adl/detection/detection.h b/engines/adl/detection.h
similarity index 100%
rename from engines/adl/detection/detection.h
rename to engines/adl/detection.h
diff --git a/engines/adl/detection/module.mk b/engines/adl/detection/module.mk
deleted file mode 100644
index 8ba9932c22..0000000000
--- a/engines/adl/detection/module.mk
+++ /dev/null
@@ -1,11 +0,0 @@
-MODULE := engines/adl/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Skip building the following objects if a static
-# module is enabled, because it already has the contents.
-ifneq ($(ENABLE_ADL), STATIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/../disk.o
-endif
diff --git a/engines/adl/detection/detection_enums.h b/engines/adl/detection_enums.h
similarity index 100%
rename from engines/adl/detection/detection_enums.h
rename to engines/adl/detection_enums.h
diff --git a/engines/adl/hires4.cpp b/engines/adl/hires4.cpp
index f571b658f9..b251d44d97 100644
--- a/engines/adl/hires4.cpp
+++ b/engines/adl/hires4.cpp
@@ -29,7 +29,7 @@
 #include "common/memstream.h"
 
 #include "adl/adl_v3.h"
-#include "adl/detection/detection_enums.h"
+#include "adl/detection_enums.h"
 #include "adl/display_a2.h"
 #include "adl/graphics.h"
 #include "adl/disk.h"
diff --git a/engines/adl/hires5.cpp b/engines/adl/hires5.cpp
index 350a7a02c2..ef8749eedd 100644
--- a/engines/adl/hires5.cpp
+++ b/engines/adl/hires5.cpp
@@ -27,7 +27,7 @@
 #include "common/stream.h"
 
 #include "adl/adl_v4.h"
-#include "adl/detection/detection_enums.h"
+#include "adl/detection_enums.h"
 #include "adl/display_a2.h"
 #include "adl/graphics.h"
 #include "adl/disk.h"
diff --git a/engines/adl/metaengine.cpp b/engines/adl/metaengine.cpp
index 195fba010d..a7dd3cdf51 100644
--- a/engines/adl/metaengine.cpp
+++ b/engines/adl/metaengine.cpp
@@ -28,8 +28,8 @@
 
 #include "graphics/thumbnail.h"
 
-#include "adl/detection/detection_enums.h"
-#include "adl/detection/detection.h"
+#include "adl/detection_enums.h"
+#include "adl/detection.h"
 #include "adl/disk_image_helpers.h"
 
 namespace Adl {
diff --git a/engines/adl/module.mk b/engines/adl/module.mk
index df7e3f8dd1..1ab8247d71 100644
--- a/engines/adl/module.mk
+++ b/engines/adl/module.mk
@@ -28,3 +28,13 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_ADL), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/disk.o
+endif
diff --git a/engines/agi/detection/detection.cpp b/engines/agi/detection.cpp
similarity index 98%
rename from engines/agi/detection/detection.cpp
rename to engines/agi/detection.cpp
index ea43d2c819..10b4772f85 100644
--- a/engines/agi/detection/detection.cpp
+++ b/engines/agi/detection.cpp
@@ -29,8 +29,8 @@
 #include "engines/advancedDetector.h"
 
 #include "agi/detection_enums.h"
-#include "agi/detection/detection.h"
-#include "agi/detection/wagparser.h" // for fallback detection
+#include "agi/detection.h"
+#include "agi/wagparser.h" // for fallback detection
 
 static const PlainGameDescriptor agiGames[] = {
 	{"agi", "Sierra AGI game"},
@@ -64,7 +64,7 @@ static const PlainGameDescriptor agiGames[] = {
 	{0, 0}
 };
 
-#include "agi/detection/detection_tables.h"
+#include "agi/detection_tables.h"
 
 static const ADExtraGuiOptionsMap optionsList[] = {
 	{
diff --git a/engines/agi/detection/detection.h b/engines/agi/detection.h
similarity index 100%
rename from engines/agi/detection/detection.h
rename to engines/agi/detection.h
diff --git a/engines/agi/detection/module.mk b/engines/agi/detection/module.mk
deleted file mode 100644
index f25e7061aa..0000000000
--- a/engines/agi/detection/module.mk
+++ /dev/null
@@ -1,9 +0,0 @@
-MODULE := engines/agi/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# External dependencies of detection.
-# This is unneeded by the engine module itself,
-# so seperate it completely.
-DETECT_OBJS += $(MODULE)/wagparser.o
diff --git a/engines/agi/detection/detection_tables.h b/engines/agi/detection_tables.h
similarity index 100%
rename from engines/agi/detection/detection_tables.h
rename to engines/agi/detection_tables.h
diff --git a/engines/agi/metaengine.cpp b/engines/agi/metaengine.cpp
index 1f7aa20909..f2507a8f37 100644
--- a/engines/agi/metaengine.cpp
+++ b/engines/agi/metaengine.cpp
@@ -38,7 +38,7 @@
 #include "agi/preagi_troll.h"
 #include "agi/preagi_winnie.h"
 
-#include "agi/detection/detection.h"
+#include "agi/detection.h"
 
 namespace Agi {
 
diff --git a/engines/agi/module.mk b/engines/agi/module.mk
index 84a7138086..d66e4129de 100644
--- a/engines/agi/module.mk
+++ b/engines/agi/module.mk
@@ -49,3 +49,11 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# External dependencies of detection.
+# This is unneeded by the engine module itself,
+# so seperate it completely.
+DETECT_OBJS += $(MODULE)/wagparser.o
diff --git a/engines/agi/detection/wagparser.cpp b/engines/agi/wagparser.cpp
similarity index 99%
rename from engines/agi/detection/wagparser.cpp
rename to engines/agi/wagparser.cpp
index f7ace22153..fa11654ad9 100644
--- a/engines/agi/detection/wagparser.cpp
+++ b/engines/agi/wagparser.cpp
@@ -26,7 +26,7 @@
 #include "common/debug.h"
 #include "common/textconsole.h"
 
-#include "agi/detection/wagparser.h"
+#include "agi/wagparser.h"
 
 namespace Agi {
 
diff --git a/engines/agi/detection/wagparser.h b/engines/agi/wagparser.h
similarity index 100%
rename from engines/agi/detection/wagparser.h
rename to engines/agi/wagparser.h
diff --git a/engines/agos/agos.h b/engines/agos/agos.h
index fa32f4fa8c..eee7406c87 100644
--- a/engines/agos/agos.h
+++ b/engines/agos/agos.h
@@ -35,7 +35,7 @@
 #include "audio/mixer.h"
 
 #include "agos/vga.h"
-#include "agos/detection/detection_enums.h"
+#include "agos/detection_enums.h"
 
 /**
  * This is the namespace of the AGOS engine.
diff --git a/engines/agos/detection/detection.cpp b/engines/agos/detection.cpp
similarity index 95%
rename from engines/agos/detection/detection.cpp
rename to engines/agos/detection.cpp
index ca7325dfcc..32dd815412 100644
--- a/engines/agos/detection/detection.cpp
+++ b/engines/agos/detection.cpp
@@ -29,8 +29,8 @@
 #include "common/textconsole.h"
 #include "common/installshield_cab.h"
 
-#include "agos/detection/detection.h"
-#include "agos/detection/detection_enums.h"
+#include "agos/detection.h"
+#include "agos/detection_enums.h"
 #include "agos/intern_detection.h"
 #include "agos/obsolete.h" // Obsolete ID table.
 
@@ -57,7 +57,7 @@ static const PlainGameDescriptor agosGames[] = {
 	{0, 0}
 };
 
-#include "agos/detection/detection_tables.h"
+#include "agos/detection_tables.h"
 
 static const char *const directoryGlobs[] = {
 	"execute", // Used by Simon1 Acorn CD
diff --git a/engines/agos/detection/detection.h b/engines/agos/detection.h
similarity index 100%
rename from engines/agos/detection/detection.h
rename to engines/agos/detection.h
diff --git a/engines/agos/detection/module.mk b/engines/agos/detection/module.mk
deleted file mode 100644
index a034c3a3d6..0000000000
--- a/engines/agos/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/agos/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/agos/detection/detection_enums.h b/engines/agos/detection_enums.h
similarity index 100%
rename from engines/agos/detection/detection_enums.h
rename to engines/agos/detection_enums.h
diff --git a/engines/agos/detection/detection_tables.h b/engines/agos/detection_tables.h
similarity index 100%
rename from engines/agos/detection/detection_tables.h
rename to engines/agos/detection_tables.h
diff --git a/engines/agos/metaengine.cpp b/engines/agos/metaengine.cpp
index 8402b67ee9..7bac156118 100644
--- a/engines/agos/metaengine.cpp
+++ b/engines/agos/metaengine.cpp
@@ -30,7 +30,7 @@
 
 #include "agos/intern.h"
 #include "agos/agos.h"
-#include "agos/detection/detection.h"
+#include "agos/detection.h"
 #include "agos/obsolete.h"
 
 class AgosMetaEngineConnect : public AdvancedMetaEngineConnect {
diff --git a/engines/agos/module.mk b/engines/agos/module.mk
index 4c4c1b77f3..919f819c1c 100644
--- a/engines/agos/module.mk
+++ b/engines/agos/module.mk
@@ -69,3 +69,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/avalanche/detection/detection.cpp b/engines/avalanche/detection.cpp
similarity index 98%
rename from engines/avalanche/detection/detection.cpp
rename to engines/avalanche/detection.cpp
index 7d8f147248..d6baf0f64e 100644
--- a/engines/avalanche/detection/detection.cpp
+++ b/engines/avalanche/detection.cpp
@@ -30,7 +30,7 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "avalanche/detection/detection.h"
+#include "avalanche/detection.h"
 
 namespace Avalanche {
 
diff --git a/engines/avalanche/detection/detection.h b/engines/avalanche/detection.h
similarity index 100%
rename from engines/avalanche/detection/detection.h
rename to engines/avalanche/detection.h
diff --git a/engines/avalanche/detection/module.mk b/engines/avalanche/detection/module.mk
deleted file mode 100644
index 280c73c519..0000000000
--- a/engines/avalanche/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/avalanche/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/avalanche/metaengine.cpp b/engines/avalanche/metaengine.cpp
index 4e1db1b76c..f004c89964 100644
--- a/engines/avalanche/metaengine.cpp
+++ b/engines/avalanche/metaengine.cpp
@@ -33,7 +33,7 @@
 #include "engines/advancedDetector.h"
 #include "graphics/thumbnail.h"
 
-#include "avalanche/detection/detection.h"
+#include "avalanche/detection.h"
 
 
 namespace Avalanche {
diff --git a/engines/avalanche/module.mk b/engines/avalanche/module.mk
index 29fabb76a4..f8380b9bd1 100644
--- a/engines/avalanche/module.mk
+++ b/engines/avalanche/module.mk
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/bbvs/bbvs.h b/engines/bbvs/bbvs.h
index b06b9dc59d..d513c679f2 100644
--- a/engines/bbvs/bbvs.h
+++ b/engines/bbvs/bbvs.h
@@ -36,7 +36,7 @@
 
 #include "engines/engine.h"
 
-#include "bbvs/detection/detection_enums.h"
+#include "bbvs/detection_enums.h"
 
 struct ADGameDescription;
 
diff --git a/engines/bbvs/detection/detection.cpp b/engines/bbvs/detection.cpp
similarity index 98%
rename from engines/bbvs/detection/detection.cpp
rename to engines/bbvs/detection.cpp
index 6ef2d144ea..af1942f411 100644
--- a/engines/bbvs/detection/detection.cpp
+++ b/engines/bbvs/detection.cpp
@@ -23,7 +23,7 @@
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
 
-#include "bbvs/detection/detection_enums.h"
+#include "bbvs/detection_enums.h"
 
 static const PlainGameDescriptor bbvsGames[] = {
 	{ "bbvs", "Beavis and Butt-head in Virtual Stupidity" },
diff --git a/engines/bbvs/detection/module.mk b/engines/bbvs/detection/module.mk
deleted file mode 100644
index 89d5fa0194..0000000000
--- a/engines/bbvs/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/bbvs/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/bbvs/detection/detection_enums.h b/engines/bbvs/detection_enums.h
similarity index 100%
rename from engines/bbvs/detection/detection_enums.h
rename to engines/bbvs/detection_enums.h
diff --git a/engines/bbvs/module.mk b/engines/bbvs/module.mk
index 1b8c924738..e20210494a 100644
--- a/engines/bbvs/module.mk
+++ b/engines/bbvs/module.mk
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/bladerunner/detection/detection.cpp b/engines/bladerunner/detection.cpp
similarity index 98%
rename from engines/bladerunner/detection/detection.cpp
rename to engines/bladerunner/detection.cpp
index dc778f88d2..ecef2d5b34 100644
--- a/engines/bladerunner/detection/detection.cpp
+++ b/engines/bladerunner/detection.cpp
@@ -22,7 +22,7 @@
 
 
 #include "bladerunner/bladerunner.h"
-#include "bladerunner/detection/detection_tables.h"
+#include "bladerunner/detection_tables.h"
 #include "bladerunner/savefile.h"
 
 #include "common/config-manager.h"
diff --git a/engines/bladerunner/detection/module.mk b/engines/bladerunner/detection/module.mk
deleted file mode 100644
index 538df57d3f..0000000000
--- a/engines/bladerunner/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/bladerunner/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/bladerunner/detection/detection_tables.h b/engines/bladerunner/detection_tables.h
similarity index 100%
rename from engines/bladerunner/detection/detection_tables.h
rename to engines/bladerunner/detection_tables.h
diff --git a/engines/bladerunner/module.mk b/engines/bladerunner/module.mk
index a52b87426f..aae2394a9b 100644
--- a/engines/bladerunner/module.mk
+++ b/engines/bladerunner/module.mk
@@ -288,3 +288,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cge/detection/detection.cpp b/engines/cge/detection.cpp
similarity index 100%
rename from engines/cge/detection/detection.cpp
rename to engines/cge/detection.cpp
diff --git a/engines/cge/detection/module.mk b/engines/cge/detection/module.mk
deleted file mode 100644
index a9bdc97733..0000000000
--- a/engines/cge/detection/module.mk
+++ /dev/null
@@ -1,11 +0,0 @@
-MODULE := engines/cge/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Skip building the following objects if a static
-# module is enabled, because it already has the contents.
-ifneq ($(ENABLE_CGE), STATIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/../fileio.o
-endif
diff --git a/engines/cge/module.mk b/engines/cge/module.mk
index cc37bee472..6e920349b7 100644
--- a/engines/cge/module.mk
+++ b/engines/cge/module.mk
@@ -27,3 +27,13 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_CGE), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/fileio.o
+endif
diff --git a/engines/cge2/detection/detection.cpp b/engines/cge2/detection.cpp
similarity index 100%
rename from engines/cge2/detection/detection.cpp
rename to engines/cge2/detection.cpp
diff --git a/engines/cge2/detection/module.mk b/engines/cge2/detection/module.mk
deleted file mode 100644
index 89a8a9d63d..0000000000
--- a/engines/cge2/detection/module.mk
+++ /dev/null
@@ -1,11 +0,0 @@
-MODULE := engines/cge2/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Skip building the following objects if a static
-# module is enabled, because it already has the contents.
-ifneq ($(ENABLE_CGE2), STATIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/../fileio.o
-endif
diff --git a/engines/cge2/module.mk b/engines/cge2/module.mk
index 17604a6194..5c45f60051 100644
--- a/engines/cge2/module.mk
+++ b/engines/cge2/module.mk
@@ -28,3 +28,13 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_CGE2), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/fileio.o
+endif
diff --git a/engines/chewy/detection/detection.cpp b/engines/chewy/detection.cpp
similarity index 98%
rename from engines/chewy/detection/detection.cpp
rename to engines/chewy/detection.cpp
index 16d07d1e5f..17ed3f2b25 100644
--- a/engines/chewy/detection/detection.cpp
+++ b/engines/chewy/detection.cpp
@@ -23,7 +23,7 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "chewy/detection/detection.h"
+#include "chewy/detection.h"
 
 static const PlainGameDescriptor chewyGames[] = {
 	{"chewy", "Chewy: Esc from F5"},
diff --git a/engines/chewy/detection/detection.h b/engines/chewy/detection.h
similarity index 100%
rename from engines/chewy/detection/detection.h
rename to engines/chewy/detection.h
diff --git a/engines/chewy/detection/module.mk b/engines/chewy/detection/module.mk
deleted file mode 100644
index f7fc8665b2..0000000000
--- a/engines/chewy/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/chewy/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/chewy/metaengine.cpp b/engines/chewy/metaengine.cpp
index cfd9239cb7..bf14b79ebb 100644
--- a/engines/chewy/metaengine.cpp
+++ b/engines/chewy/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "engines/advancedDetector.h"
 
 #include "chewy/chewy.h"
-#include "chewy/detection/detection.h"
+#include "chewy/detection.h"
 
 namespace Chewy {
 
diff --git a/engines/chewy/module.mk b/engines/chewy/module.mk
index e552c48e3a..87d8042c52 100644
--- a/engines/chewy/module.mk
+++ b/engines/chewy/module.mk
@@ -20,3 +20,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cine/cine.h b/engines/cine/cine.h
index bab8c6f057..aec244e440 100644
--- a/engines/cine/cine.h
+++ b/engines/cine/cine.h
@@ -48,7 +48,7 @@
 #include "cine/various.h"
 #include "cine/console.h"
 #include "cine/sound.h"
-#include "cine/detection/detection_enums.h"
+#include "cine/detection_enums.h"
 
 //#define DUMP_SCRIPTS
 
diff --git a/engines/cine/detection/detection.cpp b/engines/cine/detection.cpp
similarity index 94%
rename from engines/cine/detection/detection.cpp
rename to engines/cine/detection.cpp
index 0b144c5346..311c922507 100644
--- a/engines/cine/detection/detection.cpp
+++ b/engines/cine/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "common/translation.h"
 
-#include "cine/detection/detection.h"
-#include "cine/detection/detection_enums.h"
+#include "cine/detection.h"
+#include "cine/detection_enums.h"
 
 static const PlainGameDescriptor cineGames[] = {
 	{"fw", "Future Wars"},
@@ -35,7 +35,7 @@ static const PlainGameDescriptor cineGames[] = {
 	{0, 0}
 };
 
-#include "cine/detection/detection_tables.h"
+#include "cine/detection_tables.h"
 
 static const ADExtraGuiOptionsMap optionsList[] = {
 	{
diff --git a/engines/cine/detection/detection.h b/engines/cine/detection.h
similarity index 100%
rename from engines/cine/detection/detection.h
rename to engines/cine/detection.h
diff --git a/engines/cine/detection/module.mk b/engines/cine/detection/module.mk
deleted file mode 100644
index 7d384f8379..0000000000
--- a/engines/cine/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/cine/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cine/detection/detection_enums.h b/engines/cine/detection_enums.h
similarity index 100%
rename from engines/cine/detection/detection_enums.h
rename to engines/cine/detection_enums.h
diff --git a/engines/cine/detection/detection_tables.h b/engines/cine/detection_tables.h
similarity index 100%
rename from engines/cine/detection/detection_tables.h
rename to engines/cine/detection_tables.h
diff --git a/engines/cine/metaengine.cpp b/engines/cine/metaengine.cpp
index 19db79d3b6..12c2d0a7bc 100644
--- a/engines/cine/metaengine.cpp
+++ b/engines/cine/metaengine.cpp
@@ -32,7 +32,7 @@
 #include "cine/cine.h"
 #include "cine/various.h"
 
-#include "cine/detection/detection.h"
+#include "cine/detection.h"
 
 namespace Cine {
 
diff --git a/engines/cine/module.mk b/engines/cine/module.mk
index 1c3dfbab46..510d3d0043 100644
--- a/engines/cine/module.mk
+++ b/engines/cine/module.mk
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/composer/composer.h b/engines/composer/composer.h
index 55759a8360..43716d648b 100644
--- a/engines/composer/composer.h
+++ b/engines/composer/composer.h
@@ -44,7 +44,7 @@
 
 #include "composer/resource.h"
 #include "composer/console.h"
-#include "composer/detection/detection_enums.h"
+#include "composer/detection_enums.h"
 
 namespace Audio {
 	class QueuingAudioStream;
diff --git a/engines/composer/detection/detection.cpp b/engines/composer/detection.cpp
similarity index 94%
rename from engines/composer/detection/detection.cpp
rename to engines/composer/detection.cpp
index e583c6081a..f548e00c59 100644
--- a/engines/composer/detection/detection.cpp
+++ b/engines/composer/detection.cpp
@@ -23,8 +23,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "composer/detection/detection_enums.h"
-#include "composer/detection/detection.h"
+#include "composer/detection_enums.h"
+#include "composer/detection.h"
 
 static const PlainGameDescriptor composerGames[] = {
 	{"babayaga", "Magic Tales: Baba Yaga and the Magic Geese"},
@@ -39,7 +39,7 @@ static const PlainGameDescriptor composerGames[] = {
 	{0, 0}
 };
 
-#include "composer/detection/detection_tables.h"
+#include "composer/detection_tables.h"
 
 using namespace Composer;
 
diff --git a/engines/composer/detection/detection.h b/engines/composer/detection.h
similarity index 100%
rename from engines/composer/detection/detection.h
rename to engines/composer/detection.h
diff --git a/engines/composer/detection/module.mk b/engines/composer/detection/module.mk
deleted file mode 100644
index f40bb0242d..0000000000
--- a/engines/composer/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/composer/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/composer/detection/detection_enums.h b/engines/composer/detection_enums.h
similarity index 100%
rename from engines/composer/detection/detection_enums.h
rename to engines/composer/detection_enums.h
diff --git a/engines/composer/detection/detection_tables.h b/engines/composer/detection_tables.h
similarity index 100%
rename from engines/composer/detection/detection_tables.h
rename to engines/composer/detection_tables.h
diff --git a/engines/composer/metaengine.cpp b/engines/composer/metaengine.cpp
index 5460e0e493..bb70d1bdc4 100644
--- a/engines/composer/metaengine.cpp
+++ b/engines/composer/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "engines/advancedDetector.h"
 
 #include "composer/composer.h"
-#include "composer/detection/detection.h"
+#include "composer/detection.h"
 
 namespace Composer {
 
diff --git a/engines/composer/module.mk b/engines/composer/module.mk
index 8d0ef0ee2c..6fdcc59d05 100644
--- a/engines/composer/module.mk
+++ b/engines/composer/module.mk
@@ -16,3 +16,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cruise/detection/detection.cpp b/engines/cruise/detection.cpp
similarity index 99%
rename from engines/cruise/detection/detection.cpp
rename to engines/cruise/detection.cpp
index f5772a3b05..b47cdb59ee 100644
--- a/engines/cruise/detection/detection.cpp
+++ b/engines/cruise/detection.cpp
@@ -23,7 +23,7 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "cruise/detection/detection.h"
+#include "cruise/detection.h"
 
 static const PlainGameDescriptor cruiseGames[] = {
 	{"cruise", "Cruise for a Corpse"},
diff --git a/engines/cruise/detection/detection.h b/engines/cruise/detection.h
similarity index 100%
rename from engines/cruise/detection/detection.h
rename to engines/cruise/detection.h
diff --git a/engines/cruise/detection/module.mk b/engines/cruise/detection/module.mk
deleted file mode 100644
index 47f6e46113..0000000000
--- a/engines/cruise/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/cruise/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cruise/metaengine.cpp b/engines/cruise/metaengine.cpp
index 3e7d45349a..83abf985fe 100644
--- a/engines/cruise/metaengine.cpp
+++ b/engines/cruise/metaengine.cpp
@@ -27,7 +27,7 @@
 
 #include "cruise/cruise.h"
 #include "cruise/saveload.h"
-#include "cruise/detection/detection.h"
+#include "cruise/detection.h"
 
 namespace Cruise {
 
diff --git a/engines/cruise/module.mk b/engines/cruise/module.mk
index 8b8cf3d120..8487ff3ff0 100644
--- a/engines/cruise/module.mk
+++ b/engines/cruise/module.mk
@@ -40,3 +40,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cryo/detection/detection.cpp b/engines/cryo/detection.cpp
similarity index 100%
rename from engines/cryo/detection/detection.cpp
rename to engines/cryo/detection.cpp
diff --git a/engines/cryo/detection/module.mk b/engines/cryo/detection/module.mk
deleted file mode 100644
index fe3b29d869..0000000000
--- a/engines/cryo/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/cryo/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cryo/module.mk b/engines/cryo/module.mk
index f99f68814b..11227ac5ee 100644
--- a/engines/cryo/module.mk
+++ b/engines/cryo/module.mk
@@ -18,3 +18,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cryomni3d/cryomni3d.h b/engines/cryomni3d/cryomni3d.h
index 51ed23b4af..d0dad279cf 100644
--- a/engines/cryomni3d/cryomni3d.h
+++ b/engines/cryomni3d/cryomni3d.h
@@ -38,7 +38,7 @@
 #include "cryomni3d/font_manager.h"
 #include "cryomni3d/objects.h"
 #include "cryomni3d/sprites.h"
-#include "cryomni3d/detection/detection_enums.h"
+#include "cryomni3d/detection_enums.h"
 
 class OSystem;
 
diff --git a/engines/cryomni3d/detection/detection.cpp b/engines/cryomni3d/detection.cpp
similarity index 93%
rename from engines/cryomni3d/detection/detection.cpp
rename to engines/cryomni3d/detection.cpp
index 6a77e5039e..78f119a117 100644
--- a/engines/cryomni3d/detection/detection.cpp
+++ b/engines/cryomni3d/detection.cpp
@@ -27,8 +27,8 @@
 #include "common/file.h"
 #include "common/md5.h"
 
-#include "cryomni3d/detection/detection.h"
-#include "cryomni3d/detection/detection_enums.h"
+#include "cryomni3d/detection.h"
+#include "cryomni3d/detection_enums.h"
 
 namespace CryOmni3D {
 
@@ -39,7 +39,7 @@ static const PlainGameDescriptor cryomni3DGames[] = {
 
 } // End of namespace CryOmni3D
 
-#include "cryomni3d/detection/detection_tables.h"
+#include "cryomni3d/detection_tables.h"
 
 namespace CryOmni3D {
 
diff --git a/engines/cryomni3d/detection/detection.h b/engines/cryomni3d/detection.h
similarity index 100%
rename from engines/cryomni3d/detection/detection.h
rename to engines/cryomni3d/detection.h
diff --git a/engines/cryomni3d/detection/module.mk b/engines/cryomni3d/detection/module.mk
deleted file mode 100644
index 57c244b75e..0000000000
--- a/engines/cryomni3d/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/cryomni3d/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/cryomni3d/detection/detection_enums.h b/engines/cryomni3d/detection_enums.h
similarity index 100%
rename from engines/cryomni3d/detection/detection_enums.h
rename to engines/cryomni3d/detection_enums.h
diff --git a/engines/cryomni3d/detection/detection_tables.h b/engines/cryomni3d/detection_tables.h
similarity index 100%
rename from engines/cryomni3d/detection/detection_tables.h
rename to engines/cryomni3d/detection_tables.h
diff --git a/engines/cryomni3d/metaengine.cpp b/engines/cryomni3d/metaengine.cpp
index 94c2b57310..edf688c661 100644
--- a/engines/cryomni3d/metaengine.cpp
+++ b/engines/cryomni3d/metaengine.cpp
@@ -36,7 +36,7 @@
 #include "cryomni3d/versailles/engine.h"
 #endif
 
-#include "cryomni3d/detection/detection.h"
+#include "cryomni3d/detection.h"
 
 namespace CryOmni3D {
 
diff --git a/engines/cryomni3d/module.mk b/engines/cryomni3d/module.mk
index 3b6559e6d3..2b8ed9dc7e 100644
--- a/engines/cryomni3d/module.mk
+++ b/engines/cryomni3d/module.mk
@@ -39,3 +39,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/director/detection/detection.cpp b/engines/director/detection.cpp
similarity index 98%
rename from engines/director/detection/detection.cpp
rename to engines/director/detection.cpp
index 9791adddcd..662ee94b83 100644
--- a/engines/director/detection/detection.cpp
+++ b/engines/director/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "common/file.h"
 
-#include "director/detection/detection_enums.h"
-#include "director/detection/detection.h"
+#include "director/detection_enums.h"
+#include "director/detection.h"
 
 static const PlainGameDescriptor directorGames[] = {
 	{ "director",			"Macromedia Director Game" },
@@ -166,7 +166,7 @@ static const PlainGameDescriptor directorGames[] = {
 	{ 0, 0 }
 };
 
-#include "director/detection/detection_tables.h"
+#include "director/detection_tables.h"
 
 static const char *directoryGlobs[] = {
 	"install",
diff --git a/engines/director/detection/detection.h b/engines/director/detection.h
similarity index 100%
rename from engines/director/detection/detection.h
rename to engines/director/detection.h
diff --git a/engines/director/detection/module.mk b/engines/director/detection/module.mk
deleted file mode 100644
index 8e1b03908c..0000000000
--- a/engines/director/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/director/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/director/detection/detection_enums.h b/engines/director/detection_enums.h
similarity index 100%
rename from engines/director/detection/detection_enums.h
rename to engines/director/detection_enums.h
diff --git a/engines/director/detection/detection_tables.h b/engines/director/detection_tables.h
similarity index 100%
rename from engines/director/detection/detection_tables.h
rename to engines/director/detection_tables.h
diff --git a/engines/director/director.h b/engines/director/director.h
index ef56ebe24a..1b20960b97 100644
--- a/engines/director/director.h
+++ b/engines/director/director.h
@@ -36,7 +36,7 @@
 
 #include "director/types.h"
 #include "director/util.h"
-#include "director/detection/detection_enums.h"
+#include "director/detection_enums.h"
 
 namespace Common {
 class MacResManager;
diff --git a/engines/director/metaengine.cpp b/engines/director/metaengine.cpp
index 607ae0acce..15f4313e56 100644
--- a/engines/director/metaengine.cpp
+++ b/engines/director/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "common/config-manager.h"
 
 #include "director/director.h"
-#include "director/detection/detection.h"
+#include "director/detection.h"
 
 namespace Director {
 
diff --git a/engines/director/module.mk b/engines/director/module.mk
index 65f8e86598..508ea8707a 100644
--- a/engines/director/module.mk
+++ b/engines/director/module.mk
@@ -51,3 +51,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dm/detection/detection.cpp b/engines/dm/detection.cpp
similarity index 97%
rename from engines/dm/detection/detection.cpp
rename to engines/dm/detection.cpp
index bbe2db53b7..aa051815f8 100644
--- a/engines/dm/detection/detection.cpp
+++ b/engines/dm/detection.cpp
@@ -29,8 +29,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "dm/detection/detection_enums.h"
-#include "dm/detection/detection.h"
+#include "dm/detection_enums.h"
+#include "dm/detection.h"
 
 namespace DM {
 
diff --git a/engines/dm/detection/detection.h b/engines/dm/detection.h
similarity index 100%
rename from engines/dm/detection/detection.h
rename to engines/dm/detection.h
diff --git a/engines/dm/detection/module.mk b/engines/dm/detection/module.mk
deleted file mode 100644
index f93250e3ed..0000000000
--- a/engines/dm/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/dm/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dm/detection/detection_enums.h b/engines/dm/detection_enums.h
similarity index 100%
rename from engines/dm/detection/detection_enums.h
rename to engines/dm/detection_enums.h
diff --git a/engines/dm/dm.h b/engines/dm/dm.h
index fa1d49a15d..029b671c23 100644
--- a/engines/dm/dm.h
+++ b/engines/dm/dm.h
@@ -39,8 +39,8 @@
 #include "advancedDetector.h"
 
 #include "dm/console.h"
-#include "dm/detection/detection_enums.h"
-#include "dm/detection/detection.h"
+#include "dm/detection_enums.h"
+#include "dm/detection.h"
 
 struct ADGameDescription;
 
diff --git a/engines/dm/module.mk b/engines/dm/module.mk
index 51ec4ecef8..95688dada9 100644
--- a/engines/dm/module.mk
+++ b/engines/dm/module.mk
@@ -60,3 +60,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/draci/detection/detection.cpp b/engines/draci/detection.cpp
similarity index 100%
rename from engines/draci/detection/detection.cpp
rename to engines/draci/detection.cpp
diff --git a/engines/draci/detection/module.mk b/engines/draci/detection/module.mk
deleted file mode 100644
index 238f621d72..0000000000
--- a/engines/draci/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/draci/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/draci/module.mk b/engines/draci/module.mk
index f6ad32af8e..43afb8cbe3 100644
--- a/engines/draci/module.mk
+++ b/engines/draci/module.mk
@@ -25,3 +25,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dragons/detection/detection.cpp b/engines/dragons/detection.cpp
similarity index 97%
rename from engines/dragons/detection/detection.cpp
rename to engines/dragons/detection.cpp
index 1cf5fa5bf0..75c6f1861a 100644
--- a/engines/dragons/detection/detection.cpp
+++ b/engines/dragons/detection.cpp
@@ -22,8 +22,8 @@
 
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
-#include "dragons/detection/detection_enums.h"
-#include "dragons/detection/detection.h"
+#include "dragons/detection_enums.h"
+#include "dragons/detection.h"
 
 static const PlainGameDescriptor dragonsGames[] = {
 		{ "dragons", "Blazing Dragons" },
diff --git a/engines/dragons/detection/detection.h b/engines/dragons/detection.h
similarity index 100%
rename from engines/dragons/detection/detection.h
rename to engines/dragons/detection.h
diff --git a/engines/dragons/detection/module.mk b/engines/dragons/detection/module.mk
deleted file mode 100644
index d3c27c1b3c..0000000000
--- a/engines/dragons/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/dragons/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dragons/detection/detection_enums.h b/engines/dragons/detection_enums.h
similarity index 100%
rename from engines/dragons/detection/detection_enums.h
rename to engines/dragons/detection_enums.h
diff --git a/engines/dragons/dragons.h b/engines/dragons/dragons.h
index e301b88ff6..c3b2883c93 100644
--- a/engines/dragons/dragons.h
+++ b/engines/dragons/dragons.h
@@ -25,8 +25,8 @@
 #include "gui/EventRecorder.h"
 #include "engines/engine.h"
 #include "dragons/specialopcodes.h"
-#include "dragons/detection/detection_enums.h"
-#include "dragons/detection/detection.h"
+#include "dragons/detection_enums.h"
+#include "dragons/detection.h"
 
 namespace Dragons {
 
diff --git a/engines/dragons/module.mk b/engines/dragons/module.mk
index edb6d20443..e05786f525 100644
--- a/engines/dragons/module.mk
+++ b/engines/dragons/module.mk
@@ -43,3 +43,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/drascula/detection/detection.cpp b/engines/drascula/detection.cpp
similarity index 98%
rename from engines/drascula/detection/detection.cpp
rename to engines/drascula/detection.cpp
index e3aae16c9d..d8eb9b0a5a 100644
--- a/engines/drascula/detection/detection.cpp
+++ b/engines/drascula/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "engines/advancedDetector.h"
 
-#include "drascula/detection/detection_enums.h"
-#include "drascula/detection/detection.h"
+#include "drascula/detection_enums.h"
+#include "drascula/detection.h"
 
 static const PlainGameDescriptor drasculaGames[] = {
 	{"drascula", "Drascula: The Vampire Strikes Back"},
diff --git a/engines/drascula/detection/detection.h b/engines/drascula/detection.h
similarity index 100%
rename from engines/drascula/detection/detection.h
rename to engines/drascula/detection.h
diff --git a/engines/drascula/detection/module.mk b/engines/drascula/detection/module.mk
deleted file mode 100644
index 275ec6b460..0000000000
--- a/engines/drascula/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/drascula/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/drascula/detection/detection_enums.h b/engines/drascula/detection_enums.h
similarity index 100%
rename from engines/drascula/detection/detection_enums.h
rename to engines/drascula/detection_enums.h
diff --git a/engines/drascula/drascula.h b/engines/drascula/drascula.h
index c1b2c9bc86..749f9c3033 100644
--- a/engines/drascula/drascula.h
+++ b/engines/drascula/drascula.h
@@ -39,7 +39,7 @@
 #include "engines/savestate.h"
 
 #include "drascula/console.h"
-#include "drascula/detection/detection_enums.h"
+#include "drascula/detection_enums.h"
 
 #include "audio/mixer.h"
 
diff --git a/engines/drascula/metaengine.cpp b/engines/drascula/metaengine.cpp
index 1adb8068e5..ec732a512b 100644
--- a/engines/drascula/metaengine.cpp
+++ b/engines/drascula/metaengine.cpp
@@ -26,7 +26,7 @@
 #include "graphics/thumbnail.h"
 
 #include "drascula/drascula.h"
-#include "drascula/detection/detection.h"
+#include "drascula/detection.h"
 
 namespace Drascula {
 
diff --git a/engines/drascula/module.mk b/engines/drascula/module.mk
index 3d2bf5ad37..46dae3e731 100644
--- a/engines/drascula/module.mk
+++ b/engines/drascula/module.mk
@@ -25,3 +25,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dreamweb/detection/detection.cpp b/engines/dreamweb/detection.cpp
similarity index 96%
rename from engines/dreamweb/detection/detection.cpp
rename to engines/dreamweb/detection.cpp
index ed5572bb1a..19e9a502a1 100644
--- a/engines/dreamweb/detection/detection.cpp
+++ b/engines/dreamweb/detection.cpp
@@ -28,14 +28,14 @@
 
 #include "engines/advancedDetector.h"
 
-#include "dreamweb/detection/detection.h"
+#include "dreamweb/detection.h"
 
 static const PlainGameDescriptor dreamWebGames[] = {
 	{ "dreamweb", "DreamWeb" },
 	{ 0, 0 }
 };
 
-#include "dreamweb/detection/detection_tables.h"
+#include "dreamweb/detection_tables.h"
 
 static const ADExtraGuiOptionsMap gameGuiOptions[] = {
 	{
diff --git a/engines/dreamweb/detection/detection.h b/engines/dreamweb/detection.h
similarity index 100%
rename from engines/dreamweb/detection/detection.h
rename to engines/dreamweb/detection.h
diff --git a/engines/dreamweb/detection/module.mk b/engines/dreamweb/detection/module.mk
deleted file mode 100644
index 7554d6e4a4..0000000000
--- a/engines/dreamweb/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/dreamweb/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/dreamweb/detection/detection_tables.h b/engines/dreamweb/detection_tables.h
similarity index 99%
rename from engines/dreamweb/detection/detection_tables.h
rename to engines/dreamweb/detection_tables.h
index 651b07fe22..73802e862e 100644
--- a/engines/dreamweb/detection/detection_tables.h
+++ b/engines/dreamweb/detection_tables.h
@@ -23,7 +23,7 @@
 #ifndef DREAMWEB_DETECTION_TABLES_H
 #define DREAMWEB_DETECTION_TABLES_H
 
-#include "dreamweb/detection/detection.h"
+#include "dreamweb/detection.h"
 
 namespace DreamWeb {
 
diff --git a/engines/dreamweb/metaengine.cpp b/engines/dreamweb/metaengine.cpp
index 80acb819dc..1d7a1c213f 100644
--- a/engines/dreamweb/metaengine.cpp
+++ b/engines/dreamweb/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "engines/advancedDetector.h"
 
 #include "dreamweb/dreamweb.h"
-#include "dreamweb/detection/detection.h"
+#include "dreamweb/detection.h"
 
 class DreamWebMetaEngineConnect : public AdvancedMetaEngineConnect {
 public:
diff --git a/engines/dreamweb/module.mk b/engines/dreamweb/module.mk
index 15966d81b2..d3c0f48a2a 100644
--- a/engines/dreamweb/module.mk
+++ b/engines/dreamweb/module.mk
@@ -31,3 +31,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/fullpipe/detection/detection.cpp b/engines/fullpipe/detection.cpp
similarity index 100%
rename from engines/fullpipe/detection/detection.cpp
rename to engines/fullpipe/detection.cpp
diff --git a/engines/fullpipe/detection/module.mk b/engines/fullpipe/detection/module.mk
deleted file mode 100644
index cd09772f65..0000000000
--- a/engines/fullpipe/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/fullpipe/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/fullpipe/module.mk b/engines/fullpipe/module.mk
index 232ab076db..3e59fdcb79 100644
--- a/engines/fullpipe/module.mk
+++ b/engines/fullpipe/module.mk
@@ -75,3 +75,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/glk/detection/detection.cpp b/engines/glk/detection.cpp
similarity index 100%
rename from engines/glk/detection/detection.cpp
rename to engines/glk/detection.cpp
diff --git a/engines/glk/detection/module.mk b/engines/glk/detection/module.mk
deleted file mode 100644
index 1608485f0a..0000000000
--- a/engines/glk/detection/module.mk
+++ /dev/null
@@ -1,30 +0,0 @@
-MODULE := engines/glk/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Sub-engine detection objects
-DETECT_OBJS += $(MODULE)/../adrift/detection.o
-DETECT_OBJS += $(MODULE)/../advsys/detection.o
-DETECT_OBJS += $(MODULE)/../agt/detection.o
-DETECT_OBJS += $(MODULE)/../alan2/detection.o
-DETECT_OBJS += $(MODULE)/../alan3/detection.o
-DETECT_OBJS += $(MODULE)/../archetype/detection.o
-DETECT_OBJS += $(MODULE)/../comprehend/detection.o
-DETECT_OBJS += $(MODULE)/../glulx/detection.o
-DETECT_OBJS += $(MODULE)/../hugo/detection.o
-DETECT_OBJS += $(MODULE)/../jacl/detection.o
-DETECT_OBJS += $(MODULE)/../level9/detection.o
-DETECT_OBJS += $(MODULE)/../magnetic/detection.o
-DETECT_OBJS += $(MODULE)/../quest/detection.o
-DETECT_OBJS += $(MODULE)/../scott/detection.o
-DETECT_OBJS += $(MODULE)/../tads/detection.o
-DETECT_OBJS += $(MODULE)/../zcode/detection.o
-
-# Skip building the following objects if a static
-# module is enabled, because it already has the contents.
-ifneq ($(ENABLE_GLK), STATIC_PLUGIN)
-# Dependencies of detection objects
-DETECT_OBJS += $(MODULE)/../blorb.o
-DETECT_OBJS += $(MODULE)/../advsys/game.o
-endif
diff --git a/engines/glk/module.mk b/engines/glk/module.mk
index 8b6eee35d4..d9892b3bb4 100644
--- a/engines/glk/module.mk
+++ b/engines/glk/module.mk
@@ -305,3 +305,32 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Sub-engine detection objects
+DETECT_OBJS += $(MODULE)/adrift/detection.o
+DETECT_OBJS += $(MODULE)/advsys/detection.o
+DETECT_OBJS += $(MODULE)/agt/detection.o
+DETECT_OBJS += $(MODULE)/alan2/detection.o
+DETECT_OBJS += $(MODULE)/alan3/detection.o
+DETECT_OBJS += $(MODULE)/archetype/detection.o
+DETECT_OBJS += $(MODULE)/comprehend/detection.o
+DETECT_OBJS += $(MODULE)/glulx/detection.o
+DETECT_OBJS += $(MODULE)/hugo/detection.o
+DETECT_OBJS += $(MODULE)/jacl/detection.o
+DETECT_OBJS += $(MODULE)/level9/detection.o
+DETECT_OBJS += $(MODULE)/magnetic/detection.o
+DETECT_OBJS += $(MODULE)/quest/detection.o
+DETECT_OBJS += $(MODULE)/scott/detection.o
+DETECT_OBJS += $(MODULE)/tads/detection.o
+DETECT_OBJS += $(MODULE)/zcode/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_GLK), STATIC_PLUGIN)
+# Dependencies of detection objects
+DETECT_OBJS += $(MODULE)/blorb.o
+DETECT_OBJS += $(MODULE)/advsys/game.o
+endif
diff --git a/engines/gnap/detection/detection.cpp b/engines/gnap/detection.cpp
similarity index 100%
rename from engines/gnap/detection/detection.cpp
rename to engines/gnap/detection.cpp
diff --git a/engines/gnap/detection/module.mk b/engines/gnap/detection/module.mk
deleted file mode 100644
index 950a149cbd..0000000000
--- a/engines/gnap/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/gnap/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/gnap/module.mk b/engines/gnap/module.mk
index 6e91598a4f..14f3aa5003 100644
--- a/engines/gnap/module.mk
+++ b/engines/gnap/module.mk
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/gob/detection/module.mk b/engines/gob/detection/module.mk
deleted file mode 100644
index 43211a9832..0000000000
--- a/engines/gob/detection/module.mk
+++ /dev/null
@@ -1,11 +0,0 @@
-MODULE := engines/gob/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Skip building the following objects if a static
-# module is enabled, because it already has the contents.
-ifneq ($(ENABLE_GOB), STATIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/../dataio.o
-endif
diff --git a/engines/gob/module.mk b/engines/gob/module.mk
index b3980f4d7f..0a09eb8404 100644
--- a/engines/gob/module.mk
+++ b/engines/gob/module.mk
@@ -133,3 +133,13 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_GOB), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/dataio.o
+endif
diff --git a/engines/griffon/detection/detection.cpp b/engines/griffon/detection.cpp
similarity index 100%
rename from engines/griffon/detection/detection.cpp
rename to engines/griffon/detection.cpp
diff --git a/engines/griffon/detection/module.mk b/engines/griffon/detection/module.mk
deleted file mode 100644
index 7c70709aeb..0000000000
--- a/engines/griffon/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/griffon/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/griffon/module.mk b/engines/griffon/module.mk
index 503571321b..a3ed512096 100644
--- a/engines/griffon/module.mk
+++ b/engines/griffon/module.mk
@@ -26,3 +26,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/groovie/detection/detection.cpp b/engines/groovie/detection.cpp
similarity index 99%
rename from engines/groovie/detection/detection.cpp
rename to engines/groovie/detection.cpp
index 67d908090c..c607181551 100644
--- a/engines/groovie/detection/detection.cpp
+++ b/engines/groovie/detection.cpp
@@ -24,8 +24,8 @@
 #include "common/translation.h"
 
 #include "engines/advancedDetector.h"
-#include "groovie/detection/detection_enums.h"
-#include "groovie/detection/detection.h"
+#include "groovie/detection_enums.h"
+#include "groovie/detection.h"
 
 namespace Groovie {
 
diff --git a/engines/groovie/detection/detection.h b/engines/groovie/detection.h
similarity index 100%
rename from engines/groovie/detection/detection.h
rename to engines/groovie/detection.h
diff --git a/engines/groovie/detection/module.mk b/engines/groovie/detection/module.mk
deleted file mode 100644
index f799e077ac..0000000000
--- a/engines/groovie/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/groovie/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/groovie/detection/detection_enums.h b/engines/groovie/detection_enums.h
similarity index 100%
rename from engines/groovie/detection/detection_enums.h
rename to engines/groovie/detection_enums.h
diff --git a/engines/groovie/groovie.cpp b/engines/groovie/groovie.cpp
index 1adb247276..f44a0a2759 100644
--- a/engines/groovie/groovie.cpp
+++ b/engines/groovie/groovie.cpp
@@ -22,7 +22,7 @@
 
 #include "groovie/groovie.h"
 #include "groovie/cursor.h"
-#include "groovie/detection/detection.h"
+#include "groovie/detection.h"
 #include "groovie/graphics.h"
 #include "groovie/script.h"
 #include "groovie/music.h"
diff --git a/engines/groovie/groovie.h b/engines/groovie/groovie.h
index 7c314f6c88..4d26552bf8 100644
--- a/engines/groovie/groovie.h
+++ b/engines/groovie/groovie.h
@@ -28,7 +28,7 @@
 
 #include "engines/engine.h"
 #include "graphics/pixelformat.h"
-#include "groovie/detection/detection_enums.h"
+#include "groovie/detection_enums.h"
 
 namespace Common {
 class MacResManager;
diff --git a/engines/groovie/metaengine.cpp b/engines/groovie/metaengine.cpp
index ac01717257..316237f6a7 100644
--- a/engines/groovie/metaengine.cpp
+++ b/engines/groovie/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "common/translation.h"
 
 #include "engines/advancedDetector.h"
-#include "groovie/detection/detection.h"
+#include "groovie/detection.h"
 
 namespace Groovie {
 
diff --git a/engines/groovie/module.mk b/engines/groovie/module.mk
index 58ae8d8bc8..b01ac47a11 100644
--- a/engines/groovie/module.mk
+++ b/engines/groovie/module.mk
@@ -29,3 +29,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/groovie/script.h b/engines/groovie/script.h
index 9a8e3a4d51..4b82a8ef50 100644
--- a/engines/groovie/script.h
+++ b/engines/groovie/script.h
@@ -24,7 +24,7 @@
 #define GROOVIE_SCRIPT_H
 
 #include "groovie/groovie.h"
-#include "groovie/detection/detection_enums.h"
+#include "groovie/detection_enums.h"
 
 #include "common/random.h"
 #include "common/rect.h"
diff --git a/engines/hdb/detection/detection.cpp b/engines/hdb/detection.cpp
similarity index 98%
rename from engines/hdb/detection/detection.cpp
rename to engines/hdb/detection.cpp
index 1df1eb263b..8f995787ae 100644
--- a/engines/hdb/detection/detection.cpp
+++ b/engines/hdb/detection.cpp
@@ -24,7 +24,7 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "hdb/detection/detection_enums.h"
+#include "hdb/detection_enums.h"
 
 static const PlainGameDescriptor hdbGames[] = {
 	{"hdb", "Hyperspace Delivery Boy!"},
diff --git a/engines/hdb/detection/module.mk b/engines/hdb/detection/module.mk
deleted file mode 100644
index d5388c2fe8..0000000000
--- a/engines/hdb/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/hdb/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hdb/detection/detection_enums.h b/engines/hdb/detection_enums.h
similarity index 100%
rename from engines/hdb/detection/detection_enums.h
rename to engines/hdb/detection_enums.h
diff --git a/engines/hdb/metaengine.cpp b/engines/hdb/metaengine.cpp
index f0ae2379c9..a83a0402fa 100644
--- a/engines/hdb/metaengine.cpp
+++ b/engines/hdb/metaengine.cpp
@@ -34,7 +34,7 @@
 
 #include "hdb/hdb.h"
 #include "hdb/input.h"
-#include "hdb/detection/detection_enums.h"
+#include "hdb/detection_enums.h"
 
 namespace HDB {
 
diff --git a/engines/hdb/module.mk b/engines/hdb/module.mk
index 9e78f1e874..24cc53bd41 100644
--- a/engines/hdb/module.mk
+++ b/engines/hdb/module.mk
@@ -32,3 +32,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hopkins/detection/detection.cpp b/engines/hopkins/detection.cpp
similarity index 96%
rename from engines/hopkins/detection/detection.cpp
rename to engines/hopkins/detection.cpp
index 753d2c9d6f..97fcb86eb9 100644
--- a/engines/hopkins/detection/detection.cpp
+++ b/engines/hopkins/detection.cpp
@@ -24,14 +24,14 @@
 #include "engines/advancedDetector.h"
 #include "common/translation.h"
 
-#include "hopkins/detection/detection.h"
+#include "hopkins/detection.h"
 
 static const PlainGameDescriptor hopkinsGames[] = {
 	{"hopkins", "Hopkins FBI"},
 	{0, 0}
 };
 
-#include "hopkins/detection/detection_tables.h"
+#include "hopkins/detection_tables.h"
 
 static const ADExtraGuiOptionsMap optionsList[] = {
 	{
diff --git a/engines/hopkins/detection/detection.h b/engines/hopkins/detection.h
similarity index 100%
rename from engines/hopkins/detection/detection.h
rename to engines/hopkins/detection.h
diff --git a/engines/hopkins/detection/module.mk b/engines/hopkins/detection/module.mk
deleted file mode 100644
index 14d10d93a1..0000000000
--- a/engines/hopkins/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/hopkins/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hopkins/detection/detection_tables.h b/engines/hopkins/detection_tables.h
similarity index 100%
rename from engines/hopkins/detection/detection_tables.h
rename to engines/hopkins/detection_tables.h
diff --git a/engines/hopkins/metaengine.cpp b/engines/hopkins/metaengine.cpp
index 58814f1e1e..bc07ba1599 100644
--- a/engines/hopkins/metaengine.cpp
+++ b/engines/hopkins/metaengine.cpp
@@ -31,7 +31,7 @@
 #include "common/translation.h"
 #include "graphics/surface.h"
 
-#include "hopkins/detection/detection.h"
+#include "hopkins/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/hopkins/module.mk b/engines/hopkins/module.mk
index 67525a05b8..2110a45e2c 100644
--- a/engines/hopkins/module.mk
+++ b/engines/hopkins/module.mk
@@ -27,3 +27,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hugo/detection/detection.cpp b/engines/hugo/detection.cpp
similarity index 97%
rename from engines/hugo/detection/detection.cpp
rename to engines/hugo/detection.cpp
index 9f6f47135e..1b261eeb2d 100644
--- a/engines/hugo/detection/detection.cpp
+++ b/engines/hugo/detection.cpp
@@ -23,8 +23,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "hugo/detection/detection_enums.h"
-#include "hugo/detection/detection.h"
+#include "hugo/detection_enums.h"
+#include "hugo/detection.h"
 
 namespace Hugo {
 
diff --git a/engines/hugo/detection/detection.h b/engines/hugo/detection.h
similarity index 100%
rename from engines/hugo/detection/detection.h
rename to engines/hugo/detection.h
diff --git a/engines/hugo/detection/module.mk b/engines/hugo/detection/module.mk
deleted file mode 100644
index ad62659f74..0000000000
--- a/engines/hugo/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/hugo/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/hugo/detection/detection_enums.h b/engines/hugo/detection_enums.h
similarity index 100%
rename from engines/hugo/detection/detection_enums.h
rename to engines/hugo/detection_enums.h
diff --git a/engines/hugo/hugo.h b/engines/hugo/hugo.h
index e58caffcc7..288d73b20c 100644
--- a/engines/hugo/hugo.h
+++ b/engines/hugo/hugo.h
@@ -27,7 +27,7 @@
 
 // This include is here temporarily while the engine is being refactored.
 #include "hugo/game.h"
-#include "hugo/detection/detection_enums.h"
+#include "hugo/detection_enums.h"
 
 #define HUGO_DAT_VER_MAJ 0                          // 1 byte
 #define HUGO_DAT_VER_MIN 42                         // 1 byte
diff --git a/engines/hugo/metaengine.cpp b/engines/hugo/metaengine.cpp
index 0f0290cbcc..8deb53be2c 100644
--- a/engines/hugo/metaengine.cpp
+++ b/engines/hugo/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "graphics/surface.h"
 
 #include "hugo/hugo.h"
-#include "hugo/detection/detection.h"
+#include "hugo/detection.h"
 
 namespace Hugo {
 
diff --git a/engines/hugo/module.mk b/engines/hugo/module.mk
index cdaadd9a23..1f5c5f41ec 100644
--- a/engines/hugo/module.mk
+++ b/engines/hugo/module.mk
@@ -38,3 +38,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/illusions/detection/detection.cpp b/engines/illusions/detection.cpp
similarity index 97%
rename from engines/illusions/detection/detection.cpp
rename to engines/illusions/detection.cpp
index fbbd29bf6c..4d04a6f7db 100644
--- a/engines/illusions/detection/detection.cpp
+++ b/engines/illusions/detection.cpp
@@ -24,8 +24,8 @@
 
 #include "base/plugins.h"
 
-#include "illusions/detection/detection_enums.h"
-#include "illusions/detection/detection.h"
+#include "illusions/detection_enums.h"
+#include "illusions/detection.h"
 
 static const PlainGameDescriptor illusionsGames[] = {
 	{ "bbdou", "Beavis and Butt-head Do U" },
diff --git a/engines/illusions/detection/detection.h b/engines/illusions/detection.h
similarity index 100%
rename from engines/illusions/detection/detection.h
rename to engines/illusions/detection.h
diff --git a/engines/illusions/detection/module.mk b/engines/illusions/detection/module.mk
deleted file mode 100644
index e3925749b3..0000000000
--- a/engines/illusions/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/illusions/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/illusions/detection/detection_enums.h b/engines/illusions/detection_enums.h
similarity index 100%
rename from engines/illusions/detection/detection_enums.h
rename to engines/illusions/detection_enums.h
diff --git a/engines/illusions/illusions.h b/engines/illusions/illusions.h
index f1945c16d8..73d6eced49 100644
--- a/engines/illusions/illusions.h
+++ b/engines/illusions/illusions.h
@@ -38,7 +38,7 @@
 
 #include "engines/engine.h"
 #include "graphics/surface.h"
-#include "illusions/detection/detection_enums.h"
+#include "illusions/detection_enums.h"
 
 namespace Illusions {
 
diff --git a/engines/illusions/metaengine.cpp b/engines/illusions/metaengine.cpp
index 45051adf94..b01997b873 100644
--- a/engines/illusions/metaengine.cpp
+++ b/engines/illusions/metaengine.cpp
@@ -31,7 +31,7 @@
 #include "base/plugins.h"
 #include "graphics/thumbnail.h"
 
-#include "illusions/detection/detection.h"
+#include "illusions/detection.h"
 
 namespace Illusions {
 
diff --git a/engines/illusions/module.mk b/engines/illusions/module.mk
index f134b1eda0..752cfdbbf6 100644
--- a/engines/illusions/module.mk
+++ b/engines/illusions/module.mk
@@ -76,3 +76,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/kingdom/detection/detection.cpp b/engines/kingdom/detection.cpp
similarity index 100%
rename from engines/kingdom/detection/detection.cpp
rename to engines/kingdom/detection.cpp
diff --git a/engines/kingdom/detection/module.mk b/engines/kingdom/detection/module.mk
deleted file mode 100644
index d98b678e6f..0000000000
--- a/engines/kingdom/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/kingdom/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/kingdom/module.mk b/engines/kingdom/module.mk
index c8a948495c..82c7dd45b6 100644
--- a/engines/kingdom/module.mk
+++ b/engines/kingdom/module.mk
@@ -18,3 +18,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/kyra/detection/detection.cpp b/engines/kyra/detection.cpp
similarity index 96%
rename from engines/kyra/detection/detection.cpp
rename to engines/kyra/detection.cpp
index d2d88817c8..295ddd7309 100644
--- a/engines/kyra/detection/detection.cpp
+++ b/engines/kyra/detection.cpp
@@ -24,9 +24,9 @@
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
 
-#include "kyra/detection/detection_enums.h"
-#include "kyra/detection/detection.h"
-#include "kyra/detection/detection_tables.h"
+#include "kyra/detection_enums.h"
+#include "kyra/detection.h"
+#include "kyra/detection_tables.h"
 
 namespace {
 
diff --git a/engines/kyra/detection/detection.h b/engines/kyra/detection.h
similarity index 100%
rename from engines/kyra/detection/detection.h
rename to engines/kyra/detection.h
diff --git a/engines/kyra/detection/module.mk b/engines/kyra/detection/module.mk
deleted file mode 100644
index b3866074c4..0000000000
--- a/engines/kyra/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/kyra/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/kyra/detection/detection_enums.h b/engines/kyra/detection_enums.h
similarity index 100%
rename from engines/kyra/detection/detection_enums.h
rename to engines/kyra/detection_enums.h
diff --git a/engines/kyra/detection/detection_tables.h b/engines/kyra/detection_tables.h
similarity index 100%
rename from engines/kyra/detection/detection_tables.h
rename to engines/kyra/detection_tables.h
diff --git a/engines/kyra/kyra_v1.h b/engines/kyra/kyra_v1.h
index 7aef4a2e97..65d02ebf25 100644
--- a/engines/kyra/kyra_v1.h
+++ b/engines/kyra/kyra_v1.h
@@ -36,7 +36,7 @@
 
 #include "kyra/script/script.h"
 #include "kyra/engine/item.h"
-#include "kyra/detection/detection_enums.h"
+#include "kyra/detection_enums.h"
 
 namespace Common {
 class OutSaveFile;
diff --git a/engines/kyra/metaengine.cpp b/engines/kyra/metaengine.cpp
index 9c92d204be..3d6c680693 100644
--- a/engines/kyra/metaengine.cpp
+++ b/engines/kyra/metaengine.cpp
@@ -36,7 +36,7 @@
 
 #include "base/plugins.h"
 
-#include "kyra/detection/detection.h"
+#include "kyra/detection.h"
 
 class KyraMetaEngineConnect : public AdvancedMetaEngineConnect {
 public:
diff --git a/engines/kyra/module.mk b/engines/kyra/module.mk
index 9f4b9a7520..dbab44939c 100644
--- a/engines/kyra/module.mk
+++ b/engines/kyra/module.mk
@@ -159,3 +159,6 @@ $(MODULE)/graphics/screen.o: $(MODULE)/graphics/screen.cpp
 	$(MKDIR) $(*D)/$(DEPDIR)
 	$(CXX) -Wp,-MMD,"$(*D)/$(DEPDIR)/$(*F).d",-MQ,"$@",-MP $(CXXFLAGS) -O3 $(CPPFLAGS) -c $(<) -o $*.o
 endif
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lab/detection/detection.cpp b/engines/lab/detection.cpp
similarity index 98%
rename from engines/lab/detection/detection.cpp
rename to engines/lab/detection.cpp
index a944e51e14..8a63ca3604 100644
--- a/engines/lab/detection/detection.cpp
+++ b/engines/lab/detection.cpp
@@ -29,7 +29,7 @@
  */
 
 #include "engines/advancedDetector.h"
-#include "lab/detection/detection_enums.h"
+#include "lab/detection_enums.h"
 
 static const PlainGameDescriptor lab_setting[] = {
 	{ "lab", "Labyrinth of Time" },
diff --git a/engines/lab/detection/module.mk b/engines/lab/detection/module.mk
deleted file mode 100644
index 1c32822a69..0000000000
--- a/engines/lab/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/lab/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lab/detection/detection_enums.h b/engines/lab/detection_enums.h
similarity index 100%
rename from engines/lab/detection/detection_enums.h
rename to engines/lab/detection_enums.h
diff --git a/engines/lab/lab.h b/engines/lab/lab.h
index 496f0b88f8..17667cc70f 100644
--- a/engines/lab/lab.h
+++ b/engines/lab/lab.h
@@ -41,7 +41,7 @@
 #include "lab/console.h"
 #include "lab/image.h"
 #include "lab/labsets.h"
-#include "lab/detection/detection_enums.h"
+#include "lab/detection_enums.h"
 
 struct ADGameDescription;
 
diff --git a/engines/lab/module.mk b/engines/lab/module.mk
index d7dcd58e3e..67fd2fd2db 100644
--- a/engines/lab/module.mk
+++ b/engines/lab/module.mk
@@ -28,3 +28,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lastexpress/detection/detection.cpp b/engines/lastexpress/detection.cpp
similarity index 100%
rename from engines/lastexpress/detection/detection.cpp
rename to engines/lastexpress/detection.cpp
diff --git a/engines/lastexpress/detection/module.mk b/engines/lastexpress/detection/module.mk
deleted file mode 100644
index d4c7f9d700..0000000000
--- a/engines/lastexpress/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/lastexpress/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lastexpress/module.mk b/engines/lastexpress/module.mk
index 77a7cf8271..d25a57c581 100644
--- a/engines/lastexpress/module.mk
+++ b/engines/lastexpress/module.mk
@@ -81,3 +81,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lilliput/detection/detection.cpp b/engines/lilliput/detection.cpp
similarity index 97%
rename from engines/lilliput/detection/detection.cpp
rename to engines/lilliput/detection.cpp
index 3a26a60591..74d582efb7 100644
--- a/engines/lilliput/detection/detection.cpp
+++ b/engines/lilliput/detection.cpp
@@ -24,8 +24,8 @@
 #include "engines/advancedDetector.h"
 #include "common/textconsole.h"
 
-#include "lilliput/detection/detection_enums.h"
-#include "lilliput/detection/detection.h"
+#include "lilliput/detection_enums.h"
+#include "lilliput/detection.h"
 
 namespace Lilliput {
 
diff --git a/engines/lilliput/detection/detection.h b/engines/lilliput/detection.h
similarity index 100%
rename from engines/lilliput/detection/detection.h
rename to engines/lilliput/detection.h
diff --git a/engines/lilliput/detection/module.mk b/engines/lilliput/detection/module.mk
deleted file mode 100644
index a6dbcc6f61..0000000000
--- a/engines/lilliput/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/lilliput/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lilliput/detection/detection_enums.h b/engines/lilliput/detection_enums.h
similarity index 100%
rename from engines/lilliput/detection/detection_enums.h
rename to engines/lilliput/detection_enums.h
diff --git a/engines/lilliput/lilliput.h b/engines/lilliput/lilliput.h
index eac0120ed2..b4e90a0afb 100644
--- a/engines/lilliput/lilliput.h
+++ b/engines/lilliput/lilliput.h
@@ -27,7 +27,7 @@
 #include "lilliput/script.h"
 #include "lilliput/sound.h"
 #include "lilliput/stream.h"
-#include "lilliput/detection/detection_enums.h"
+#include "lilliput/detection_enums.h"
 
 #include "common/file.h"
 #include "common/rect.h"
diff --git a/engines/lilliput/metaengine.cpp b/engines/lilliput/metaengine.cpp
index 55c237f59a..e6df2bacfb 100644
--- a/engines/lilliput/metaengine.cpp
+++ b/engines/lilliput/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "graphics/surface.h"
 
 #include "lilliput/lilliput.h"
-#include "lilliput/detection/detection.h"
+#include "lilliput/detection.h"
 
 namespace Lilliput {
 
diff --git a/engines/lilliput/module.mk b/engines/lilliput/module.mk
index 8391675b58..4002907135 100644
--- a/engines/lilliput/module.mk
+++ b/engines/lilliput/module.mk
@@ -18,3 +18,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lure/detection/detection.cpp b/engines/lure/detection.cpp
similarity index 98%
rename from engines/lure/detection/detection.cpp
rename to engines/lure/detection.cpp
index 74874418c7..017b7d9b52 100644
--- a/engines/lure/detection/detection.cpp
+++ b/engines/lure/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "common/translation.h"
 
-#include "lure/detection/detection_enums.h"
-#include "lure/detection/detection.h"
+#include "lure/detection_enums.h"
+#include "lure/detection.h"
 
 static const PlainGameDescriptor lureGames[] = {
 	{"lure", "Lure of the Temptress"},
diff --git a/engines/lure/detection/detection.h b/engines/lure/detection.h
similarity index 100%
rename from engines/lure/detection/detection.h
rename to engines/lure/detection.h
diff --git a/engines/lure/detection/module.mk b/engines/lure/detection/module.mk
deleted file mode 100644
index cacf1641bd..0000000000
--- a/engines/lure/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/lure/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/lure/detection/detection_enums.h b/engines/lure/detection_enums.h
similarity index 100%
rename from engines/lure/detection/detection_enums.h
rename to engines/lure/detection_enums.h
diff --git a/engines/lure/lure.h b/engines/lure/lure.h
index 0c849b46c9..c2ec5a5328 100644
--- a/engines/lure/lure.h
+++ b/engines/lure/lure.h
@@ -40,7 +40,7 @@
 #include "lure/strings.h"
 #include "lure/room.h"
 #include "lure/fights.h"
-#include "lure/detection/detection_enums.h"
+#include "lure/detection_enums.h"
 
 /**
  * This is the namespace of the Lure engine.
diff --git a/engines/lure/metaengine.cpp b/engines/lure/metaengine.cpp
index 7a680418ee..c6d7171f3b 100644
--- a/engines/lure/metaengine.cpp
+++ b/engines/lure/metaengine.cpp
@@ -26,7 +26,7 @@
 #include "engines/advancedDetector.h"
 
 #include "lure/lure.h"
-#include "lure/detection/detection.h"
+#include "lure/detection.h"
 
 namespace Lure {
 
diff --git a/engines/lure/module.mk b/engines/lure/module.mk
index efde4c7db7..7aae9073ef 100644
--- a/engines/lure/module.mk
+++ b/engines/lure/module.mk
@@ -31,3 +31,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/macventure/detection/detection.cpp b/engines/macventure/detection.cpp
similarity index 100%
rename from engines/macventure/detection/detection.cpp
rename to engines/macventure/detection.cpp
diff --git a/engines/macventure/detection/module.mk b/engines/macventure/detection/module.mk
deleted file mode 100644
index 80d08585c9..0000000000
--- a/engines/macventure/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/macventure/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/macventure/module.mk b/engines/macventure/module.mk
index 79541c69ce..0c0cf8b093 100644
--- a/engines/macventure/module.mk
+++ b/engines/macventure/module.mk
@@ -29,3 +29,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/made/detection/detection.cpp b/engines/made/detection.cpp
similarity index 95%
rename from engines/made/detection/detection.cpp
rename to engines/made/detection.cpp
index ba71394855..02dbc5763a 100644
--- a/engines/made/detection/detection.cpp
+++ b/engines/made/detection.cpp
@@ -23,8 +23,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "made/detection/detection_enums.h"
-#include "made/detection/detection.h"
+#include "made/detection_enums.h"
+#include "made/detection.h"
 
 static const PlainGameDescriptor madeGames[] = {
 	{"manhole", "The Manhole"},
@@ -34,7 +34,7 @@ static const PlainGameDescriptor madeGames[] = {
 	{0, 0}
 };
 
-#include "made/detection/detection_tables.h"
+#include "made/detection_tables.h"
 
 class MadeMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/made/detection/detection.h b/engines/made/detection.h
similarity index 100%
rename from engines/made/detection/detection.h
rename to engines/made/detection.h
diff --git a/engines/made/detection/module.mk b/engines/made/detection/module.mk
deleted file mode 100644
index e4b2b31d6f..0000000000
--- a/engines/made/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/made/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/made/detection/detection_enums.h b/engines/made/detection_enums.h
similarity index 100%
rename from engines/made/detection/detection_enums.h
rename to engines/made/detection_enums.h
diff --git a/engines/made/detection/detection_tables.h b/engines/made/detection_tables.h
similarity index 100%
rename from engines/made/detection/detection_tables.h
rename to engines/made/detection_tables.h
diff --git a/engines/made/made.h b/engines/made/made.h
index 7451978142..3f7007f24e 100644
--- a/engines/made/made.h
+++ b/engines/made/made.h
@@ -24,7 +24,7 @@
 #define MADE_MADE_H
 
 #include "made/sound.h"
-#include "made/detection/detection_enums.h"
+#include "made/detection_enums.h"
 
 #include "engines/engine.h"
 
diff --git a/engines/made/metaengine.cpp b/engines/made/metaengine.cpp
index 53b283e331..cacc7b929e 100644
--- a/engines/made/metaengine.cpp
+++ b/engines/made/metaengine.cpp
@@ -22,7 +22,7 @@
 
 #include "engines/advancedDetector.h"
 #include "made/made.h"
-#include "made/detection/detection.h"
+#include "made/detection.h"
 
 
 namespace Made {
diff --git a/engines/made/module.mk b/engines/made/module.mk
index 075ee141b3..2717b4d3c4 100644
--- a/engines/made/module.mk
+++ b/engines/made/module.mk
@@ -24,3 +24,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mads/detection/detection.cpp b/engines/mads/detection.cpp
similarity index 96%
rename from engines/mads/detection/detection.cpp
rename to engines/mads/detection.cpp
index 6d992c7730..f8c31ab64a 100644
--- a/engines/mads/detection/detection.cpp
+++ b/engines/mads/detection.cpp
@@ -27,8 +27,8 @@
 #include "common/system.h"
 #include "common/translation.h"
 
-#include "mads/detection/detection_enums.h"
-#include "mads/detection/detection.h"
+#include "mads/detection_enums.h"
+#include "mads/detection.h"
 
 static const PlainGameDescriptor MADSGames[] = {
 	{"dragonsphere", "Dragonsphere"},
@@ -47,7 +47,7 @@ static const PlainGameDescriptor MADSGames[] = {
 #define GAMEOPTION_TTS_NARRATOR 	GUIO_GAMEOPTIONS5
 #endif
 
-#include "mads/detection/detection_tables.h"
+#include "mads/detection_tables.h"
 
 static const ADExtraGuiOptionsMap optionsList[] = {
 	{
diff --git a/engines/mads/detection/detection.h b/engines/mads/detection.h
similarity index 100%
rename from engines/mads/detection/detection.h
rename to engines/mads/detection.h
diff --git a/engines/mads/detection/module.mk b/engines/mads/detection/module.mk
deleted file mode 100644
index 8309bf143b..0000000000
--- a/engines/mads/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/mads/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mads/detection/detection_enums.h b/engines/mads/detection_enums.h
similarity index 100%
rename from engines/mads/detection/detection_enums.h
rename to engines/mads/detection_enums.h
diff --git a/engines/mads/detection/detection_tables.h b/engines/mads/detection_tables.h
similarity index 100%
rename from engines/mads/detection/detection_tables.h
rename to engines/mads/detection_tables.h
diff --git a/engines/mads/mads.h b/engines/mads/mads.h
index 7948f03248..9cda26e63a 100644
--- a/engines/mads/mads.h
+++ b/engines/mads/mads.h
@@ -40,7 +40,7 @@
 #include "mads/msurface.h"
 #include "mads/resources.h"
 #include "mads/sound.h"
-#include "mads/detection/detection_enums.h"
+#include "mads/detection_enums.h"
 
 /**
  * This is the namespace of the MADS engine.
diff --git a/engines/mads/metaengine.cpp b/engines/mads/metaengine.cpp
index bf5239716f..9ba6633666 100644
--- a/engines/mads/metaengine.cpp
+++ b/engines/mads/metaengine.cpp
@@ -35,7 +35,7 @@
 
 #include "mads/events.h"
 #include "mads/game.h"
-#include "mads/detection/detection.h"
+#include "mads/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/mads/module.mk b/engines/mads/module.mk
index 9d0eda253d..2093fcb71f 100644
--- a/engines/mads/module.mk
+++ b/engines/mads/module.mk
@@ -68,3 +68,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mohawk/detection/detection.cpp b/engines/mohawk/detection.cpp
similarity index 97%
rename from engines/mohawk/detection/detection.cpp
rename to engines/mohawk/detection.cpp
index 1548cf5d46..d2d6b4f6a0 100644
--- a/engines/mohawk/detection/detection.cpp
+++ b/engines/mohawk/detection.cpp
@@ -27,8 +27,8 @@
 #include "common/textconsole.h"
 #include "common/translation.h"
 
-#include "mohawk/detection/detection.h"
-#include "mohawk/detection/detection_enums.h"
+#include "mohawk/detection.h"
+#include "mohawk/detection_enums.h"
 
 #include "mohawk/riven_metaengine/metaengine.h"
 #include "mohawk/myst_metaengine/metaengine.h"
@@ -65,7 +65,7 @@ static const PlainGameDescriptor mohawkGames[] = {
 	{nullptr, nullptr}
 };
 
-#include "mohawk/detection/detection_tables.h"
+#include "mohawk/detection_tables.h"
 
 static const char *directoryGlobs[] = {
 	"all",
diff --git a/engines/mohawk/detection/detection.h b/engines/mohawk/detection.h
similarity index 100%
rename from engines/mohawk/detection/detection.h
rename to engines/mohawk/detection.h
diff --git a/engines/mohawk/detection/module.mk b/engines/mohawk/detection/module.mk
deleted file mode 100644
index 4f3ca23a28..0000000000
--- a/engines/mohawk/detection/module.mk
+++ /dev/null
@@ -1,15 +0,0 @@
-MODULE := engines/mohawk/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Skip building the following objects if a static
-# module is enabled, because it already has the contents.
-ifneq ($(ENABLE_MOHAWK), STATIC_PLUGIN)
-#ifndef ENABLE_MYST
-DETECT_OBJS += $(MODULE)/../myst_metaengine/metaengine.o
-#endif
-#ifndef ENABLE_RIVEN
-DETECT_OBJS += $(MODULE)/../riven_metaengine/metaengine.o
-#endif
-endif
diff --git a/engines/mohawk/detection/detection_enums.h b/engines/mohawk/detection_enums.h
similarity index 100%
rename from engines/mohawk/detection/detection_enums.h
rename to engines/mohawk/detection_enums.h
diff --git a/engines/mohawk/detection/detection_tables.h b/engines/mohawk/detection_tables.h
similarity index 100%
rename from engines/mohawk/detection/detection_tables.h
rename to engines/mohawk/detection_tables.h
diff --git a/engines/mohawk/metaengine.cpp b/engines/mohawk/metaengine.cpp
index d6f5e68f91..764e2d8c18 100644
--- a/engines/mohawk/metaengine.cpp
+++ b/engines/mohawk/metaengine.cpp
@@ -52,7 +52,7 @@
 #include "mohawk/riven_saveload.h"
 #endif
 
-#include "mohawk/detection/detection.h"
+#include "mohawk/detection.h"
 
 namespace Mohawk {
 
diff --git a/engines/mohawk/module.mk b/engines/mohawk/module.mk
index a09c9c3807..8cafb7c7b3 100644
--- a/engines/mohawk/module.mk
+++ b/engines/mohawk/module.mk
@@ -85,3 +85,13 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_MOHAWK), STATIC_PLUGIN)
+DETECT_OBJS += $(MODULE)/myst_metaengine/metaengine.o
+DETECT_OBJS += $(MODULE)/riven_metaengine/metaengine.o
+endif
diff --git a/engines/mohawk/mohawk.h b/engines/mohawk/mohawk.h
index 7dcf3b15d4..55a0f667f4 100644
--- a/engines/mohawk/mohawk.h
+++ b/engines/mohawk/mohawk.h
@@ -28,7 +28,7 @@
 
 #include "engines/engine.h"
 
-#include "mohawk/detection/detection_enums.h"
+#include "mohawk/detection_enums.h"
 
 class OSystem;
 
diff --git a/engines/mortevielle/detection/detection.cpp b/engines/mortevielle/detection.cpp
similarity index 92%
rename from engines/mortevielle/detection/detection.cpp
rename to engines/mortevielle/detection.cpp
index 36e2574532..a0d85c7ae0 100644
--- a/engines/mortevielle/detection/detection.cpp
+++ b/engines/mortevielle/detection.cpp
@@ -23,15 +23,15 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "mortevielle/detection/detection.h"
-#include "mortevielle/detection/detection_enums.h"
+#include "mortevielle/detection.h"
+#include "mortevielle/detection_enums.h"
 
 static const PlainGameDescriptor MortevielleGame[] = {
 	{"mortevielle", "Mortville Manor"},
 	{0, 0}
 };
 
-#include "mortevielle/detection/detection_tables.h"
+#include "mortevielle/detection_tables.h"
 
 class MortevielleMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/mortevielle/detection/detection.h b/engines/mortevielle/detection.h
similarity index 100%
rename from engines/mortevielle/detection/detection.h
rename to engines/mortevielle/detection.h
diff --git a/engines/mortevielle/detection/module.mk b/engines/mortevielle/detection/module.mk
deleted file mode 100644
index eb10fe101c..0000000000
--- a/engines/mortevielle/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/mortevielle/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mortevielle/detection/detection_enums.h b/engines/mortevielle/detection_enums.h
similarity index 100%
rename from engines/mortevielle/detection/detection_enums.h
rename to engines/mortevielle/detection_enums.h
diff --git a/engines/mortevielle/detection/detection_tables.h b/engines/mortevielle/detection_tables.h
similarity index 100%
rename from engines/mortevielle/detection/detection_tables.h
rename to engines/mortevielle/detection_tables.h
diff --git a/engines/mortevielle/metaengine.cpp b/engines/mortevielle/metaengine.cpp
index a9820bacbd..6bc1e23ef2 100644
--- a/engines/mortevielle/metaengine.cpp
+++ b/engines/mortevielle/metaengine.cpp
@@ -25,7 +25,7 @@
 
 #include "mortevielle/mortevielle.h"
 #include "mortevielle/saveload.h"
-#include "mortevielle/detection/detection.h"
+#include "mortevielle/detection.h"
 
 namespace Mortevielle {
 
diff --git a/engines/mortevielle/module.mk b/engines/mortevielle/module.mk
index 0a1c924920..0c525fefe3 100644
--- a/engines/mortevielle/module.mk
+++ b/engines/mortevielle/module.mk
@@ -21,3 +21,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mortevielle/mortevielle.h b/engines/mortevielle/mortevielle.h
index f1bf9333d7..93872c8f43 100644
--- a/engines/mortevielle/mortevielle.h
+++ b/engines/mortevielle/mortevielle.h
@@ -44,7 +44,7 @@
 #include "mortevielle/saveload.h"
 #include "mortevielle/sound.h"
 #include "mortevielle/outtext.h"
-#include "mortevielle/detection/detection_enums.h"
+#include "mortevielle/detection_enums.h"
 
 namespace Mortevielle {
 
diff --git a/engines/mutationofjb/detection/detection.cpp b/engines/mutationofjb/detection.cpp
similarity index 100%
rename from engines/mutationofjb/detection/detection.cpp
rename to engines/mutationofjb/detection.cpp
diff --git a/engines/mutationofjb/detection/module.mk b/engines/mutationofjb/detection/module.mk
deleted file mode 100644
index f641caa9f3..0000000000
--- a/engines/mutationofjb/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/mutationofjb/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/mutationofjb/module.mk b/engines/mutationofjb/module.mk
index 948a02ad2c..f45acd8db1 100644
--- a/engines/mutationofjb/module.mk
+++ b/engines/mutationofjb/module.mk
@@ -68,3 +68,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/neverhood/detection/detection.cpp b/engines/neverhood/detection.cpp
similarity index 99%
rename from engines/neverhood/detection/detection.cpp
rename to engines/neverhood/detection.cpp
index 4303a39ef0..036b3397a2 100644
--- a/engines/neverhood/detection/detection.cpp
+++ b/engines/neverhood/detection.cpp
@@ -26,7 +26,7 @@
 #include "common/file.h"
 #include "common/translation.h"
 
-#include "neverhood/detection/detection.h"
+#include "neverhood/detection.h"
 
 static const PlainGameDescriptor neverhoodGames[] = {
 	{"neverhood", "The Neverhood Chronicles"},
diff --git a/engines/neverhood/detection/detection.h b/engines/neverhood/detection.h
similarity index 100%
rename from engines/neverhood/detection/detection.h
rename to engines/neverhood/detection.h
diff --git a/engines/neverhood/detection/module.mk b/engines/neverhood/detection/module.mk
deleted file mode 100644
index f5b9e43d80..0000000000
--- a/engines/neverhood/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/neverhood/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/neverhood/metaengine.cpp b/engines/neverhood/metaengine.cpp
index 8b3b1f44cb..239a1955d6 100644
--- a/engines/neverhood/metaengine.cpp
+++ b/engines/neverhood/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "common/translation.h"
 
 #include "neverhood/neverhood.h"
-#include "neverhood/detection/detection.h"
+#include "neverhood/detection.h"
 
 enum NeverhoodGameFeatures {
 	GF_BIG_DEMO = (1 << 0)
diff --git a/engines/neverhood/module.mk b/engines/neverhood/module.mk
index f23f8146ae..2ffef0c3bb 100644
--- a/engines/neverhood/module.mk
+++ b/engines/neverhood/module.mk
@@ -75,3 +75,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/parallaction/detection/detection.cpp b/engines/parallaction/detection.cpp
similarity index 98%
rename from engines/parallaction/detection/detection.cpp
rename to engines/parallaction/detection.cpp
index ad1462260b..0ca0dfc7aa 100644
--- a/engines/parallaction/detection/detection.cpp
+++ b/engines/parallaction/detection.cpp
@@ -27,8 +27,8 @@
 #include "common/system.h"
 #include "common/textconsole.h"
 
-#include "parallaction/detection/detection_enums.h"
-#include "parallaction/detection/detection.h"
+#include "parallaction/detection_enums.h"
+#include "parallaction/detection.h"
 
 static const PlainGameDescriptor parallactionGames[] = {
 	{"nippon", "Nippon Safes Inc."},
diff --git a/engines/parallaction/detection/detection.h b/engines/parallaction/detection.h
similarity index 100%
rename from engines/parallaction/detection/detection.h
rename to engines/parallaction/detection.h
diff --git a/engines/parallaction/detection/module.mk b/engines/parallaction/detection/module.mk
deleted file mode 100644
index ce4c2ad427..0000000000
--- a/engines/parallaction/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/parallaction/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/parallaction/detection/detection_enums.h b/engines/parallaction/detection_enums.h
similarity index 100%
rename from engines/parallaction/detection/detection_enums.h
rename to engines/parallaction/detection_enums.h
diff --git a/engines/parallaction/metaengine.cpp b/engines/parallaction/metaengine.cpp
index 41be04b0e0..42ec7d6520 100644
--- a/engines/parallaction/metaengine.cpp
+++ b/engines/parallaction/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "common/textconsole.h"
 
 #include "parallaction/parallaction.h"
-#include "parallaction/detection/detection.h"
+#include "parallaction/detection.h"
 
 namespace Parallaction {
 
diff --git a/engines/parallaction/module.mk b/engines/parallaction/module.mk
index 7dba9f9a2b..3ad5b48b05 100644
--- a/engines/parallaction/module.mk
+++ b/engines/parallaction/module.mk
@@ -41,3 +41,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/parallaction/parallaction.h b/engines/parallaction/parallaction.h
index 54ccf06241..ed907fc4b4 100644
--- a/engines/parallaction/parallaction.h
+++ b/engines/parallaction/parallaction.h
@@ -37,7 +37,7 @@
 #include "parallaction/inventory.h"
 #include "parallaction/objects.h"
 #include "parallaction/disk.h"
-#include "parallaction/detection/detection_enums.h"
+#include "parallaction/detection_enums.h"
 
 #define PATH_LEN	200
 
diff --git a/engines/pegasus/detection/detection.cpp b/engines/pegasus/detection.cpp
similarity index 97%
rename from engines/pegasus/detection/detection.cpp
rename to engines/pegasus/detection.cpp
index e0728f812b..035527230e 100644
--- a/engines/pegasus/detection/detection.cpp
+++ b/engines/pegasus/detection.cpp
@@ -26,8 +26,8 @@
 #include "common/config-manager.h"
 #include "common/file.h"
 
-#include "pegasus/detection/detection_enums.h"
-#include "pegasus/detection/detection.h"
+#include "pegasus/detection_enums.h"
+#include "pegasus/detection.h"
 
 static const PlainGameDescriptor pegasusGames[] = {
 	{"pegasus", "The Journeyman Project: Pegasus Prime"},
diff --git a/engines/pegasus/detection/detection.h b/engines/pegasus/detection.h
similarity index 100%
rename from engines/pegasus/detection/detection.h
rename to engines/pegasus/detection.h
diff --git a/engines/pegasus/detection/module.mk b/engines/pegasus/detection/module.mk
deleted file mode 100644
index 8b554b5929..0000000000
--- a/engines/pegasus/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/pegasus/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/pegasus/detection/detection_enums.h b/engines/pegasus/detection_enums.h
similarity index 100%
rename from engines/pegasus/detection/detection_enums.h
rename to engines/pegasus/detection_enums.h
diff --git a/engines/pegasus/metaengine.cpp b/engines/pegasus/metaengine.cpp
index 16840b4e1c..e0b780fb6b 100644
--- a/engines/pegasus/metaengine.cpp
+++ b/engines/pegasus/metaengine.cpp
@@ -28,8 +28,8 @@
 #include "common/savefile.h"
 
 #include "pegasus/pegasus.h"
-#include "pegasus/detection/detection_enums.h"
-#include "pegasus/detection/detection.h"
+#include "pegasus/detection_enums.h"
+#include "pegasus/detection.h"
 
 namespace Pegasus {
 
diff --git a/engines/pegasus/module.mk b/engines/pegasus/module.mk
index 39481cb665..1fe1963f32 100644
--- a/engines/pegasus/module.mk
+++ b/engines/pegasus/module.mk
@@ -99,3 +99,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/petka/detection/detection.cpp b/engines/petka/detection.cpp
similarity index 97%
rename from engines/petka/detection/detection.cpp
rename to engines/petka/detection.cpp
index 57954a37ee..ee2db73a33 100644
--- a/engines/petka/detection/detection.cpp
+++ b/engines/petka/detection.cpp
@@ -31,7 +31,7 @@ static const PlainGameDescriptor petkaGames[] = {
 	{0, 0}
 };
 
-#include "petka/detection/detection_tables.h"
+#include "petka/detection_tables.h"
 
 class PetkaMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/petka/detection/module.mk b/engines/petka/detection/module.mk
deleted file mode 100644
index 99ab6a67ac..0000000000
--- a/engines/petka/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/petka/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/petka/detection/detection_tables.h b/engines/petka/detection_tables.h
similarity index 100%
rename from engines/petka/detection/detection_tables.h
rename to engines/petka/detection_tables.h
diff --git a/engines/petka/module.mk b/engines/petka/module.mk
index 44d74c22c7..7bcbb03ef3 100644
--- a/engines/petka/module.mk
+++ b/engines/petka/module.mk
@@ -35,3 +35,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/pink/detection/detection.cpp b/engines/pink/detection.cpp
similarity index 97%
rename from engines/pink/detection/detection.cpp
rename to engines/pink/detection.cpp
index ad21dead52..c6ffafa324 100644
--- a/engines/pink/detection/detection.cpp
+++ b/engines/pink/detection.cpp
@@ -30,7 +30,7 @@ static const PlainGameDescriptor pinkGames[] = {
 	{0, 0}
 };
 
-#include "pink/detection/detection_tables.h"
+#include "pink/detection_tables.h"
 
 static const char *directoryGlobs[] = {
 	"install",
diff --git a/engines/pink/detection/module.mk b/engines/pink/detection/module.mk
deleted file mode 100644
index 26585ca263..0000000000
--- a/engines/pink/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/pink/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/pink/detection/detection_tables.h b/engines/pink/detection_tables.h
similarity index 100%
rename from engines/pink/detection/detection_tables.h
rename to engines/pink/detection_tables.h
diff --git a/engines/pink/module.mk b/engines/pink/module.mk
index db758c2719..bc85597e2c 100644
--- a/engines/pink/module.mk
+++ b/engines/pink/module.mk
@@ -57,3 +57,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/plumbers/detection/detection.cpp b/engines/plumbers/detection.cpp
similarity index 100%
rename from engines/plumbers/detection/detection.cpp
rename to engines/plumbers/detection.cpp
diff --git a/engines/plumbers/detection/module.mk b/engines/plumbers/detection/module.mk
deleted file mode 100644
index aa4c34686b..0000000000
--- a/engines/plumbers/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/plumbers/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/plumbers/module.mk b/engines/plumbers/module.mk
index 02dbcdf579..63fde172d3 100644
--- a/engines/plumbers/module.mk
+++ b/engines/plumbers/module.mk
@@ -12,3 +12,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/prince/detection/detection.cpp b/engines/prince/detection.cpp
similarity index 97%
rename from engines/prince/detection/detection.cpp
rename to engines/prince/detection.cpp
index 65ed046302..f0f9b5984c 100644
--- a/engines/prince/detection/detection.cpp
+++ b/engines/prince/detection.cpp
@@ -22,8 +22,8 @@
 
 #include "engines/advancedDetector.h"
 
-#include "prince/detection/detection_enums.h"
-#include "prince/detection/detection.h"
+#include "prince/detection_enums.h"
+#include "prince/detection.h"
 
 static const PlainGameDescriptor princeGames[] = {
 	{"prince", "The Prince and the Coward"},
diff --git a/engines/prince/detection/detection.h b/engines/prince/detection.h
similarity index 100%
rename from engines/prince/detection/detection.h
rename to engines/prince/detection.h
diff --git a/engines/prince/detection/module.mk b/engines/prince/detection/module.mk
deleted file mode 100644
index 9d9d472db4..0000000000
--- a/engines/prince/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/prince/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/prince/detection/detection_enums.h b/engines/prince/detection_enums.h
similarity index 100%
rename from engines/prince/detection/detection_enums.h
rename to engines/prince/detection_enums.h
diff --git a/engines/prince/metaengine.cpp b/engines/prince/metaengine.cpp
index 1e82802bd1..23ea7e7667 100644
--- a/engines/prince/metaengine.cpp
+++ b/engines/prince/metaengine.cpp
@@ -22,7 +22,7 @@
 
 #include "engines/advancedDetector.h"
 #include "prince/prince.h"
-#include "prince/detection/detection.h"
+#include "prince/detection.h"
 
 namespace Prince {
 
diff --git a/engines/prince/module.mk b/engines/prince/module.mk
index bd93e08a98..0bca0ab5b0 100644
--- a/engines/prince/module.mk
+++ b/engines/prince/module.mk
@@ -34,3 +34,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/prince/prince.h b/engines/prince/prince.h
index e58759b959..bbcb97edaa 100644
--- a/engines/prince/prince.h
+++ b/engines/prince/prince.h
@@ -48,7 +48,7 @@
 #include "prince/mob.h"
 #include "prince/object.h"
 #include "prince/pscr.h"
-#include "prince/detection/detection_enums.h"
+#include "prince/detection_enums.h"
 
 namespace Prince {
 
diff --git a/engines/queen/detection/detection.cpp b/engines/queen/detection.cpp
similarity index 99%
rename from engines/queen/detection/detection.cpp
rename to engines/queen/detection.cpp
index 9ca6f71b4a..ccafc68a47 100644
--- a/engines/queen/detection/detection.cpp
+++ b/engines/queen/detection.cpp
@@ -28,7 +28,7 @@
 #include "common/file.h"
 #include "common/translation.h"
 
-#include "queen/detection/detection.h"
+#include "queen/detection.h"
 #include "queen/resource.h"
 
 static const PlainGameDescriptor queenGames[] = {
diff --git a/engines/queen/detection/detection.h b/engines/queen/detection.h
similarity index 100%
rename from engines/queen/detection/detection.h
rename to engines/queen/detection.h
diff --git a/engines/queen/detection/module.mk b/engines/queen/detection/module.mk
deleted file mode 100644
index 57e44e76dc..0000000000
--- a/engines/queen/detection/module.mk
+++ /dev/null
@@ -1,12 +0,0 @@
-MODULE := engines/queen/detection
-
-# Detection objecs
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Skip building the following objects if a static
-# module is enabled, because it already has the contents.
-ifneq ($(ENABLE_QUEEN), STATIC_PLUGIN)
-# External dependencies for detection.
-DETECT_OBJS += $(MODULE)/../resource.o
-DETECT_OBJS += $(MODULE)/../restables.o
-endif
diff --git a/engines/queen/metaengine.cpp b/engines/queen/metaengine.cpp
index 1b0803f10b..8cdbbecda3 100644
--- a/engines/queen/metaengine.cpp
+++ b/engines/queen/metaengine.cpp
@@ -27,7 +27,7 @@
 
 #include "queen/queen.h"
 #include "queen/resource.h"
-#include "queen/detection/detection.h"
+#include "queen/detection.h"
 
 class QueenMetaEngineConnect : public AdvancedMetaEngineConnect {
 public:
diff --git a/engines/queen/module.mk b/engines/queen/module.mk
index 7e504c587f..efb4bb4a80 100644
--- a/engines/queen/module.mk
+++ b/engines/queen/module.mk
@@ -31,3 +31,14 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objecs
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_QUEEN), STATIC_PLUGIN)
+# External dependencies for detection.
+DETECT_OBJS += $(MODULE)/resource.o
+DETECT_OBJS += $(MODULE)/restables.o
+endif
\ No newline at end of file
diff --git a/engines/saga/detection/detection.cpp b/engines/saga/detection.cpp
similarity index 94%
rename from engines/saga/detection/detection.cpp
rename to engines/saga/detection.cpp
index c74f93be17..e58d6689b1 100644
--- a/engines/saga/detection/detection.cpp
+++ b/engines/saga/detection.cpp
@@ -25,8 +25,8 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "saga/detection/detection_enums.h"
-#include "saga/detection/detection.h"
+#include "saga/detection_enums.h"
+#include "saga/detection.h"
 
 static const PlainGameDescriptor sagaGames[] = {
 	{"ite", "Inherit the Earth: Quest for the Orb"},
@@ -36,7 +36,7 @@ static const PlainGameDescriptor sagaGames[] = {
 	{0, 0}
 };
 
-#include "saga/detection/detection_tables.h"
+#include "saga/detection_tables.h"
 
 class SagaMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/saga/detection/detection.h b/engines/saga/detection.h
similarity index 100%
rename from engines/saga/detection/detection.h
rename to engines/saga/detection.h
diff --git a/engines/saga/detection/module.mk b/engines/saga/detection/module.mk
deleted file mode 100644
index 4f32d52de5..0000000000
--- a/engines/saga/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/saga/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/saga/detection/detection_enums.h b/engines/saga/detection_enums.h
similarity index 100%
rename from engines/saga/detection/detection_enums.h
rename to engines/saga/detection_enums.h
diff --git a/engines/saga/detection/detection_tables.h b/engines/saga/detection_tables.h
similarity index 100%
rename from engines/saga/detection/detection_tables.h
rename to engines/saga/detection_tables.h
diff --git a/engines/saga/metaengine.cpp b/engines/saga/metaengine.cpp
index 1a477c7e2f..43d8b6bceb 100644
--- a/engines/saga/metaengine.cpp
+++ b/engines/saga/metaengine.cpp
@@ -37,7 +37,7 @@
 #include "saga/resource.h"
 #include "saga/interface.h"
 #include "saga/scene.h"
-#include "saga/detection/detection.h"
+#include "saga/detection.h"
 
 namespace Saga {
 
diff --git a/engines/saga/module.mk b/engines/saga/module.mk
index b4721ca605..07af31efc0 100644
--- a/engines/saga/module.mk
+++ b/engines/saga/module.mk
@@ -55,3 +55,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/saga/saga.h b/engines/saga/saga.h
index cbe58b691b..59a8ecf202 100644
--- a/engines/saga/saga.h
+++ b/engines/saga/saga.h
@@ -31,7 +31,7 @@
 #include "common/textconsole.h"
 
 #include "saga/gfx.h"
-#include "saga/detection/detection_enums.h"
+#include "saga/detection_enums.h"
 
 struct ADGameFileDescription;
 
diff --git a/engines/sci/detection/detection.cpp b/engines/sci/detection.cpp
similarity index 99%
rename from engines/sci/detection/detection.cpp
rename to engines/sci/detection.cpp
index ae445defb5..667c2d3176 100644
--- a/engines/sci/detection/detection.cpp
+++ b/engines/sci/detection.cpp
@@ -31,8 +31,8 @@
 #include "gui/widget.h"
 #include "gui/widgets/popup.h"
 
-#include "sci/detection/detection_enums.h"
-#include "sci/detection/detection_defines.h"
+#include "sci/detection_enums.h"
+#include "sci/detection_defines.h"
 #include "sci/graphics/helpers_detection_enums.h"
 
 namespace Sci {
@@ -133,7 +133,7 @@ static const PlainGameDescriptor s_sciGameTitles[] = {
 
 } // End of namespace Sci
 
-#include "sci/detection/detection_tables.h"
+#include "sci/detection_tables.h"
 
 namespace Sci {
 
diff --git a/engines/sci/detection/module.mk b/engines/sci/detection/module.mk
deleted file mode 100644
index 26de2b20f0..0000000000
--- a/engines/sci/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/sci/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sci/detection/detection_defines.h b/engines/sci/detection_defines.h
similarity index 100%
rename from engines/sci/detection/detection_defines.h
rename to engines/sci/detection_defines.h
diff --git a/engines/sci/detection/detection_enums.h b/engines/sci/detection_enums.h
similarity index 100%
rename from engines/sci/detection/detection_enums.h
rename to engines/sci/detection_enums.h
diff --git a/engines/sci/detection/detection_tables.h b/engines/sci/detection_tables.h
similarity index 100%
rename from engines/sci/detection/detection_tables.h
rename to engines/sci/detection_tables.h
diff --git a/engines/sci/module.mk b/engines/sci/module.mk
index 8ec7ea5714..4e2724cede 100644
--- a/engines/sci/module.mk
+++ b/engines/sci/module.mk
@@ -113,3 +113,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sci/sci.h b/engines/sci/sci.h
index 144700e1a8..7ea28b38f7 100644
--- a/engines/sci/sci.h
+++ b/engines/sci/sci.h
@@ -29,8 +29,8 @@
 #include "common/random.h"
 #include "sci/engine/vm_types.h"	// for Selector
 #include "sci/debug.h"	// for DebugState
-#include "sci/detection/detection_enums.h" // for shared enums between detection/engine
-#include "sci/detection/detection_defines.h" // for shared defines between detection/engine
+#include "sci/detection_enums.h" // for shared enums between detection/engine
+#include "sci/detection_defines.h" // for shared defines between detection/engine
 
 struct ADGameDescription;
 
diff --git a/engines/scumm/detection/detection.cpp b/engines/scumm/detection.cpp
similarity index 97%
rename from engines/scumm/detection/detection.cpp
rename to engines/scumm/detection.cpp
index ca36ad094e..0b316898b7 100644
--- a/engines/scumm/detection/detection.cpp
+++ b/engines/scumm/detection.cpp
@@ -33,8 +33,8 @@
 
 #include "audio/mididrv.h"
 
-#include "scumm/detection/detection.h"
-#include "scumm/detection/detection_tables.h"
+#include "scumm/detection.h"
+#include "scumm/detection_tables.h"
 #include "scumm/file.h"
 #include "scumm/file_nes.h"
 
@@ -44,7 +44,7 @@
 
 
 // Various methods to help in core detection.
-#include "scumm/detection/detection_internal.h"
+#include "scumm/detection_internal.h"
 
 
 #pragma mark -
diff --git a/engines/scumm/detection/detection.h b/engines/scumm/detection.h
similarity index 100%
rename from engines/scumm/detection/detection.h
rename to engines/scumm/detection.h
diff --git a/engines/scumm/detection/module.mk b/engines/scumm/detection/module.mk
deleted file mode 100644
index e8ee8168b2..0000000000
--- a/engines/scumm/detection/module.mk
+++ /dev/null
@@ -1,11 +0,0 @@
-MODULE := engines/scumm/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
-
-# Skip building the following objects if a static
-# module is enabled, because it already has the contents.
-ifneq ($(ENABLE_SCUMM), STATIC_PLUGIN)
-DETECT_OBJS += $(MODULE)/../file.o
-DETECT_OBJS += $(MODULE)/../file_nes.o
-endif
diff --git a/engines/scumm/detection/detection_internal.h b/engines/scumm/detection_internal.h
similarity index 99%
rename from engines/scumm/detection/detection_internal.h
rename to engines/scumm/detection_internal.h
index 2baf3a0021..8e6c1116c3 100644
--- a/engines/scumm/detection/detection_internal.h
+++ b/engines/scumm/detection_internal.h
@@ -26,7 +26,7 @@
 // Includes some shared functionalities, which is required by multiple TU's.
 // Mark it as static in the header, so visibility for function is limited by the TU, and we can use it whereever required.
 // This is being done, because it's necessary in detection, creating an instance, as well as in initiliasing the ScummEngine.
-#include "scumm/detection/detection_steam.h"
+#include "scumm/detection_steam.h"
 
 namespace Scumm {
 
diff --git a/engines/scumm/detection/detection_steam.h b/engines/scumm/detection_steam.h
similarity index 100%
rename from engines/scumm/detection/detection_steam.h
rename to engines/scumm/detection_steam.h
diff --git a/engines/scumm/detection/detection_tables.h b/engines/scumm/detection_tables.h
similarity index 99%
rename from engines/scumm/detection/detection_tables.h
rename to engines/scumm/detection_tables.h
index ed057bb1c5..50bc9755ff 100644
--- a/engines/scumm/detection/detection_tables.h
+++ b/engines/scumm/detection_tables.h
@@ -28,7 +28,7 @@
 #include "common/rect.h"
 #include "common/util.h"
 
-#include "scumm/detection/detection.h"
+#include "scumm/detection.h"
 #include "scumm/scumm.h"
 
 #include "scumm/scumm-md5.h"
diff --git a/engines/scumm/file.h b/engines/scumm/file.h
index feacfbe65f..e367190d2d 100644
--- a/engines/scumm/file.h
+++ b/engines/scumm/file.h
@@ -26,7 +26,7 @@
 #include "common/file.h"
 #include "common/stream.h"
 
-#include "scumm/detection/detection.h"
+#include "scumm/detection.h"
 
 namespace Scumm {
 
diff --git a/engines/scumm/metaengine.cpp b/engines/scumm/metaengine.cpp
index bbcb0a66f5..18a76618d1 100644
--- a/engines/scumm/metaengine.cpp
+++ b/engines/scumm/metaengine.cpp
@@ -37,8 +37,8 @@
 
 // Files related for detection.
 #include "scumm/metaengine.h"
-#include "scumm/detection/detection.h"
-#include "scumm/detection/detection_tables.h"
+#include "scumm/detection.h"
+#include "scumm/detection_tables.h"
 #include "scumm/file.h"
 #include "scumm/file_nes.h"
 
@@ -206,7 +206,7 @@ bool ScummEngine::isMacM68kIMuse() const {
 
 
 // Various methods to help in core detection.
-#include "scumm/detection/detection_internal.h"
+#include "scumm/detection_internal.h"
 
 
 #pragma mark -
diff --git a/engines/scumm/module.mk b/engines/scumm/module.mk
index da4c0e4c0d..8f82add778 100644
--- a/engines/scumm/module.mk
+++ b/engines/scumm/module.mk
@@ -168,3 +168,13 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
+
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_SCUMM), STATIC_PLUGIN)
+DETECT_OBJS += $(MODULE)/file.o
+DETECT_OBJS += $(MODULE)/file_nes.o
+endif
diff --git a/engines/scumm/scumm.cpp b/engines/scumm/scumm.cpp
index 1cffbf1edc..6bc433fa51 100644
--- a/engines/scumm/scumm.cpp
+++ b/engines/scumm/scumm.cpp
@@ -80,7 +80,7 @@
 #include "scumm/imuse/drivers/mac_m68k.h"
 #include "scumm/imuse/drivers/amiga.h"
 #include "scumm/imuse/drivers/fmtowns.h"
-#include "scumm/detection/detection_steam.h"
+#include "scumm/detection_steam.h"
 
 #include "backends/audiocd/audiocd.h"
 
diff --git a/engines/scumm/scumm.h b/engines/scumm/scumm.h
index 1a9f03f723..550ae0f6b1 100644
--- a/engines/scumm/scumm.h
+++ b/engines/scumm/scumm.h
@@ -40,7 +40,7 @@
 #include "graphics/sjis.h"
 
 #include "scumm/gfx.h"
-#include "scumm/detection/detection.h"
+#include "scumm/detection.h"
 #include "scumm/script.h"
 
 #ifdef __DS__
diff --git a/engines/sherlock/detection/detection.cpp b/engines/sherlock/detection.cpp
similarity index 96%
rename from engines/sherlock/detection/detection.cpp
rename to engines/sherlock/detection.cpp
index 40fc76a3b0..2454b54899 100644
--- a/engines/sherlock/detection/detection.cpp
+++ b/engines/sherlock/detection.cpp
@@ -23,8 +23,8 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "sherlock/detection/detection_enums.h"
-#include "sherlock/detection/detection.h"
+#include "sherlock/detection_enums.h"
+#include "sherlock/detection.h"
 
 static const PlainGameDescriptor sherlockGames[] = {
 	{ "scalpel", "The Case of the Serrated Scalpel" },
@@ -120,7 +120,7 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 };
 
 
-#include "sherlock/detection/detection_tables.h"
+#include "sherlock/detection_tables.h"
 
 class SherlockMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/sherlock/detection/detection.h b/engines/sherlock/detection.h
similarity index 100%
rename from engines/sherlock/detection/detection.h
rename to engines/sherlock/detection.h
diff --git a/engines/sherlock/detection/module.mk b/engines/sherlock/detection/module.mk
deleted file mode 100644
index 2290606a55..0000000000
--- a/engines/sherlock/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/sherlock/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sherlock/detection/detection_enums.h b/engines/sherlock/detection_enums.h
similarity index 100%
rename from engines/sherlock/detection/detection_enums.h
rename to engines/sherlock/detection_enums.h
diff --git a/engines/sherlock/detection/detection_tables.h b/engines/sherlock/detection_tables.h
similarity index 100%
rename from engines/sherlock/detection/detection_tables.h
rename to engines/sherlock/detection_tables.h
diff --git a/engines/sherlock/metaengine.cpp b/engines/sherlock/metaengine.cpp
index 3167b697ec..e5fa0f1ea6 100644
--- a/engines/sherlock/metaengine.cpp
+++ b/engines/sherlock/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "sherlock/detection/detection.h"
+#include "sherlock/detection.h"
 
 namespace Sherlock {
 
diff --git a/engines/sherlock/module.mk b/engines/sherlock/module.mk
index 9a8b35c722..265053a080 100644
--- a/engines/sherlock/module.mk
+++ b/engines/sherlock/module.mk
@@ -77,3 +77,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sherlock/sherlock.h b/engines/sherlock/sherlock.h
index 4c7a19f6a5..06a28af8bb 100644
--- a/engines/sherlock/sherlock.h
+++ b/engines/sherlock/sherlock.h
@@ -50,7 +50,7 @@
 #include "sherlock/sound.h"
 #include "sherlock/talk.h"
 #include "sherlock/user_interface.h"
-#include "sherlock/detection/detection_enums.h"
+#include "sherlock/detection_enums.h"
 
 namespace Sherlock {
 
diff --git a/engines/sky/detection/detection.cpp b/engines/sky/detection.cpp
similarity index 100%
rename from engines/sky/detection/detection.cpp
rename to engines/sky/detection.cpp
diff --git a/engines/sky/detection/module.mk b/engines/sky/detection/module.mk
deleted file mode 100644
index 77bae631c1..0000000000
--- a/engines/sky/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/sky/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sky/module.mk b/engines/sky/module.mk
index 2a9a12c92b..4dd4d20b0b 100644
--- a/engines/sky/module.mk
+++ b/engines/sky/module.mk
@@ -31,3 +31,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sludge/detection/detection.cpp b/engines/sludge/detection.cpp
similarity index 98%
rename from engines/sludge/detection/detection.cpp
rename to engines/sludge/detection.cpp
index aecb0688fe..8ab37da31c 100644
--- a/engines/sludge/detection/detection.cpp
+++ b/engines/sludge/detection.cpp
@@ -25,7 +25,7 @@
 
 #include "engines/advancedDetector.h"
 
-#include "sludge/detection/detection.h"
+#include "sludge/detection.h"
 
 static const PlainGameDescriptor sludgeGames[] = {
 	{ "sludge",			"Sludge Game" },
@@ -47,7 +47,7 @@ static const PlainGameDescriptor sludgeGames[] = {
 	{ 0, 0 }
 };
 
-#include "sludge/detection/detection_tables.h"
+#include "sludge/detection_tables.h"
 
 static Sludge::SludgeGameDescription s_fallbackDesc =
 {
diff --git a/engines/sludge/detection/detection.h b/engines/sludge/detection.h
similarity index 100%
rename from engines/sludge/detection/detection.h
rename to engines/sludge/detection.h
diff --git a/engines/sludge/detection/module.mk b/engines/sludge/detection/module.mk
deleted file mode 100644
index c0177ea565..0000000000
--- a/engines/sludge/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/sludge/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sludge/detection/detection_tables.h b/engines/sludge/detection_tables.h
similarity index 100%
rename from engines/sludge/detection/detection_tables.h
rename to engines/sludge/detection_tables.h
diff --git a/engines/sludge/metaengine.cpp b/engines/sludge/metaengine.cpp
index 2ea4d4eda3..96385daea5 100644
--- a/engines/sludge/metaengine.cpp
+++ b/engines/sludge/metaengine.cpp
@@ -26,7 +26,7 @@
 #include "engines/advancedDetector.h"
 
 #include "sludge/sludge.h"
-#include "sludge/detection/detection.h"
+#include "sludge/detection.h"
 
 namespace Sludge {
 
diff --git a/engines/sludge/module.mk b/engines/sludge/module.mk
index accc922643..19435b559d 100644
--- a/engines/sludge/module.mk
+++ b/engines/sludge/module.mk
@@ -50,3 +50,6 @@ endif
  
 # Include common rules 
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/startrek/detection/detection.cpp b/engines/startrek/detection.cpp
similarity index 98%
rename from engines/startrek/detection/detection.cpp
rename to engines/startrek/detection.cpp
index 6121bd1194..26480182a3 100644
--- a/engines/startrek/detection/detection.cpp
+++ b/engines/startrek/detection.cpp
@@ -27,8 +27,8 @@
 #include "common/config-manager.h"
 #include "common/file.h"
 
-#include "startrek/detection/detection.h"
-#include "startrek/detection/detection_enums.h"
+#include "startrek/detection.h"
+#include "startrek/detection_enums.h"
 
 static const PlainGameDescriptor starTrekGames[] = {
 	{"st25", "Star Trek: 25th Anniversary"},
diff --git a/engines/startrek/detection/detection.h b/engines/startrek/detection.h
similarity index 100%
rename from engines/startrek/detection/detection.h
rename to engines/startrek/detection.h
diff --git a/engines/startrek/detection/module.mk b/engines/startrek/detection/module.mk
deleted file mode 100644
index c258375e84..0000000000
--- a/engines/startrek/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/startrek/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/startrek/detection/detection_enums.h b/engines/startrek/detection_enums.h
similarity index 100%
rename from engines/startrek/detection/detection_enums.h
rename to engines/startrek/detection_enums.h
diff --git a/engines/startrek/metaengine.cpp b/engines/startrek/metaengine.cpp
index 9bc75174af..f7c5007a62 100644
--- a/engines/startrek/metaengine.cpp
+++ b/engines/startrek/metaengine.cpp
@@ -32,7 +32,7 @@
 
 #include "startrek/startrek.h"
 
-#include "startrek/detection/detection.h"
+#include "startrek/detection.h"
 
 namespace StarTrek {
 
diff --git a/engines/startrek/module.mk b/engines/startrek/module.mk
index 922ffa2edf..b169b15fef 100644
--- a/engines/startrek/module.mk
+++ b/engines/startrek/module.mk
@@ -88,3 +88,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/startrek/startrek.h b/engines/startrek/startrek.h
index f3d59fa3db..804878da59 100644
--- a/engines/startrek/startrek.h
+++ b/engines/startrek/startrek.h
@@ -48,7 +48,7 @@
 #include "startrek/object.h"
 #include "startrek/sound.h"
 #include "startrek/space.h"
-#include "startrek/detection/detection_enums.h"
+#include "startrek/detection_enums.h"
 
 
 using Common::SharedPtr;
diff --git a/engines/supernova/detection/detection.cpp b/engines/supernova/detection.cpp
similarity index 100%
rename from engines/supernova/detection/detection.cpp
rename to engines/supernova/detection.cpp
diff --git a/engines/supernova/detection/module.mk b/engines/supernova/detection/module.mk
deleted file mode 100644
index 6300f2866d..0000000000
--- a/engines/supernova/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/supernova/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/supernova/module.mk b/engines/supernova/module.mk
index 311f87aa38..22db249658 100644
--- a/engines/supernova/module.mk
+++ b/engines/supernova/module.mk
@@ -25,3 +25,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword1/detection/detection.cpp b/engines/sword1/detection.cpp
similarity index 100%
rename from engines/sword1/detection/detection.cpp
rename to engines/sword1/detection.cpp
diff --git a/engines/sword1/detection/module.mk b/engines/sword1/detection/module.mk
deleted file mode 100644
index f11dba72dc..0000000000
--- a/engines/sword1/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/sword1/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword1/module.mk b/engines/sword1/module.mk
index 143cb20a0b..a2b38fc75a 100644
--- a/engines/sword1/module.mk
+++ b/engines/sword1/module.mk
@@ -28,3 +28,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword2/detection/detection.cpp b/engines/sword2/detection.cpp
similarity index 97%
rename from engines/sword2/detection/detection.cpp
rename to engines/sword2/detection.cpp
index 1fd9547d96..c7b7134155 100644
--- a/engines/sword2/detection/detection.cpp
+++ b/engines/sword2/detection.cpp
@@ -26,8 +26,8 @@
 
 #include "engines/metaengine.h"
 
-#include "sword2/detection/detection_enums.h"
-#include "sword2/detection/detection_internal.h"
+#include "sword2/detection_enums.h"
+#include "sword2/detection_internal.h"
 
 static const ExtraGuiOption sword2ExtraGuiOption = {
 	_s("Show object labels"),
diff --git a/engines/sword2/detection/module.mk b/engines/sword2/detection/module.mk
deleted file mode 100644
index 8217bc1a33..0000000000
--- a/engines/sword2/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/sword2/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword2/detection/detection_enums.h b/engines/sword2/detection_enums.h
similarity index 100%
rename from engines/sword2/detection/detection_enums.h
rename to engines/sword2/detection_enums.h
diff --git a/engines/sword2/detection/detection_internal.h b/engines/sword2/detection_internal.h
similarity index 98%
rename from engines/sword2/detection/detection_internal.h
rename to engines/sword2/detection_internal.h
index 9ba2769c77..02861d6fb0 100644
--- a/engines/sword2/detection/detection_internal.h
+++ b/engines/sword2/detection_internal.h
@@ -27,7 +27,7 @@
 
 #include "engines/metaengine.h"
 #include "common/gui_options.h"
-#include "sword2/detection/detection_enums.h"
+#include "sword2/detection_enums.h"
 
 /**
  * The contents of this file are helpful in detecting games, 
diff --git a/engines/sword2/metaengine.cpp b/engines/sword2/metaengine.cpp
index 5d1000dc48..cee3d1011e 100644
--- a/engines/sword2/metaengine.cpp
+++ b/engines/sword2/metaengine.cpp
@@ -34,7 +34,7 @@
 
 #include "sword2/sword2.h"
 #include "sword2/saveload.h"
-#include "sword2/detection/detection_internal.h"
+#include "sword2/detection_internal.h"
 
 class Sword2MetaEngineConnect : public MetaEngineConnect {
 public:
diff --git a/engines/sword2/module.mk b/engines/sword2/module.mk
index 613a95c794..a7d3255788 100644
--- a/engines/sword2/module.mk
+++ b/engines/sword2/module.mk
@@ -42,3 +42,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword2/sword2.h b/engines/sword2/sword2.h
index 241d6088a1..044f0d4032 100644
--- a/engines/sword2/sword2.h
+++ b/engines/sword2/sword2.h
@@ -39,7 +39,7 @@
 #include "common/events.h"
 #include "common/util.h"
 #include "common/random.h"
-#include "sword2/detection/detection_enums.h"
+#include "sword2/detection_enums.h"
 
 #define	MAX_starts	100
 #define	MAX_description	100
diff --git a/engines/sword25/detection/detection.cpp b/engines/sword25/detection.cpp
similarity index 96%
rename from engines/sword25/detection/detection.cpp
rename to engines/sword25/detection.cpp
index b4e07a2d39..7825fa9977 100644
--- a/engines/sword25/detection/detection.cpp
+++ b/engines/sword25/detection.cpp
@@ -24,8 +24,8 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "sword25/detection/detection_enums.h"
-#include "sword25/detection/detection_tables.h"
+#include "sword25/detection_enums.h"
+#include "sword25/detection_tables.h"
 
 static const PlainGameDescriptor sword25Game[] = {
 	{"sword25", "Broken Sword 2.5"},
diff --git a/engines/sword25/detection/module.mk b/engines/sword25/detection/module.mk
deleted file mode 100644
index 598c9008a3..0000000000
--- a/engines/sword25/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/sword25/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword25/detection/detection_enums.h b/engines/sword25/detection_enums.h
similarity index 100%
rename from engines/sword25/detection/detection_enums.h
rename to engines/sword25/detection_enums.h
diff --git a/engines/sword25/detection/detection_tables.h b/engines/sword25/detection_tables.h
similarity index 100%
rename from engines/sword25/detection/detection_tables.h
rename to engines/sword25/detection_tables.h
diff --git a/engines/sword25/module.mk b/engines/sword25/module.mk
index 28f224dafd..def48b42ad 100644
--- a/engines/sword25/module.mk
+++ b/engines/sword25/module.mk
@@ -62,3 +62,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/sword25/sword25.h b/engines/sword25/sword25.h
index e4bad15d86..ead4c28fcf 100644
--- a/engines/sword25/sword25.h
+++ b/engines/sword25/sword25.h
@@ -27,7 +27,7 @@
 #include "engines/engine.h"
 
 #include "sword25/console.h"
-#include "sword25/detection/detection_enums.h"
+#include "sword25/detection_enums.h"
 
 namespace Common {
 class Error;
diff --git a/engines/teenagent/detection/detection.cpp b/engines/teenagent/detection.cpp
similarity index 100%
rename from engines/teenagent/detection/detection.cpp
rename to engines/teenagent/detection.cpp
diff --git a/engines/teenagent/detection/module.mk b/engines/teenagent/detection/module.mk
deleted file mode 100644
index e617a5d087..0000000000
--- a/engines/teenagent/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/teenagent/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/teenagent/module.mk b/engines/teenagent/module.mk
index 174887687b..8deb130f57 100644
--- a/engines/teenagent/module.mk
+++ b/engines/teenagent/module.mk
@@ -26,3 +26,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/testbed/detection/detection.cpp b/engines/testbed/detection.cpp
similarity index 100%
rename from engines/testbed/detection/detection.cpp
rename to engines/testbed/detection.cpp
diff --git a/engines/testbed/detection/module.mk b/engines/testbed/detection/module.mk
deleted file mode 100644
index 0b8aec5b1c..0000000000
--- a/engines/testbed/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/testbed/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/testbed/module.mk b/engines/testbed/module.mk
index 02dbcd260e..f63cb70efa 100644
--- a/engines/testbed/module.mk
+++ b/engines/testbed/module.mk
@@ -44,3 +44,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tinsel/detection/detection.cpp b/engines/tinsel/detection.cpp
similarity index 97%
rename from engines/tinsel/detection/detection.cpp
rename to engines/tinsel/detection.cpp
index 454e0e48c0..e4e364539a 100644
--- a/engines/tinsel/detection/detection.cpp
+++ b/engines/tinsel/detection.cpp
@@ -26,8 +26,8 @@
 #include "common/file.h"
 #include "common/md5.h"
 
-#include "tinsel/detection/detection.h"
-#include "tinsel/detection/detection_enums.h"
+#include "tinsel/detection.h"
+#include "tinsel/detection_enums.h"
 
 static const PlainGameDescriptor tinselGames[] = {
 	{"dw", "Discworld"},
@@ -35,7 +35,7 @@ static const PlainGameDescriptor tinselGames[] = {
 	{0, 0}
 };
 
-#include "tinsel/detection/detection_tables.h"
+#include "tinsel/detection_tables.h"
 
 class TinselMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/tinsel/detection/detection.h b/engines/tinsel/detection.h
similarity index 100%
rename from engines/tinsel/detection/detection.h
rename to engines/tinsel/detection.h
diff --git a/engines/tinsel/detection/module.mk b/engines/tinsel/detection/module.mk
deleted file mode 100644
index 582856d47b..0000000000
--- a/engines/tinsel/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/tinsel/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tinsel/detection/detection_enums.h b/engines/tinsel/detection_enums.h
similarity index 100%
rename from engines/tinsel/detection/detection_enums.h
rename to engines/tinsel/detection_enums.h
diff --git a/engines/tinsel/detection/detection_tables.h b/engines/tinsel/detection_tables.h
similarity index 100%
rename from engines/tinsel/detection/detection_tables.h
rename to engines/tinsel/detection_tables.h
diff --git a/engines/tinsel/metaengine.cpp b/engines/tinsel/metaengine.cpp
index f167dfdc5f..a5a5eb3c67 100644
--- a/engines/tinsel/metaengine.cpp
+++ b/engines/tinsel/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "tinsel/tinsel.h"
 #include "tinsel/savescn.h"	// needed by TinselMetaEngine::
 
-#include "tinsel/detection/detection.h"
+#include "tinsel/detection.h"
 
 namespace Tinsel {
 
diff --git a/engines/tinsel/module.mk b/engines/tinsel/module.mk
index cd7a0cc533..1a76fd192d 100644
--- a/engines/tinsel/module.mk
+++ b/engines/tinsel/module.mk
@@ -54,3 +54,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tinsel/tinsel.h b/engines/tinsel/tinsel.h
index d2e07a4e87..ad529d15ef 100644
--- a/engines/tinsel/tinsel.h
+++ b/engines/tinsel/tinsel.h
@@ -38,7 +38,7 @@
 #include "tinsel/graphics.h"
 #include "tinsel/sound.h"
 #include "tinsel/dw.h"
-#include "tinsel/detection/detection_enums.h"
+#include "tinsel/detection_enums.h"
 
 /**
  * This is the namespace of the Tinsel engine.
diff --git a/engines/titanic/detection/detection.cpp b/engines/titanic/detection.cpp
similarity index 95%
rename from engines/titanic/detection/detection.cpp
rename to engines/titanic/detection.cpp
index 9ba686844e..c3aaf829b2 100644
--- a/engines/titanic/detection/detection.cpp
+++ b/engines/titanic/detection.cpp
@@ -25,14 +25,14 @@
 #include "common/memstream.h"
 #include "engines/advancedDetector.h"
 
-#include "titanic/detection/detection.h"
+#include "titanic/detection.h"
 
 static const PlainGameDescriptor TitanicGames[] = {
 	{"titanic", "Starship Titanic"},
 	{0, 0}
 };
 
-#include "titanic/detection/detection_tables.h"
+#include "titanic/detection_tables.h"
 
 class TitanicMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/titanic/detection/detection.h b/engines/titanic/detection.h
similarity index 100%
rename from engines/titanic/detection/detection.h
rename to engines/titanic/detection.h
diff --git a/engines/titanic/detection/module.mk b/engines/titanic/detection/module.mk
deleted file mode 100644
index 32bd415152..0000000000
--- a/engines/titanic/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/titanic/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/titanic/detection/detection_tables.h b/engines/titanic/detection_tables.h
similarity index 100%
rename from engines/titanic/detection/detection_tables.h
rename to engines/titanic/detection_tables.h
diff --git a/engines/titanic/metaengine.cpp b/engines/titanic/metaengine.cpp
index 7eba0badf2..1883f04e2c 100644
--- a/engines/titanic/metaengine.cpp
+++ b/engines/titanic/metaengine.cpp
@@ -31,7 +31,7 @@
 #include "engines/advancedDetector.h"
 #include "common/system.h"
 #include "graphics/surface.h"
-#include "titanic/detection/detection.h"
+#include "titanic/detection.h"
 
 namespace Titanic {
 
diff --git a/engines/titanic/module.mk b/engines/titanic/module.mk
index 551296479a..92cb2a6cd6 100644
--- a/engines/titanic/module.mk
+++ b/engines/titanic/module.mk
@@ -531,3 +531,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/toltecs/detection/detection.cpp b/engines/toltecs/detection.cpp
similarity index 99%
rename from engines/toltecs/detection/detection.cpp
rename to engines/toltecs/detection.cpp
index abad76da9f..201d6aba02 100644
--- a/engines/toltecs/detection/detection.cpp
+++ b/engines/toltecs/detection.cpp
@@ -30,7 +30,7 @@
 #include "common/system.h"
 
 #include "toltecs/toltecs.h"
-#include "toltecs/detection/detection.h"
+#include "toltecs/detection.h"
 
 
 static const PlainGameDescriptor toltecsGames[] = {
diff --git a/engines/toltecs/detection/detection.h b/engines/toltecs/detection.h
similarity index 100%
rename from engines/toltecs/detection/detection.h
rename to engines/toltecs/detection.h
diff --git a/engines/toltecs/detection/module.mk b/engines/toltecs/detection/module.mk
deleted file mode 100644
index f7067d006d..0000000000
--- a/engines/toltecs/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/toltecs/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/toltecs/metaengine.cpp b/engines/toltecs/metaengine.cpp
index 9ae5ef03db..e3dda22ed2 100644
--- a/engines/toltecs/metaengine.cpp
+++ b/engines/toltecs/metaengine.cpp
@@ -30,7 +30,7 @@
 #include "common/system.h"
 
 #include "toltecs/toltecs.h"
-#include "toltecs/detection/detection.h"
+#include "toltecs/detection.h"
 
 namespace Toltecs {
 
diff --git a/engines/toltecs/module.mk b/engines/toltecs/module.mk
index 338eb39542..146de8caa6 100644
--- a/engines/toltecs/module.mk
+++ b/engines/toltecs/module.mk
@@ -27,3 +27,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tony/detection/detection.cpp b/engines/tony/detection.cpp
similarity index 93%
rename from engines/tony/detection/detection.cpp
rename to engines/tony/detection.cpp
index 594f873402..fa6d8d15e5 100644
--- a/engines/tony/detection/detection.cpp
+++ b/engines/tony/detection.cpp
@@ -24,15 +24,15 @@
 
 #include "engines/advancedDetector.h"
 
-#include "tony/detection/detection.h"
-#include "tony/detection/detection_enums.h"
+#include "tony/detection.h"
+#include "tony/detection_enums.h"
 
 static const PlainGameDescriptor tonyGames[] = {
 	{"tony", "Tony Tough and the Night of Roasted Moths"},
 	{0, 0}
 };
 
-#include "tony/detection/detection_tables.h"
+#include "tony/detection_tables.h"
 
 class TonyMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/tony/detection/detection.h b/engines/tony/detection.h
similarity index 100%
rename from engines/tony/detection/detection.h
rename to engines/tony/detection.h
diff --git a/engines/tony/detection/module.mk b/engines/tony/detection/module.mk
deleted file mode 100644
index fddb4e8cad..0000000000
--- a/engines/tony/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/tony/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tony/detection/detection_enums.h b/engines/tony/detection_enums.h
similarity index 100%
rename from engines/tony/detection/detection_enums.h
rename to engines/tony/detection_enums.h
diff --git a/engines/tony/detection/detection_tables.h b/engines/tony/detection_tables.h
similarity index 100%
rename from engines/tony/detection/detection_tables.h
rename to engines/tony/detection_tables.h
diff --git a/engines/tony/metaengine.cpp b/engines/tony/metaengine.cpp
index 3beea77996..4d592d90bb 100644
--- a/engines/tony/metaengine.cpp
+++ b/engines/tony/metaengine.cpp
@@ -29,8 +29,8 @@
 
 #include "tony/tony.h"
 #include "tony/game.h"
-#include "tony/detection/detection.h"
-#include "tony/detection/detection_enums.h"
+#include "tony/detection.h"
+#include "tony/detection_enums.h"
 
 namespace Tony {
 
diff --git a/engines/tony/module.mk b/engines/tony/module.mk
index 2f99d65b8f..f9f2b1c019 100644
--- a/engines/tony/module.mk
+++ b/engines/tony/module.mk
@@ -31,3 +31,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/toon/detection/detection.cpp b/engines/toon/detection.cpp
similarity index 100%
rename from engines/toon/detection/detection.cpp
rename to engines/toon/detection.cpp
diff --git a/engines/toon/detection/module.mk b/engines/toon/detection/module.mk
deleted file mode 100644
index c48eb17963..0000000000
--- a/engines/toon/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/toon/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/toon/module.mk b/engines/toon/module.mk
index e017ef5abd..c07fceae83 100644
--- a/engines/toon/module.mk
+++ b/engines/toon/module.mk
@@ -30,3 +30,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/touche/detection/detection.cpp b/engines/touche/detection.cpp
similarity index 100%
rename from engines/touche/detection/detection.cpp
rename to engines/touche/detection.cpp
diff --git a/engines/touche/detection/module.mk b/engines/touche/detection/module.mk
deleted file mode 100644
index 6bd8004936..0000000000
--- a/engines/touche/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/touche/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/touche/module.mk b/engines/touche/module.mk
index 782c37f3f9..7bedba30dc 100644
--- a/engines/touche/module.mk
+++ b/engines/touche/module.mk
@@ -19,3 +19,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tsage/detection/detection.cpp b/engines/tsage/detection.cpp
similarity index 93%
rename from engines/tsage/detection/detection.cpp
rename to engines/tsage/detection.cpp
index b983980b46..4ca63dbc19 100644
--- a/engines/tsage/detection/detection.cpp
+++ b/engines/tsage/detection.cpp
@@ -24,8 +24,8 @@
 
 #include "base/plugins.h"
 
-#include "tsage/detection/detection.h"
-#include "tsage/detection/detection_enums.h"
+#include "tsage/detection.h"
+#include "tsage/detection_enums.h"
 
 static const PlainGameDescriptor tSageGameTitles[] = {
 	{ "ringworld", "Ringworld: Revenge of the Patriarch" },
@@ -35,7 +35,7 @@ static const PlainGameDescriptor tSageGameTitles[] = {
 	{ 0, 0 }
 };
 
-#include "tsage/detection/detection_tables.h"
+#include "tsage/detection_tables.h"
 
 class TSageMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/tsage/detection/detection.h b/engines/tsage/detection.h
similarity index 100%
rename from engines/tsage/detection/detection.h
rename to engines/tsage/detection.h
diff --git a/engines/tsage/detection/module.mk b/engines/tsage/detection/module.mk
deleted file mode 100644
index 9e5e72d952..0000000000
--- a/engines/tsage/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/tsage/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tsage/detection/detection_enums.h b/engines/tsage/detection_enums.h
similarity index 100%
rename from engines/tsage/detection/detection_enums.h
rename to engines/tsage/detection_enums.h
diff --git a/engines/tsage/detection/detection_tables.h b/engines/tsage/detection_tables.h
similarity index 100%
rename from engines/tsage/detection/detection_tables.h
rename to engines/tsage/detection_tables.h
diff --git a/engines/tsage/metaengine.cpp b/engines/tsage/metaengine.cpp
index eb895ac5e1..a3dd011fa1 100644
--- a/engines/tsage/metaengine.cpp
+++ b/engines/tsage/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "base/plugins.h"
 
 #include "tsage/tsage.h"
-#include "tsage/detection/detection.h"
+#include "tsage/detection.h"
 
 namespace TsAGE {
 
diff --git a/engines/tsage/module.mk b/engines/tsage/module.mk
index ced8967e78..222932b223 100644
--- a/engines/tsage/module.mk
+++ b/engines/tsage/module.mk
@@ -61,3 +61,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tsage/tsage.h b/engines/tsage/tsage.h
index 18c682ce32..06b6f53ae3 100644
--- a/engines/tsage/tsage.h
+++ b/engines/tsage/tsage.h
@@ -32,7 +32,7 @@
 #include "tsage/events.h"
 #include "tsage/graphics.h"
 #include "tsage/resources.h"
-#include "tsage/detection/detection_enums.h"
+#include "tsage/detection_enums.h"
 
 
 namespace TsAGE {
diff --git a/engines/tucker/detection/detection.cpp b/engines/tucker/detection.cpp
similarity index 98%
rename from engines/tucker/detection/detection.cpp
rename to engines/tucker/detection.cpp
index a3f5671173..50d618721e 100644
--- a/engines/tucker/detection/detection.cpp
+++ b/engines/tucker/detection.cpp
@@ -23,7 +23,7 @@
 #include "common/config-manager.h"
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
-#include "tucker/detection/detection_enums.h"
+#include "tucker/detection_enums.h"
 
 static const PlainGameDescriptor tuckerGames[] = {
 	{ "tucker", "Bud Tucker in Double Trouble" },
diff --git a/engines/tucker/detection/module.mk b/engines/tucker/detection/module.mk
deleted file mode 100644
index 8633063520..0000000000
--- a/engines/tucker/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/tucker/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tucker/detection/detection_enums.h b/engines/tucker/detection_enums.h
similarity index 100%
rename from engines/tucker/detection/detection_enums.h
rename to engines/tucker/detection_enums.h
diff --git a/engines/tucker/module.mk b/engines/tucker/module.mk
index b727879bd0..df02f313e2 100644
--- a/engines/tucker/module.mk
+++ b/engines/tucker/module.mk
@@ -18,3 +18,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/tucker/tucker.h b/engines/tucker/tucker.h
index 3077a35ec9..9340d9a3cf 100644
--- a/engines/tucker/tucker.h
+++ b/engines/tucker/tucker.h
@@ -38,7 +38,7 @@
 #include "engines/engine.h"
 
 #include "tucker/console.h"
-#include "tucker/detection/detection_enums.h"
+#include "tucker/detection_enums.h"
 
 namespace Audio {
 class RewindableAudioStream;
diff --git a/engines/ultima/detection/detection.cpp b/engines/ultima/detection.cpp
similarity index 97%
rename from engines/ultima/detection/detection.cpp
rename to engines/ultima/detection.cpp
index 3103c5ad55..8f62f6fe46 100644
--- a/engines/ultima/detection/detection.cpp
+++ b/engines/ultima/detection.cpp
@@ -47,7 +47,7 @@ static const PlainGameDescriptor ULTIMA_GAMES[] = {
 
 } // End of namespace Ultima
 
-#include "ultima/detection/detection_tables.h"
+#include "ultima/detection_tables.h"
 
 UltimaMetaEngine::UltimaMetaEngine() : AdvancedMetaEngine(Ultima::GAME_DESCRIPTIONS,
 	        sizeof(Ultima::UltimaGameDescription), Ultima::ULTIMA_GAMES) {
diff --git a/engines/ultima/detection/module.mk b/engines/ultima/detection/module.mk
deleted file mode 100644
index 6130a554fc..0000000000
--- a/engines/ultima/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/ultima/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/ultima/detection/detection_tables.h b/engines/ultima/detection_tables.h
similarity index 100%
rename from engines/ultima/detection/detection_tables.h
rename to engines/ultima/detection_tables.h
diff --git a/engines/ultima/module.mk b/engines/ultima/module.mk
index 1e324a2937..59822cf863 100644
--- a/engines/ultima/module.mk
+++ b/engines/ultima/module.mk
@@ -591,3 +591,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/voyeur/detection/detection.cpp b/engines/voyeur/detection.cpp
similarity index 95%
rename from engines/voyeur/detection/detection.cpp
rename to engines/voyeur/detection.cpp
index 252dca1a74..1afa7bec50 100644
--- a/engines/voyeur/detection/detection.cpp
+++ b/engines/voyeur/detection.cpp
@@ -25,14 +25,14 @@
 #include "common/str-array.h"
 #include "common/memstream.h"
 #include "engines/advancedDetector.h"
-#include "voyeur/detection/detection.h"
+#include "voyeur/detection.h"
 
 static const PlainGameDescriptor voyeurGames[] = {
 	{"voyeur", "Voyeur"},
 	{0, 0}
 };
 
-#include "voyeur/detection/detection_tables.h"
+#include "voyeur/detection_tables.h"
 
 class VoyeurMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/voyeur/detection/detection.h b/engines/voyeur/detection.h
similarity index 100%
rename from engines/voyeur/detection/detection.h
rename to engines/voyeur/detection.h
diff --git a/engines/voyeur/detection/module.mk b/engines/voyeur/detection/module.mk
deleted file mode 100644
index f792114359..0000000000
--- a/engines/voyeur/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/voyeur/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/voyeur/detection/detection_tables.h b/engines/voyeur/detection_tables.h
similarity index 100%
rename from engines/voyeur/detection/detection_tables.h
rename to engines/voyeur/detection_tables.h
diff --git a/engines/voyeur/metaengine.cpp b/engines/voyeur/metaengine.cpp
index 66792f678c..ee145ef19f 100644
--- a/engines/voyeur/metaengine.cpp
+++ b/engines/voyeur/metaengine.cpp
@@ -29,7 +29,7 @@
 
 #include "graphics/surface.h"
 
-#include "voyeur/detection/detection.h"
+#include "voyeur/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/voyeur/module.mk b/engines/voyeur/module.mk
index 0408d27c01..ae6b7625b5 100644
--- a/engines/voyeur/module.mk
+++ b/engines/voyeur/module.mk
@@ -21,3 +21,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wage/detection/detection.cpp b/engines/wage/detection.cpp
similarity index 97%
rename from engines/wage/detection/detection.cpp
rename to engines/wage/detection.cpp
index e877bce602..6a1b243745 100644
--- a/engines/wage/detection/detection.cpp
+++ b/engines/wage/detection.cpp
@@ -37,7 +37,7 @@ static const PlainGameDescriptor wageGames[] = {
 	{0, 0}
 };
 
-#include "wage/detection/detection_tables.h"
+#include "wage/detection_tables.h"
 
 class WageMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/wage/detection/module.mk b/engines/wage/detection/module.mk
deleted file mode 100644
index 188d75bc8e..0000000000
--- a/engines/wage/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/wage/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wage/detection/detection_tables.h b/engines/wage/detection_tables.h
similarity index 100%
rename from engines/wage/detection/detection_tables.h
rename to engines/wage/detection_tables.h
diff --git a/engines/wage/module.mk b/engines/wage/module.mk
index dd66b59bcb..86b4b86c8c 100644
--- a/engines/wage/module.mk
+++ b/engines/wage/module.mk
@@ -26,3 +26,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wintermute/base/base_sprite.cpp b/engines/wintermute/base/base_sprite.cpp
index 3e826ceeda..eb88e3de09 100644
--- a/engines/wintermute/base/base_sprite.cpp
+++ b/engines/wintermute/base/base_sprite.cpp
@@ -41,7 +41,7 @@
 #include "engines/wintermute/base/scriptables/script_value.h"
 #include "engines/wintermute/base/scriptables/script.h"
 #include "engines/wintermute/base/scriptables/script_stack.h"
-#include "engines/wintermute/detection/detection.h"
+#include "engines/wintermute/detection.h"
 
 namespace Wintermute {
 
diff --git a/engines/wintermute/detection/detection.cpp b/engines/wintermute/detection.cpp
similarity index 96%
rename from engines/wintermute/detection/detection.cpp
rename to engines/wintermute/detection.cpp
index af82afe9e4..ccea897d96 100644
--- a/engines/wintermute/detection/detection.cpp
+++ b/engines/wintermute/detection.cpp
@@ -31,9 +31,9 @@
 #include "engines/metaengine.h"
 
 #include "wintermute/base/base_detection_enums.h"
-#include "wintermute/detection/detection_enums.h"
-#include "wintermute/detection/detection.h"
-#include "wintermute/detection/detection_tables.h"
+#include "wintermute/detection_enums.h"
+#include "wintermute/detection.h"
+#include "wintermute/detection_tables.h"
 
 namespace Wintermute {
 
diff --git a/engines/wintermute/detection/detection.h b/engines/wintermute/detection.h
similarity index 100%
rename from engines/wintermute/detection/detection.h
rename to engines/wintermute/detection.h
diff --git a/engines/wintermute/detection/module.mk b/engines/wintermute/detection/module.mk
deleted file mode 100644
index 47672db167..0000000000
--- a/engines/wintermute/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/wintermute/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wintermute/detection/detection_enums.h b/engines/wintermute/detection_enums.h
similarity index 100%
rename from engines/wintermute/detection/detection_enums.h
rename to engines/wintermute/detection_enums.h
diff --git a/engines/wintermute/detection/detection_tables.h b/engines/wintermute/detection_tables.h
similarity index 100%
rename from engines/wintermute/detection/detection_tables.h
rename to engines/wintermute/detection_tables.h
diff --git a/engines/wintermute/metaengine.cpp b/engines/wintermute/metaengine.cpp
index 7b9461379a..baafb427aa 100644
--- a/engines/wintermute/metaengine.cpp
+++ b/engines/wintermute/metaengine.cpp
@@ -30,8 +30,8 @@
 
 // Detection related files.
 #include "wintermute/base/base_detection_enums.h"
-#include "wintermute/detection/detection.h"
-#include "wintermute/detection/detection_tables.h"
+#include "wintermute/detection.h"
+#include "wintermute/detection_tables.h"
 
 namespace Wintermute {
 
diff --git a/engines/wintermute/module.mk b/engines/wintermute/module.mk
index 8dbe0ab3ff..9a701fbd12 100644
--- a/engines/wintermute/module.mk
+++ b/engines/wintermute/module.mk
@@ -154,3 +154,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/wintermute/wintermute.cpp b/engines/wintermute/wintermute.cpp
index 130fed3fb6..579fd54bfc 100644
--- a/engines/wintermute/wintermute.cpp
+++ b/engines/wintermute/wintermute.cpp
@@ -37,7 +37,7 @@
 #include "engines/wintermute/debugger.h"
 #include "engines/wintermute/platform_osystem.h"
 #include "engines/wintermute/base/base_engine.h"
-#include "engines/wintermute/detection/detection.h"
+#include "engines/wintermute/detection.h"
 
 #include "engines/wintermute/base/sound/base_sound_manager.h"
 #include "engines/wintermute/base/base_file_manager.h"
diff --git a/engines/wintermute/wintermute.h b/engines/wintermute/wintermute.h
index 8ba0f05021..08bfa4f6e8 100644
--- a/engines/wintermute/wintermute.h
+++ b/engines/wintermute/wintermute.h
@@ -26,7 +26,7 @@
 #include "engines/engine.h"
 #include "gui/debugger.h"
 #include "common/fs.h"
-#include "wintermute/detection/detection_enums.h"
+#include "wintermute/detection_enums.h"
 
 namespace Wintermute {
 
diff --git a/engines/xeen/detection/detection.cpp b/engines/xeen/detection.cpp
similarity index 95%
rename from engines/xeen/detection/detection.cpp
rename to engines/xeen/detection.cpp
index a73bf9d1e8..79343db575 100644
--- a/engines/xeen/detection/detection.cpp
+++ b/engines/xeen/detection.cpp
@@ -24,8 +24,8 @@
 #include "engines/advancedDetector.h"
 #include "common/translation.h"
 
-#include "xeen/detection/detection.h"
-#include "xeen/detection/detection_enums.h"
+#include "xeen/detection.h"
+#include "xeen/detection_enums.h"
 
 static const PlainGameDescriptor XeenGames[] = {
 	{ "cloudsofxeen", "Might and Magic IV: Clouds of Xeen" },
@@ -38,7 +38,7 @@ static const PlainGameDescriptor XeenGames[] = {
 #define GAMEOPTION_SHOW_ITEM_COSTS	GUIO_GAMEOPTIONS1
 #define GAMEOPTION_DURABLE_ARMOR	GUIO_GAMEOPTIONS2
 
-#include "xeen/detection/detection_tables.h"
+#include "xeen/detection_tables.h"
 
 
 static const ADExtraGuiOptionsMap optionsList[] = {
diff --git a/engines/xeen/detection/detection.h b/engines/xeen/detection.h
similarity index 100%
rename from engines/xeen/detection/detection.h
rename to engines/xeen/detection.h
diff --git a/engines/xeen/detection/module.mk b/engines/xeen/detection/module.mk
deleted file mode 100644
index f940a4abc6..0000000000
--- a/engines/xeen/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/xeen/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/xeen/detection/detection_enums.h b/engines/xeen/detection_enums.h
similarity index 100%
rename from engines/xeen/detection/detection_enums.h
rename to engines/xeen/detection_enums.h
diff --git a/engines/xeen/detection/detection_tables.h b/engines/xeen/detection_tables.h
similarity index 100%
rename from engines/xeen/detection/detection_tables.h
rename to engines/xeen/detection_tables.h
diff --git a/engines/xeen/metaengine.cpp b/engines/xeen/metaengine.cpp
index ef2c824f16..bbeca61390 100644
--- a/engines/xeen/metaengine.cpp
+++ b/engines/xeen/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "engines/advancedDetector.h"
 #include "common/system.h"
 #include "common/translation.h"
-#include "xeen/detection/detection.h"
+#include "xeen/detection.h"
 
 #define MAX_SAVES 99
 
diff --git a/engines/xeen/module.mk b/engines/xeen/module.mk
index f2468df3fd..71afe7762d 100644
--- a/engines/xeen/module.mk
+++ b/engines/xeen/module.mk
@@ -68,3 +68,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/xeen/xeen.h b/engines/xeen/xeen.h
index 628cc57d25..503d6a5a99 100644
--- a/engines/xeen/xeen.h
+++ b/engines/xeen/xeen.h
@@ -47,7 +47,7 @@
 #include "xeen/sound.h"
 #include "xeen/spells.h"
 #include "xeen/window.h"
-#include "xeen/detection/detection_enums.h"
+#include "xeen/detection_enums.h"
 
 /**
  * This is the namespace of the Xeen engine.
diff --git a/engines/zvision/detection/detection.cpp b/engines/zvision/detection.cpp
similarity index 92%
rename from engines/zvision/detection/detection.cpp
rename to engines/zvision/detection.cpp
index 290aba42f5..25a9c2ca18 100644
--- a/engines/zvision/detection/detection.cpp
+++ b/engines/zvision/detection.cpp
@@ -29,9 +29,9 @@
 #include "common/translation.h"
 #include "common/str-array.h"
 
-#include "zvision/detection/detection_enums.h"
-#include "zvision/detection/detection.h"
-#include "zvision/detection/detection_tables.h"
+#include "zvision/detection_enums.h"
+#include "zvision/detection.h"
+#include "zvision/detection_tables.h"
 
 class ZVisionMetaEngine : public AdvancedMetaEngine {
 public:
diff --git a/engines/zvision/detection/detection.h b/engines/zvision/detection.h
similarity index 100%
rename from engines/zvision/detection/detection.h
rename to engines/zvision/detection.h
diff --git a/engines/zvision/detection/module.mk b/engines/zvision/detection/module.mk
deleted file mode 100644
index ce2ddb62d7..0000000000
--- a/engines/zvision/detection/module.mk
+++ /dev/null
@@ -1,4 +0,0 @@
-MODULE := engines/zvision/detection
-
-# Detection objects
-DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/zvision/detection/detection_enums.h b/engines/zvision/detection_enums.h
similarity index 100%
rename from engines/zvision/detection/detection_enums.h
rename to engines/zvision/detection_enums.h
diff --git a/engines/zvision/detection/detection_tables.h b/engines/zvision/detection_tables.h
similarity index 100%
rename from engines/zvision/detection/detection_tables.h
rename to engines/zvision/detection_tables.h
diff --git a/engines/zvision/metaengine.cpp b/engines/zvision/metaengine.cpp
index bf3169fa6e..1732a0e5ed 100644
--- a/engines/zvision/metaengine.cpp
+++ b/engines/zvision/metaengine.cpp
@@ -27,7 +27,7 @@
 #include "zvision/zvision.h"
 #include "zvision/file/save_manager.h"
 #include "zvision/scripting/script_manager.h"
-#include "zvision/detection/detection.h"
+#include "zvision/detection.h"
 
 #include "backends/keymapper/action.h"
 #include "backends/keymapper/keymapper.h"
diff --git a/engines/zvision/module.mk b/engines/zvision/module.mk
index 89265adf49..70728e39dc 100644
--- a/engines/zvision/module.mk
+++ b/engines/zvision/module.mk
@@ -60,3 +60,6 @@ endif
 
 # Include common rules
 include $(srcdir)/rules.mk
+
+# Detection objects
+DETECT_OBJS += $(MODULE)/detection.o
diff --git a/engines/zvision/zvision.h b/engines/zvision/zvision.h
index 0677abe562..5cdb4ea9cb 100644
--- a/engines/zvision/zvision.h
+++ b/engines/zvision/zvision.h
@@ -26,7 +26,7 @@
 
 #include "zvision/core/clock.h"
 #include "zvision/file/search_manager.h"
-#include "zvision/detection/detection_enums.h"
+#include "zvision/detection_enums.h"
 
 #include "common/random.h"
 #include "common/events.h"


Commit: e64446e4ce53101bcf3ea36f20a65780dcca593c
    https://github.com/scummvm/scummvm/commit/e64446e4ce53101bcf3ea36f20a65780dcca593c
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CONFIGURE: Remove detection submodules written to engines.mk

- Write detection_table inside engines subdirectory

Changed paths:
    configure


diff --git a/configure b/configure
index cf42dd7fde..60c005db61 100755
--- a/configure
+++ b/configure
@@ -6145,8 +6145,6 @@ for engine in $_sorted_engines; do
 		# main engine
 		cat >> engines/engines.mk << EOF
 
-MODULES += engines/$engine/detection
-
 ifdef ENABLE_$j
 DEFINES += -DENABLE_$j=\$(ENABLE_$j)
 MODULES += engines/$engine
@@ -6168,31 +6166,22 @@ EOF
 	fi
 done
 
-if [ "${_detection_features_static}" == "false" ]; then
-	cat >> engines/engines.mk << EOF
-
-# This build was configured to use detection as a dynamic plugin.
-MODULES += detection
-EOF
-fi
-
 # Name which is suffixed to each detection plugin
 detectId="_DETECTION"
 
-echo "Creating detection/detection_table.h"
-cat > detection/detection_table.h << EOF
+echo "Creating engines/detection_table.h"
+cat > engines/detection_table.h << EOF
 /* This file is automatically generated by configure */
 /* DO NOT EDIT MANUALLY */
-// This file is being included by "detection/detection.cpp" and "base/plugins.cpp"
+// This file is being included by "base/plugins.cpp"
 EOF
 
 for engine in $_sorted_engines; do
 	if test "`get_engine_sub $engine`" = "no" ; then
 		j=`echo $engine | tr '[:lower:]' '[:upper:]'`
 		detectEngine="${j}${detectId}"
-		cat >> detection/detection_table.h << EOF
+		cat >> engines/detection_table.h << EOF
 LINK_PLUGIN($detectEngine)
-
 EOF
 	fi
 done


Commit: 911e0e4f3c3fd5aa79f5bb8ff03d9403eb3d5af7
    https://github.com/scummvm/scummvm/commit/911e0e4f3c3fd5aa79f5bb8ff03d9403eb3d5af7
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GIT: Rename detection_tables inside gitignore which is now present inside engines subdirectory

Changed paths:
    .gitignore


diff --git a/.gitignore b/.gitignore
index 2f2a32423e..5bacee649e 100644
--- a/.gitignore
+++ b/.gitignore
@@ -121,7 +121,7 @@ project.xcworkspace
 
 /plugins
 
-/detection/detection_table.h
+/engines/detection_table.h
 /engines/plugins_table.h
 /engines/engines.mk
 


Commit: 6735c46c410dac3844251d8131951fdb240a480c
    https://github.com/scummvm/scummvm/commit/6735c46c410dac3844251d8131951fdb240a480c
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MAKEFILES: Add a variable which helps in deciding if rules.mk should be used or not

- It is always enabled by default
- Only disabled when we would include all engine module files, so we don't include unnecessary stuff

Changed paths:
    Makefile
    rules.mk


diff --git a/Makefile b/Makefile
index 7d59044032..fdb969a158 100644
--- a/Makefile
+++ b/Makefile
@@ -17,6 +17,7 @@ MODULE_DIRS :=
 
 # All game detection-related object files for engines
 DETECT_OBJS :=
+USE_RULES   := 1
 
 # Load the make rules generated by configure
 -include config.mk
diff --git a/rules.mk b/rules.mk
index b793ea480b..6ebf055c2c 100644
--- a/rules.mk
+++ b/rules.mk
@@ -3,6 +3,7 @@
 #
 ###############################################
 
+ifeq "$(USE_RULES)" "1"
 
 # Copy the list of objects to a new variable. The name of the new variable
 # contains the module name, a trick we use so we can keep multiple different
@@ -103,3 +104,5 @@ ifdef SPLIT_DWARF
 endif
 
 .PHONY: clean-$(MODULE) $(MODULE)
+
+endif # USE_RULES


Commit: ac900a06b863a29a3cd0f87a177c77e197681db4
    https://github.com/scummvm/scummvm/commit/ac900a06b863a29a3cd0f87a177c77e197681db4
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Use engines/detection_table header for static plugins

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index cd68e2be40..52bfa0bf31 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -98,7 +98,7 @@ public:
 
 		#ifndef UNCACHED_PLUGINS
 		// Engine-detection plugins are included if we don't use uncached plugins.
-		#include "detection/detection_table.h"
+		#include "engines/detection_table.h"
 		#endif
 
 		// Music plugins


Commit: 4f55c1b689f9af2fd9c2889a94346661af4d6970
    https://github.com/scummvm/scummvm/commit/4f55c1b689f9af2fd9c2889a94346661af4d6970
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DIRECTOR & KYRA: MODULES: Use workarounds to skip warnings.

- When these files are included for the second time, a warning is shown that the previous recipes will be overriden.
- Use_Rules helps with a workaround to disable these warnings.

Changed paths:
    engines/director/module.mk
    engines/kyra/module.mk


diff --git a/engines/director/module.mk b/engines/director/module.mk
index 508ea8707a..2f17e00eef 100644
--- a/engines/director/module.mk
+++ b/engines/director/module.mk
@@ -40,9 +40,12 @@ MODULE_OBJS = \
 	lingo/xlibs/palxobj.o \
 	lingo/xlibs/winxobj.o
 
+# HACK: Skip this when including the file for detection objects.
+ifeq "$(USE_RULES)" "1"
 director-grammar:
 	`brew --prefix flex`/bin/flex engines/director/lingo/lingo-lex.l
 	`brew --prefix bison`/bin/bison -dv engines/director/lingo/lingo-gr.y
+endif
 
 # This module can be built as a plugin
 ifeq ($(ENABLE_DIRECTOR), DYNAMIC_PLUGIN)
diff --git a/engines/kyra/module.mk b/engines/kyra/module.mk
index dbab44939c..1f674408c2 100644
--- a/engines/kyra/module.mk
+++ b/engines/kyra/module.mk
@@ -153,12 +153,15 @@ endif
 # Include common rules
 include $(srcdir)/rules.mk
 
+# HACK: Skip this when including the file for detection objects.
+ifeq "$(USE_RULES)" "1"
 ifeq ($(BACKEND), maemo)
-#ugly workaround, screen.cpp crashes gcc version 3.4.4 (CodeSourcery ARM 2005q3-2) with anything but -O3
+# Ugly workaround, screen.cpp crashes gcc version 3.4.4 (CodeSourcery ARM 2005q3-2) with anything but -O3
 $(MODULE)/graphics/screen.o: $(MODULE)/graphics/screen.cpp
 	$(MKDIR) $(*D)/$(DEPDIR)
 	$(CXX) -Wp,-MMD,"$(*D)/$(DEPDIR)/$(*F).d",-MQ,"$@",-MP $(CXXFLAGS) -O3 $(CPPFLAGS) -c $(<) -o $*.o
-endif
+endif # BACKEND=MAEMO
+endif # USE_RULES
 
 # Detection objects
 DETECT_OBJS += $(MODULE)/detection.o


Commit: 1d3e4d2800927001624186afb40413dacd63c4c0
    https://github.com/scummvm/scummvm/commit/1d3e4d2800927001624186afb40413dacd63c4c0
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MOHAWK: Do not create additional folders for riven & myst metaengines.

Changed paths:
  A engines/mohawk/myst_metaengine.cpp
  A engines/mohawk/myst_metaengine.h
  A engines/mohawk/riven_graphics_detection_enums.h
  A engines/mohawk/riven_metaengine.cpp
  A engines/mohawk/riven_metaengine.h
  R engines/mohawk/myst_metaengine/metaengine.cpp
  R engines/mohawk/myst_metaengine/metaengine.h
  R engines/mohawk/riven_metaengine/graphics_detection_enums.h
  R engines/mohawk/riven_metaengine/metaengine.cpp
  R engines/mohawk/riven_metaengine/metaengine.h
    engines/mohawk/detection.cpp
    engines/mohawk/dialogs.cpp
    engines/mohawk/module.mk
    engines/mohawk/myst.cpp
    engines/mohawk/riven.cpp
    engines/mohawk/riven_graphics.h


diff --git a/engines/mohawk/detection.cpp b/engines/mohawk/detection.cpp
index d2d6b4f6a0..d766a3e4d5 100644
--- a/engines/mohawk/detection.cpp
+++ b/engines/mohawk/detection.cpp
@@ -30,8 +30,8 @@
 #include "mohawk/detection.h"
 #include "mohawk/detection_enums.h"
 
-#include "mohawk/riven_metaengine/metaengine.h"
-#include "mohawk/myst_metaengine/metaengine.h"
+#include "mohawk/riven_metaengine.h"
+#include "mohawk/myst_metaengine.h"
 
 
 static const PlainGameDescriptor mohawkGames[] = {
diff --git a/engines/mohawk/dialogs.cpp b/engines/mohawk/dialogs.cpp
index af27c530f8..dbdbeff424 100644
--- a/engines/mohawk/dialogs.cpp
+++ b/engines/mohawk/dialogs.cpp
@@ -38,13 +38,13 @@
 #include "mohawk/myst.h"
 #include "mohawk/myst_actions.h"
 #include "mohawk/myst_scripts.h"
-#include "mohawk/myst_metaengine/metaengine.h"
+#include "mohawk/myst_metaengine.h"
 #endif
 
 #ifdef ENABLE_RIVEN
 #include "mohawk/riven.h"
 #include "mohawk/riven_graphics.h"
-#include "mohawk/riven_metaengine/metaengine.h"
+#include "mohawk/riven_metaengine.h"
 #endif
 
 namespace Mohawk {
diff --git a/engines/mohawk/module.mk b/engines/mohawk/module.mk
index 8cafb7c7b3..edb3923172 100644
--- a/engines/mohawk/module.mk
+++ b/engines/mohawk/module.mk
@@ -12,6 +12,8 @@ MODULE_OBJS = \
 	livingbooks_graphics.o \
 	livingbooks_lbx.o \
 	metaengine.o \
+	riven_metaengine.o \
+	myst_metaengine.o \
 	mohawk.o \
 	resource.o \
 	sound.o \
@@ -30,7 +32,6 @@ endif
 
 ifdef ENABLE_MYST
 MODULE_OBJS += \
-	myst_metaengine/metaengine.o \
 	myst.o \
 	myst_areas.o \
 	myst_card.o \
@@ -56,7 +57,6 @@ endif
 
 ifdef ENABLE_RIVEN
 MODULE_OBJS += \
-	riven_metaengine/metaengine.o \
 	riven.o \
 	riven_card.o \
 	riven_graphics.o \
@@ -92,6 +92,6 @@ DETECT_OBJS += $(MODULE)/detection.o
 # Skip building the following objects if a static
 # module is enabled, because it already has the contents.
 ifneq ($(ENABLE_MOHAWK), STATIC_PLUGIN)
-DETECT_OBJS += $(MODULE)/myst_metaengine/metaengine.o
-DETECT_OBJS += $(MODULE)/riven_metaengine/metaengine.o
+DETECT_OBJS += $(MODULE)/myst_metaengine.o
+DETECT_OBJS += $(MODULE)/riven_metaengine.o
 endif
diff --git a/engines/mohawk/myst.cpp b/engines/mohawk/myst.cpp
index b190af4f29..dfe6daf3c6 100644
--- a/engines/mohawk/myst.cpp
+++ b/engines/mohawk/myst.cpp
@@ -63,7 +63,7 @@
 #include "mohawk/myst_stacks/stoneship.h"
 
 // Common files for detection & engines
-#include "mohawk/myst_metaengine/metaengine.h"
+#include "mohawk/myst_metaengine.h"
 
 namespace Mohawk {
 
diff --git a/engines/mohawk/myst_metaengine/metaengine.cpp b/engines/mohawk/myst_metaengine.cpp
similarity index 97%
rename from engines/mohawk/myst_metaengine/metaengine.cpp
rename to engines/mohawk/myst_metaengine.cpp
index 54976218ae..7f400bb308 100644
--- a/engines/mohawk/myst_metaengine/metaengine.cpp
+++ b/engines/mohawk/myst_metaengine.cpp
@@ -20,7 +20,7 @@
  *
  */
 
-#include "mohawk/myst_metaengine/metaengine.h"
+#include "mohawk/myst_metaengine.h"
 
 void Mohawk::MohawkMetaEngine_Myst::registerDefaultSettings() {
 	ConfMan.registerDefault("playmystflyby", false);
diff --git a/engines/mohawk/myst_metaengine/metaengine.h b/engines/mohawk/myst_metaengine.h
similarity index 100%
rename from engines/mohawk/myst_metaengine/metaengine.h
rename to engines/mohawk/myst_metaengine.h
diff --git a/engines/mohawk/riven.cpp b/engines/mohawk/riven.cpp
index a3c2b669fc..3ea276faf6 100644
--- a/engines/mohawk/riven.cpp
+++ b/engines/mohawk/riven.cpp
@@ -58,7 +58,7 @@
 #include "mohawk/console.h"
 
 // Shared code between detection/engine.
-#include "mohawk/riven_metaengine/metaengine.h"
+#include "mohawk/riven_metaengine.h"
 
 namespace Mohawk {
 
diff --git a/engines/mohawk/riven_graphics.h b/engines/mohawk/riven_graphics.h
index 25d7921290..51ecfd8e10 100644
--- a/engines/mohawk/riven_graphics.h
+++ b/engines/mohawk/riven_graphics.h
@@ -24,7 +24,7 @@
 #define MOHAWK_RIVEN_GRAPHICS_H
 
 #include "mohawk/graphics.h"
-#include "mohawk/riven_metaengine/graphics_detection_enums.h"
+#include "mohawk/riven_graphics_detection_enums.h"
 
 #include "common/ustr.h"
 
diff --git a/engines/mohawk/riven_metaengine/graphics_detection_enums.h b/engines/mohawk/riven_graphics_detection_enums.h
similarity index 100%
rename from engines/mohawk/riven_metaengine/graphics_detection_enums.h
rename to engines/mohawk/riven_graphics_detection_enums.h
diff --git a/engines/mohawk/riven_metaengine/metaengine.cpp b/engines/mohawk/riven_metaengine.cpp
similarity index 93%
rename from engines/mohawk/riven_metaengine/metaengine.cpp
rename to engines/mohawk/riven_metaengine.cpp
index e182826de3..00cd69e205 100644
--- a/engines/mohawk/riven_metaengine/metaengine.cpp
+++ b/engines/mohawk/riven_metaengine.cpp
@@ -20,8 +20,8 @@
  *
  */
 
-#include "mohawk/riven_metaengine/metaengine.h"
-#include "mohawk/riven_metaengine/graphics_detection_enums.h"
+#include "mohawk/riven_metaengine.h"
+#include "mohawk/riven_graphics_detection_enums.h"
 
 void Mohawk::MohawkMetaEngine_Riven::registerDefaultSettings() {
 	ConfMan.registerDefault("zip_mode", false);
diff --git a/engines/mohawk/riven_metaengine/metaengine.h b/engines/mohawk/riven_metaengine.h
similarity index 100%
rename from engines/mohawk/riven_metaengine/metaengine.h
rename to engines/mohawk/riven_metaengine.h


Commit: 0cbff637d45686a64ed4453520f747c83636ff88
    https://github.com/scummvm/scummvm/commit/0cbff637d45686a64ed4453520f747c83636ff88
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MAKEFILES: Include all detection objects while keeping the rest as-is.

- This enables detection objects to be always available and build into the executable.

Changed paths:
    Makefile.common


diff --git a/Makefile.common b/Makefile.common
index b4482a9143..227d4342a6 100644
--- a/Makefile.common
+++ b/Makefile.common
@@ -52,6 +52,32 @@ CPPFLAGS := $(DEFINES) $(INCLUDES)
 # Include the build instructions for all modules
 -include $(addprefix $(srcdir)/, $(addsuffix /module.mk,$(MODULES)))
 
+# Store original info
+MODULES_ORIG:= $(MODULES)
+MODULE_DIRS_ORIG := $(MODULE_DIRS)
+KYRARPG_COMMON_OBJ_ORIG := $(KYRARPG_COMMON_OBJ)
+
+# Skip rules for these files, by resetting the use_rules
+USE_RULES :=
+
+# Reset detection objects, which uptill now are filled with only
+# enabled engines.
+DETECT_OBJS :=
+
+# Include all engine's module files, which populate DETECT_OBJS
+-include $(srcdir)/engines/*/module.mk
+
+# Reset stuff
+MODULES := $(MODULES_ORIG)
+MODULE :=
+MODULE_OBJS :=
+MODULE_DIRS := $(MODULE_DIRS_ORIG)
+PLUGIN :=
+KYRARPG_COMMON_OBJ := $(KYRARPG_COMMON_OBJ_ORIG)
+
+# Enable-rules again
+USE_RULES := 1
+
 # Depdir information
 DEPDIRS = $(addsuffix $(DEPDIR),$(MODULE_DIRS))
 DEPFILES =


Commit: 867e6c4e216c25c3ad18a977362cb8c6f7d6499f
    https://github.com/scummvm/scummvm/commit/867e6c4e216c25c3ad18a977362cb8c6f7d6499f
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
CONFIGURE: Improve enabling of detection as static/dynamic

- Add config statements to help in makefiles & base/plugins.cpp
- Print to console if detection is building as static or not

Changed paths:
    configure


diff --git a/configure b/configure
index 60c005db61..08c0d79bb2 100755
--- a/configure
+++ b/configure
@@ -242,7 +242,7 @@ _pandocpath="$PATH"
 _pandocformat="default"
 _pandocext="default"
 # Detection features to be linked into executable or not
-_detection_features_static="true"
+_detection_features_static=yes
 # The following variables are automatically detected, and should not
 # be modified otherwise. Consider them read-only.
 _posix=no
@@ -1225,8 +1225,8 @@ for ac_option in $@; do
 	--enable-dependency-tracking)                        ;;
 	# End of ignored options.
 	--enable-static)              _static_build=yes      ;;
-	--enable-detection-static)    _detection_features_static="true";;
-	--enable-detection-dynamic)   _detection_features_static="false";;
+	--enable-detection-static)    _detection_features_static=yes;;
+	--enable-detection-dynamic)   _detection_features_static=no;;
 	--disable-16bit)              _16bit=no              ;;
 	--enable-highres)             _highres=yes           ;;
 	--disable-highres)            _highres=no            ;;
@@ -4190,6 +4190,12 @@ if test "$_dynamic_modules" = yes ; then
 	add_line_to_config_mk "PLUGIN_SUFFIX := $_plugin_suffix"
 fi
 
+#
+# Set up a define for detection to be used as static or not
+#
+define_in_config_if_yes "$_detection_features_static" "DETECTION_STATIC"
+echo_n "Checking if detection features building statically... "
+echo "$_detection_features_static"
 
 #
 # Check whether integrated MT-32 emulator support is requested


Commit: 81d2bb8f1128407917d3ddb0f2e5edcbdc089b11
    https://github.com/scummvm/scummvm/commit/81d2bb8f1128407917d3ddb0f2e5edcbdc089b11
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: DETECTION: Shift detection files to live inside engines subdirectory

Changed paths:
  A engines/detect_modules.mk
  A engines/detection.cpp
  A engines/detection.h
  R detection/detection.cpp
  R detection/detection.h
  R detection/module.mk


diff --git a/detection/module.mk b/engines/detect_modules.mk
similarity index 90%
rename from detection/module.mk
rename to engines/detect_modules.mk
index b53e7bad1e..e5dec7a937 100644
--- a/detection/module.mk
+++ b/engines/detect_modules.mk
@@ -3,7 +3,7 @@ MODULE := detection
 DETECT_OBJS_DYNAMIC=$(addprefix ../,$(DETECT_OBJS))
 
 MODULE_OBJS := \
-	detection.o \
+	../engines/detection.o \
 	$(DETECT_OBJS_DYNAMIC)
 
 # Reset detect objects, so none of them build into the executable.
diff --git a/detection/detection.cpp b/engines/detection.cpp
similarity index 90%
rename from detection/detection.cpp
rename to engines/detection.cpp
index 222dcc84e1..64d8a9b0db 100644
--- a/detection/detection.cpp
+++ b/engines/detection.cpp
@@ -24,7 +24,7 @@
 #include "base/plugins.h"
 #include "engines/metaengine.h"
 #include "engines/advanceddetector.h"
-#include "detection/detection.h"
+#include "engines/detection.h"
 
 const char *Detection::getName() const {
     return "detection";
@@ -37,11 +37,11 @@ Detection::Detection() {
 			extern PluginObject *g_##ID##_getObject(); \
 			_pl.push_back(new StaticPlugin(g_##ID##_getObject(), g_##ID##_type));
 
-    #include "detection/detection_table.h"
+    #include "engines/detection_table.h"
 }
 
 Detection::~Detection() {
 }
 
-REGISTER_PLUGIN_DYNAMIC(DETECTION, PLUGIN_TYPE_DETECTION, Detection);
+REGISTER_PLUGIN_DYNAMIC(DETECTION_DYNAMIC, PLUGIN_TYPE_DETECTION, Detection);
 
diff --git a/detection/detection.h b/engines/detection.h
similarity index 100%
rename from detection/detection.h
rename to engines/detection.h


Commit: 11615faca82602bf8d98111cd382b51627e710bf
    https://github.com/scummvm/scummvm/commit/11615faca82602bf8d98111cd382b51627e710bf
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
MAKEFILES: Include dynamic building detection module if requested

Changed paths:
    Makefile.common


diff --git a/Makefile.common b/Makefile.common
index 227d4342a6..7bd2827c5a 100644
--- a/Makefile.common
+++ b/Makefile.common
@@ -78,6 +78,10 @@ KYRARPG_COMMON_OBJ := $(KYRARPG_COMMON_OBJ_ORIG)
 # Enable-rules again
 USE_RULES := 1
 
+ifneq "$(DETECTION_STATIC)" "1"
+-include $(srcdir)/engines/detect_modules.mk
+endif
+
 # Depdir information
 DEPDIRS = $(addsuffix $(DEPDIR),$(MODULE_DIRS))
 DEPFILES =


Commit: ba5368542f2910a358d54bbf0851b969625089f3
    https://github.com/scummvm/scummvm/commit/ba5368542f2910a358d54bbf0851b969625089f3
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Update header file & use DETECTION_STATIC def check to build static detection features.

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index 52bfa0bf31..f3f5702c0d 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -30,7 +30,7 @@
 #include "common/fs.h"
 #endif
 
-#include "detection/detection.h"
+#include "engines/detection.h"
 
 // Plugin versioning
 
@@ -96,7 +96,7 @@ public:
 		// Engine plugins
 		#include "engines/plugins_table.h"
 
-		#ifndef UNCACHED_PLUGINS
+		#ifdef DETECTION_STATIC
 		// Engine-detection plugins are included if we don't use uncached plugins.
 		#include "engines/detection_table.h"
 		#endif


Commit: a56dc094b99e74e663a07ac9e107074684c80f96
    https://github.com/scummvm/scummvm/commit/a56dc094b99e74e663a07ac9e107074684c80f96
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: ALL: Move detection_enums -> detection.h

- Cleans up headers quite a bit.

Changed paths:
  A engines/bbvs/detection.h
  A engines/hdb/detection.h
  A engines/lab/detection.h
  A engines/sci/detection.h
  A engines/sword2/detection.h
  A engines/sword25/detection.h
  A engines/tucker/detection.h
  R engines/access/detection_enums.h
  R engines/adl/detection_enums.h
  R engines/agi/detection_enums.h
  R engines/agos/detection_enums.h
  R engines/bbvs/detection_enums.h
  R engines/cine/detection_enums.h
  R engines/composer/detection_enums.h
  R engines/cryomni3d/detection_enums.h
  R engines/director/detection_enums.h
  R engines/dm/detection_enums.h
  R engines/dragons/detection_enums.h
  R engines/drascula/detection_enums.h
  R engines/gob/detection/detection_enums.h
  R engines/groovie/detection_enums.h
  R engines/hdb/detection_enums.h
  R engines/hugo/detection_enums.h
  R engines/illusions/detection_enums.h
  R engines/kyra/detection_enums.h
  R engines/lab/detection_enums.h
  R engines/lilliput/detection_enums.h
  R engines/lure/detection_enums.h
  R engines/made/detection_enums.h
  R engines/mads/detection_enums.h
  R engines/mohawk/detection_enums.h
  R engines/mortevielle/detection_enums.h
  R engines/parallaction/detection_enums.h
  R engines/pegasus/detection_enums.h
  R engines/prince/detection_enums.h
  R engines/saga/detection_enums.h
  R engines/sci/detection_defines.h
  R engines/sci/detection_enums.h
  R engines/sherlock/detection_enums.h
  R engines/startrek/detection_enums.h
  R engines/sword2/detection_enums.h
  R engines/sword25/detection_enums.h
  R engines/tinsel/detection_enums.h
  R engines/tony/detection_enums.h
  R engines/tsage/detection_enums.h
  R engines/tucker/detection_enums.h
  R engines/wintermute/base/base_detection_enums.h
  R engines/wintermute/detection_enums.h
  R engines/xeen/detection_enums.h
  R engines/zvision/detection_enums.h
    engines/access/access.h
    engines/access/detection.cpp
    engines/access/detection.h
    engines/adl/adl.h
    engines/adl/adl_v2.cpp
    engines/adl/detection.cpp
    engines/adl/detection.h
    engines/adl/hires4.cpp
    engines/adl/hires5.cpp
    engines/adl/metaengine.cpp
    engines/agi/agi.h
    engines/agi/detection.cpp
    engines/agi/detection.h
    engines/agos/agos.h
    engines/agos/detection.cpp
    engines/agos/detection.h
    engines/agos/obsolete.h
    engines/bbvs/bbvs.h
    engines/bbvs/detection.cpp
    engines/cine/cine.h
    engines/cine/detection.cpp
    engines/cine/detection.h
    engines/composer/composer.h
    engines/composer/detection.cpp
    engines/composer/detection.h
    engines/cryomni3d/cryomni3d.h
    engines/cryomni3d/detection.cpp
    engines/cryomni3d/detection.h
    engines/director/detection.cpp
    engines/director/detection.h
    engines/director/director.h
    engines/dm/detection.cpp
    engines/dm/detection.h
    engines/dm/dm.h
    engines/dragons/detection.cpp
    engines/dragons/detection.h
    engines/dragons/dragons.h
    engines/drascula/detection.cpp
    engines/drascula/detection.h
    engines/drascula/drascula.h
    engines/gob/detection/detection.cpp
    engines/gob/detection/detection.h
    engines/gob/gob.h
    engines/groovie/detection.cpp
    engines/groovie/detection.h
    engines/groovie/groovie.h
    engines/groovie/script.h
    engines/hdb/detection.cpp
    engines/hdb/metaengine.cpp
    engines/hugo/detection.cpp
    engines/hugo/detection.h
    engines/hugo/hugo.h
    engines/illusions/detection.cpp
    engines/illusions/detection.h
    engines/illusions/illusions.h
    engines/kyra/detection.cpp
    engines/kyra/detection.h
    engines/kyra/kyra_v1.h
    engines/lab/detection.cpp
    engines/lab/lab.h
    engines/lilliput/detection.cpp
    engines/lilliput/detection.h
    engines/lilliput/lilliput.h
    engines/lure/detection.cpp
    engines/lure/detection.h
    engines/lure/lure.h
    engines/made/detection.cpp
    engines/made/detection.h
    engines/made/made.h
    engines/mads/detection.cpp
    engines/mads/detection.h
    engines/mads/mads.h
    engines/mohawk/detection.cpp
    engines/mohawk/detection.h
    engines/mohawk/mohawk.h
    engines/mortevielle/detection.cpp
    engines/mortevielle/detection.h
    engines/mortevielle/mortevielle.h
    engines/parallaction/detection.cpp
    engines/parallaction/detection.h
    engines/parallaction/parallaction.h
    engines/pegasus/detection.cpp
    engines/pegasus/detection.h
    engines/pegasus/metaengine.cpp
    engines/prince/detection.cpp
    engines/prince/detection.h
    engines/prince/prince.h
    engines/saga/detection.cpp
    engines/saga/detection.h
    engines/saga/saga.h
    engines/sci/detection.cpp
    engines/sci/graphics/helpers_detection_enums.h
    engines/sci/sci.h
    engines/sherlock/detection.cpp
    engines/sherlock/detection.h
    engines/sherlock/sherlock.h
    engines/startrek/detection.cpp
    engines/startrek/detection.h
    engines/startrek/startrek.h
    engines/sword2/detection.cpp
    engines/sword2/detection_internal.h
    engines/sword2/sword2.h
    engines/sword25/detection.cpp
    engines/sword25/sword25.h
    engines/tinsel/detection.cpp
    engines/tinsel/detection.h
    engines/tinsel/tinsel.h
    engines/tony/detection.cpp
    engines/tony/detection.h
    engines/tony/metaengine.cpp
    engines/tsage/detection.cpp
    engines/tsage/detection.h
    engines/tsage/tsage.h
    engines/tucker/detection.cpp
    engines/tucker/tucker.h
    engines/wintermute/base/base_engine.h
    engines/wintermute/detection.cpp
    engines/wintermute/detection.h
    engines/wintermute/metaengine.cpp
    engines/wintermute/wintermute.h
    engines/xeen/detection.cpp
    engines/xeen/detection.h
    engines/xeen/xeen.h
    engines/zvision/detection.cpp
    engines/zvision/detection.h
    engines/zvision/zvision.h


diff --git a/engines/access/access.h b/engines/access/access.h
index 26cf6f4f4d..72bea7156c 100644
--- a/engines/access/access.h
+++ b/engines/access/access.h
@@ -50,7 +50,7 @@
 #include "access/scripts.h"
 #include "access/sound.h"
 #include "access/video.h"
-#include "access/detection_enums.h"
+#include "access/detection.h"
 
 /**
  * This is the namespace of the Access engine.
@@ -69,8 +69,6 @@ enum AccessDebugChannels {
 	kDebugSound     = 1 << 3
 };
 
-struct AccessGameDescription;
-
 extern const char *const _estTable[];
 
 #define ACCESS_SAVEGAME_VERSION 1
diff --git a/engines/access/detection.cpp b/engines/access/detection.cpp
index e76bc9f163..173b3ea8c7 100644
--- a/engines/access/detection.cpp
+++ b/engines/access/detection.cpp
@@ -23,7 +23,6 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 #include "access/detection.h"
-#include "access/detection_enums.h"
 
 static const PlainGameDescriptor AccessGames[] = {
 	{"amazon", "Amazon: Guardians of Eden"},
diff --git a/engines/access/detection.h b/engines/access/detection.h
index 67ee624ac2..dc8d2211ca 100644
--- a/engines/access/detection.h
+++ b/engines/access/detection.h
@@ -23,8 +23,16 @@
 #ifndef ACCESS_DETECTION_H
 #define ACCESS_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Access {
 
+enum {
+	GType_Amazon = 1,
+	GType_MartianMemorandum = 2,
+	GType_Noctropolis = 3
+};
+
 struct AccessGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/access/detection_enums.h b/engines/access/detection_enums.h
deleted file mode 100644
index 805bde83cc..0000000000
--- a/engines/access/detection_enums.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef ACCESS_DETECTION_ENUMS_H
-#define ACCESS_DETECTION_ENUMS_H
-
-namespace Access {
-
-enum {
-	GType_Amazon = 1,
-	GType_MartianMemorandum = 2,
-	GType_Noctropolis = 3
-};
-
-} // End of namespace Access
-
-#endif // ACCESS_DETECTION_ENUMS_H
diff --git a/engines/adl/adl.h b/engines/adl/adl.h
index 1035b41028..5442c89e31 100644
--- a/engines/adl/adl.h
+++ b/engines/adl/adl.h
@@ -41,7 +41,7 @@
 #include "adl/console.h"
 #include "adl/disk.h"
 #include "adl/sound.h"
-#include "adl/detection_enums.h"
+#include "adl/detection.h"
 
 namespace Common {
 class ReadStream;
@@ -62,7 +62,6 @@ Common::Platform getPlatform(const AdlGameDescription &desc);
 class Console;
 class Display;
 class GraphicsMan;
-struct AdlGameDescription;
 class ScriptEnv;
 
 enum kDebugChannels {
diff --git a/engines/adl/adl_v2.cpp b/engines/adl/adl_v2.cpp
index d13455c353..e30502eac9 100644
--- a/engines/adl/adl_v2.cpp
+++ b/engines/adl/adl_v2.cpp
@@ -26,7 +26,7 @@
 #include "adl/adl_v2.h"
 #include "adl/display.h"
 #include "adl/graphics.h"
-#include "adl/detection_enums.h"
+#include "adl/detection.h"
 
 namespace Adl {
 
diff --git a/engines/adl/detection.cpp b/engines/adl/detection.cpp
index fcb5b2bcd4..11603e231b 100644
--- a/engines/adl/detection.cpp
+++ b/engines/adl/detection.cpp
@@ -27,7 +27,6 @@
 
 #include "engines/advancedDetector.h"
 
-#include "adl/detection_enums.h"
 #include "adl/detection.h"
 #include "adl/disk.h"
 #include "adl/disk_image_helpers.h"
diff --git a/engines/adl/detection.h b/engines/adl/detection.h
index b1f84aaa89..c609530b1f 100644
--- a/engines/adl/detection.h
+++ b/engines/adl/detection.h
@@ -23,8 +23,47 @@
 #ifndef ADL_DETECTION_H
 #define ADL_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Adl {
 
+#define SAVEGAME_VERSION 0
+#define SAVEGAME_NAME_LEN 32
+
+enum GameType {
+	GAME_TYPE_NONE,
+	GAME_TYPE_HIRES0,
+	GAME_TYPE_HIRES1,
+	GAME_TYPE_HIRES2,
+	GAME_TYPE_HIRES3,
+	GAME_TYPE_HIRES4,
+	GAME_TYPE_HIRES5,
+	GAME_TYPE_HIRES6
+};
+
+/*
+ * ====== Mystery House supported versions ======
+ * GAME_VER_HR1_SIMI:
+ * - Instructions always shown (no prompt)
+ * - Instructions contain Simi Valley address
+ * - On-Line Systems title screen in main executable only and waits for key
+ * GAME_VER_HR1_COARSE:
+ * - Longer instructions, now containing Coarsegold address
+ * - On-Line Systems title screen with instructions prompt
+ * GAME_VER_HR1_PD:
+ * - Public Domain disclaimer on startup
+ * - Sierra On-Line title screen with instructions prompt
+ *
+ * Note: there are probably at least two or three more variants
+ */
+
+enum GameVersion {
+	GAME_VER_NONE = 0,
+	GAME_VER_HR1_SIMI = 0,
+	GAME_VER_HR1_COARSE,
+	GAME_VER_HR1_PD
+};
+
 struct AdlGameDescription {
 	ADGameDescription desc;
 	GameType gameType;
diff --git a/engines/adl/detection_enums.h b/engines/adl/detection_enums.h
deleted file mode 100644
index da5461c118..0000000000
--- a/engines/adl/detection_enums.h
+++ /dev/null
@@ -1,69 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef ADL_DETECTION_ENUMS_H
-#define ADL_DETECTION_ENUMS_H
-
-namespace Adl {
-
-#define SAVEGAME_VERSION 0
-#define SAVEGAME_NAME_LEN 32
-
-enum GameType {
-	GAME_TYPE_NONE,
-	GAME_TYPE_HIRES0,
-	GAME_TYPE_HIRES1,
-	GAME_TYPE_HIRES2,
-	GAME_TYPE_HIRES3,
-	GAME_TYPE_HIRES4,
-	GAME_TYPE_HIRES5,
-	GAME_TYPE_HIRES6
-};
-
-/*
- * ====== Mystery House supported versions ======
- * GAME_VER_HR1_SIMI:
- * - Instructions always shown (no prompt)
- * - Instructions contain Simi Valley address
- * - On-Line Systems title screen in main executable only and waits for key
- * GAME_VER_HR1_COARSE:
- * - Longer instructions, now containing Coarsegold address
- * - On-Line Systems title screen with instructions prompt
- * GAME_VER_HR1_PD:
- * - Public Domain disclaimer on startup
- * - Sierra On-Line title screen with instructions prompt
- *
- * Note: there are probably at least two or three more variants
- */
-
-enum GameVersion {
-	GAME_VER_NONE = 0,
-	GAME_VER_HR1_SIMI = 0,
-	GAME_VER_HR1_COARSE,
-	GAME_VER_HR1_PD
-};
-
-struct AdlGameDescription;
-
-} // End of namespace Adl
-
-#endif // ADL_DETECTION_ENUMS_H
diff --git a/engines/adl/hires4.cpp b/engines/adl/hires4.cpp
index b251d44d97..626e23b6d6 100644
--- a/engines/adl/hires4.cpp
+++ b/engines/adl/hires4.cpp
@@ -29,7 +29,7 @@
 #include "common/memstream.h"
 
 #include "adl/adl_v3.h"
-#include "adl/detection_enums.h"
+#include "adl/detection.h"
 #include "adl/display_a2.h"
 #include "adl/graphics.h"
 #include "adl/disk.h"
diff --git a/engines/adl/hires5.cpp b/engines/adl/hires5.cpp
index ef8749eedd..399671a1de 100644
--- a/engines/adl/hires5.cpp
+++ b/engines/adl/hires5.cpp
@@ -27,7 +27,7 @@
 #include "common/stream.h"
 
 #include "adl/adl_v4.h"
-#include "adl/detection_enums.h"
+#include "adl/detection.h"
 #include "adl/display_a2.h"
 #include "adl/graphics.h"
 #include "adl/disk.h"
diff --git a/engines/adl/metaengine.cpp b/engines/adl/metaengine.cpp
index a7dd3cdf51..a479c5ef1f 100644
--- a/engines/adl/metaengine.cpp
+++ b/engines/adl/metaengine.cpp
@@ -28,7 +28,6 @@
 
 #include "graphics/thumbnail.h"
 
-#include "adl/detection_enums.h"
 #include "adl/detection.h"
 #include "adl/disk_image_helpers.h"
 
diff --git a/engines/agi/agi.h b/engines/agi/agi.h
index 1235c6d92a..f6d4b10ca4 100644
--- a/engines/agi/agi.h
+++ b/engines/agi/agi.h
@@ -44,7 +44,7 @@
 #include "agi/picture.h"
 #include "agi/logic.h"
 #include "agi/sound.h"
-#include "agi/detection_enums.h"
+#include "agi/detection.h"
 
 namespace Common {
 class RandomSource;
@@ -105,8 +105,6 @@ typedef signed int Err;
 
 #define CMD_BSIZE 12
 
-struct AGIGameDescription;
-
 enum {
 	NO_GAMEDIR = 0,
 	GAMEDIR
diff --git a/engines/agi/detection.cpp b/engines/agi/detection.cpp
index 10b4772f85..e3a87feb1e 100644
--- a/engines/agi/detection.cpp
+++ b/engines/agi/detection.cpp
@@ -28,7 +28,6 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "agi/detection_enums.h"
 #include "agi/detection.h"
 #include "agi/wagparser.h" // for fallback detection
 
diff --git a/engines/agi/detection.h b/engines/agi/detection.h
index 936ed786aa..56a6e50261 100644
--- a/engines/agi/detection.h
+++ b/engines/agi/detection.h
@@ -23,8 +23,60 @@
 #ifndef AGI_DETECTION_H
 #define AGI_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Agi {
 
+enum AgiGameType {
+	GType_PreAGI = 0,
+	GType_V1 = 1,
+	GType_V2 = 2,
+	GType_V3 = 3
+};
+
+enum AgiGameID {
+	GID_AGIDEMO,
+	GID_BC,
+	GID_DDP,
+	GID_GOLDRUSH,
+	GID_KQ1,
+	GID_KQ2,
+	GID_KQ3,
+	GID_KQ4,
+	GID_LSL1,
+	GID_MH1,
+	GID_MH2,
+	GID_MIXEDUP,
+	GID_PQ1,
+	GID_SQ1,
+	GID_SQ2,
+	GID_XMASCARD,
+	GID_FANMADE,
+	GID_GETOUTTASQ, // Fanmade
+	GID_MICKEY,     // PreAGI
+	GID_WINNIE,     // PreAGI
+	GID_TROLL       // PreAGI
+};
+
+//
+// GF_OLDAMIGAV20 means that the interpreter is an old Amiga AGI interpreter that
+// uses value 20 for the computer type (v20 i.e. vComputer) rather than the usual value 5.
+//
+enum AgiGameFeatures {
+	GF_AGIMOUSE    = (1 << 0), // this disables "Click-to-walk mouse interface"
+	GF_AGDS        = (1 << 1),
+	GF_AGI256      = (1 << 2), // marks fanmade AGI-256 games
+	GF_MACGOLDRUSH = (1 << 3), // use "grdir" instead of "dir" for volume loading
+	GF_FANMADE     = (1 << 4), // marks fanmade games
+	GF_OLDAMIGAV20 = (1 << 5),
+	GF_2GSOLDSOUND = (1 << 6)
+};
+
+enum BooterDisks {
+	BooterDisk1 = 0,
+	BooterDisk2 = 1
+};
+
 struct AGIGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/agi/detection_enums.h b/engines/agi/detection_enums.h
deleted file mode 100644
index 66f9384c7f..0000000000
--- a/engines/agi/detection_enums.h
+++ /dev/null
@@ -1,80 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef AGI_DETECTION_ENUMS_H
-#define AGI_DETECTION_ENUMS_H
-
-namespace Agi {
-
-enum AgiGameType {
-	GType_PreAGI = 0,
-	GType_V1 = 1,
-	GType_V2 = 2,
-	GType_V3 = 3
-};
-
-enum AgiGameID {
-	GID_AGIDEMO,
-	GID_BC,
-	GID_DDP,
-	GID_GOLDRUSH,
-	GID_KQ1,
-	GID_KQ2,
-	GID_KQ3,
-	GID_KQ4,
-	GID_LSL1,
-	GID_MH1,
-	GID_MH2,
-	GID_MIXEDUP,
-	GID_PQ1,
-	GID_SQ1,
-	GID_SQ2,
-	GID_XMASCARD,
-	GID_FANMADE,
-	GID_GETOUTTASQ, // Fanmade
-	GID_MICKEY,     // PreAGI
-	GID_WINNIE,     // PreAGI
-	GID_TROLL       // PreAGI
-};
-
-//
-// GF_OLDAMIGAV20 means that the interpreter is an old Amiga AGI interpreter that
-// uses value 20 for the computer type (v20 i.e. vComputer) rather than the usual value 5.
-//
-enum AgiGameFeatures {
-	GF_AGIMOUSE    = (1 << 0), // this disables "Click-to-walk mouse interface"
-	GF_AGDS        = (1 << 1),
-	GF_AGI256      = (1 << 2), // marks fanmade AGI-256 games
-	GF_MACGOLDRUSH = (1 << 3), // use "grdir" instead of "dir" for volume loading
-	GF_FANMADE     = (1 << 4), // marks fanmade games
-	GF_OLDAMIGAV20 = (1 << 5),
-	GF_2GSOLDSOUND = (1 << 6)
-};
-
-enum BooterDisks {
-	BooterDisk1 = 0,
-	BooterDisk2 = 1
-};
-
-} // End of namespace Agi
-
-#endif // AGI_DETECTION_ENUMS_H
diff --git a/engines/agos/agos.h b/engines/agos/agos.h
index eee7406c87..f8ad420007 100644
--- a/engines/agos/agos.h
+++ b/engines/agos/agos.h
@@ -35,7 +35,7 @@
 #include "audio/mixer.h"
 
 #include "agos/vga.h"
-#include "agos/detection_enums.h"
+#include "agos/detection.h"
 
 /**
  * This is the namespace of the AGOS engine.
@@ -184,8 +184,6 @@ enum EventType {
 	MONSTER_DAMAGE_EVENT = 1 << 5
 };
 
-struct AGOSGameDescription;
-
 struct GameSpecificSettings;
 
 class Debugger;
diff --git a/engines/agos/detection.cpp b/engines/agos/detection.cpp
index 32dd815412..6626c980e7 100644
--- a/engines/agos/detection.cpp
+++ b/engines/agos/detection.cpp
@@ -30,7 +30,6 @@
 #include "common/installshield_cab.h"
 
 #include "agos/detection.h"
-#include "agos/detection_enums.h"
 #include "agos/intern_detection.h"
 #include "agos/obsolete.h" // Obsolete ID table.
 
diff --git a/engines/agos/detection.h b/engines/agos/detection.h
index fde741c438..1056c97879 100644
--- a/engines/agos/detection.h
+++ b/engines/agos/detection.h
@@ -23,8 +23,21 @@
 #ifndef AGOS_DETECTION_H
 #define AGOS_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace AGOS {
 
+enum SIMONGameType {
+	GType_PN = 0,
+	GType_ELVIRA1 = 1,
+	GType_ELVIRA2 = 2,
+	GType_WW = 3,
+	GType_SIMON1 = 4,
+	GType_SIMON2 = 5,
+	GType_FF = 6,
+	GType_PP = 7
+};
+
 struct AGOSGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/agos/detection_enums.h b/engines/agos/detection_enums.h
deleted file mode 100644
index 3dee3df101..0000000000
--- a/engines/agos/detection_enums.h
+++ /dev/null
@@ -1,42 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef AGOS_DETECTION_ENUMS_H
-#define AGOS_DETECTION_ENUMS_H
-
-namespace AGOS {
-
-// Enums related to detection, from the main agos/agos.h file.
-enum SIMONGameType {
-	GType_PN = 0,
-	GType_ELVIRA1 = 1,
-	GType_ELVIRA2 = 2,
-	GType_WW = 3,
-	GType_SIMON1 = 4,
-	GType_SIMON2 = 5,
-	GType_FF = 6,
-	GType_PP = 7
-};
-
-} // End of namespace AGOS
-
-#endif // AGOS_DETECTION_ENUMS_H
diff --git a/engines/agos/obsolete.h b/engines/agos/obsolete.h
index 00ea8ef2cd..84e373516e 100644
--- a/engines/agos/obsolete.h
+++ b/engines/agos/obsolete.h
@@ -20,6 +20,8 @@
  *
  */
 
+#ifndef AGOS_OBSOLETE_H
+#define AGOS_OBSOLETE_H
 
 static const Engines::ObsoleteGameID obsoleteGameIDsTable[] = {
 	{"simon1acorn", "simon1", Common::kPlatformAcorn},
@@ -35,3 +37,5 @@ static const Engines::ObsoleteGameID obsoleteGameIDsTable[] = {
 	{"simon2win", "simon2", Common::kPlatformWindows},
 	{0, 0, Common::kPlatformUnknown}
 };
+
+#endif // AGOS_OBSOLETE_H
diff --git a/engines/bbvs/bbvs.h b/engines/bbvs/bbvs.h
index d513c679f2..e061fb98a0 100644
--- a/engines/bbvs/bbvs.h
+++ b/engines/bbvs/bbvs.h
@@ -36,7 +36,7 @@
 
 #include "engines/engine.h"
 
-#include "bbvs/detection_enums.h"
+#include "bbvs/detection.h"
 
 struct ADGameDescription;
 
diff --git a/engines/bbvs/detection.cpp b/engines/bbvs/detection.cpp
index af1942f411..a5d30d8806 100644
--- a/engines/bbvs/detection.cpp
+++ b/engines/bbvs/detection.cpp
@@ -23,7 +23,7 @@
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
 
-#include "bbvs/detection_enums.h"
+#include "bbvs/detection.h"
 
 static const PlainGameDescriptor bbvsGames[] = {
 	{ "bbvs", "Beavis and Butt-head in Virtual Stupidity" },
diff --git a/engines/bbvs/detection_enums.h b/engines/bbvs/detection.h
similarity index 91%
rename from engines/bbvs/detection_enums.h
rename to engines/bbvs/detection.h
index 919327cfd7..01d75218d7 100644
--- a/engines/bbvs/detection_enums.h
+++ b/engines/bbvs/detection.h
@@ -20,8 +20,8 @@
  *
  */
 
-#ifndef BBVS_DETECTION_ENUMS_H
-#define BBVS_DETECTION_ENUMS_H
+#ifndef BBVS_DETECTION_H
+#define BBVS_DETECTION_H
 
 namespace Bbvs {
 
@@ -31,4 +31,4 @@ enum {
 
 } // End of namespace Bbvs
 
-#endif // BBVS_DETECTION_ENUMS_H
+#endif // BBVS_DETECTION_H
diff --git a/engines/cine/cine.h b/engines/cine/cine.h
index aec244e440..2ae6208c6c 100644
--- a/engines/cine/cine.h
+++ b/engines/cine/cine.h
@@ -48,7 +48,7 @@
 #include "cine/various.h"
 #include "cine/console.h"
 #include "cine/sound.h"
-#include "cine/detection_enums.h"
+#include "cine/detection.h"
 
 //#define DUMP_SCRIPTS
 
@@ -82,7 +82,6 @@
  */
 namespace Cine {
 
-struct CINEGameDescription;
 struct SeqListElement;
 
 struct VolumeResource {
diff --git a/engines/cine/detection.cpp b/engines/cine/detection.cpp
index 311c922507..7b183b6868 100644
--- a/engines/cine/detection.cpp
+++ b/engines/cine/detection.cpp
@@ -27,7 +27,6 @@
 #include "common/translation.h"
 
 #include "cine/detection.h"
-#include "cine/detection_enums.h"
 
 static const PlainGameDescriptor cineGames[] = {
 	{"fw", "Future Wars"},
diff --git a/engines/cine/detection.h b/engines/cine/detection.h
index fa0573a5aa..ec154f80ed 100644
--- a/engines/cine/detection.h
+++ b/engines/cine/detection.h
@@ -23,8 +23,22 @@
 #ifndef CINE_DETECTION_H
 #define CINE_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Cine {
 
+enum CineGameType {
+	GType_FW = 1,
+	GType_OS
+};
+
+enum CineGameFeatures {
+	GF_CD =   1 << 0,
+	GF_DEMO = 1 << 1,
+	GF_ALT_FONT = 1 << 2,
+	GF_CRYPTED_BOOT_PRC = 1 << 3
+};
+
 struct CINEGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/cine/detection_enums.h b/engines/cine/detection_enums.h
deleted file mode 100644
index 2d37a005fe..0000000000
--- a/engines/cine/detection_enums.h
+++ /dev/null
@@ -1,42 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef CINE_DETECTION_ENUMS_H
-#define CINE_DETECTION_ENUMS_H
-
-namespace Cine {
-
-enum CineGameType {
-	GType_FW = 1,
-	GType_OS
-};
-
-enum CineGameFeatures {
-	GF_CD =   1 << 0,
-	GF_DEMO = 1 << 1,
-	GF_ALT_FONT = 1 << 2,
-	GF_CRYPTED_BOOT_PRC = 1 << 3
-};
-
-} // End of namespace Cine
-
-#endif // CINE_DETECTION_ENUMS_H
diff --git a/engines/composer/composer.h b/engines/composer/composer.h
index 43716d648b..3daa8040b8 100644
--- a/engines/composer/composer.h
+++ b/engines/composer/composer.h
@@ -44,7 +44,7 @@
 
 #include "composer/resource.h"
 #include "composer/console.h"
-#include "composer/detection_enums.h"
+#include "composer/detection.h"
 
 namespace Audio {
 	class QueuingAudioStream;
@@ -52,8 +52,6 @@ namespace Audio {
 
 namespace Composer {
 
-struct ComposerGameDescription;
-
 class Archive;
 struct Animation;
 class ComposerEngine;
diff --git a/engines/composer/detection.cpp b/engines/composer/detection.cpp
index f548e00c59..57cc9bcbbd 100644
--- a/engines/composer/detection.cpp
+++ b/engines/composer/detection.cpp
@@ -23,7 +23,6 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "composer/detection_enums.h"
 #include "composer/detection.h"
 
 static const PlainGameDescriptor composerGames[] = {
diff --git a/engines/composer/detection.h b/engines/composer/detection.h
index d1871f3c9f..0688b95d55 100644
--- a/engines/composer/detection.h
+++ b/engines/composer/detection.h
@@ -23,8 +23,21 @@
 #ifndef COMPOSER_DETECTION_H
 #define COMPOSER_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Composer {
 
+enum GameType {
+	GType_ComposerV1,
+	GType_ComposerV2
+};
+
+enum GameFileTypes {
+	GAME_CONFIGFILE     = 1 << 0,    // Game configuration
+	GAME_SCRIPTFILE     = 1 << 1,    // Game script
+	GAME_EXECUTABLE     = 1 << 2     // Game executable
+};
+
 struct ComposerGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/composer/detection_enums.h b/engines/composer/detection_enums.h
deleted file mode 100644
index 981435b681..0000000000
--- a/engines/composer/detection_enums.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef COMPOSER_DETECTION_ENUMS_H
-#define COMPOSER_DETECTION_ENUMS_H
-
-namespace Composer {
-
-enum GameType {
-	GType_ComposerV1,
-	GType_ComposerV2
-};
-
-enum GameFileTypes {
-	GAME_CONFIGFILE     = 1 << 0,    // Game configuration
-	GAME_SCRIPTFILE     = 1 << 1,    // Game script
-	GAME_EXECUTABLE     = 1 << 2     // Game executable
-};
-
-} // End of namespace Composer
-
-#endif // COMPOSER_DETECTION_ENUMS_H
diff --git a/engines/cryomni3d/cryomni3d.h b/engines/cryomni3d/cryomni3d.h
index d0dad279cf..f9b88babe3 100644
--- a/engines/cryomni3d/cryomni3d.h
+++ b/engines/cryomni3d/cryomni3d.h
@@ -38,7 +38,7 @@
 #include "cryomni3d/font_manager.h"
 #include "cryomni3d/objects.h"
 #include "cryomni3d/sprites.h"
-#include "cryomni3d/detection_enums.h"
+#include "cryomni3d/detection.h"
 
 class OSystem;
 
@@ -64,8 +64,6 @@ namespace CryOmni3D {
 
 class DATSeekableStream;
 
-struct CryOmni3DGameDescription;
-
 // Engine Debug Flags
 enum {
 	kDebugFile     = (1 << 0),
diff --git a/engines/cryomni3d/detection.cpp b/engines/cryomni3d/detection.cpp
index 78f119a117..054af4dbae 100644
--- a/engines/cryomni3d/detection.cpp
+++ b/engines/cryomni3d/detection.cpp
@@ -28,7 +28,6 @@
 #include "common/md5.h"
 
 #include "cryomni3d/detection.h"
-#include "cryomni3d/detection_enums.h"
 
 namespace CryOmni3D {
 
diff --git a/engines/cryomni3d/detection.h b/engines/cryomni3d/detection.h
index dba8dc8788..d90b079cfc 100644
--- a/engines/cryomni3d/detection.h
+++ b/engines/cryomni3d/detection.h
@@ -23,8 +23,28 @@
 #ifndef CRYOMNI3D_DETECTION_H
 #define CRYOMNI3D_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace CryOmni3D {
 
+enum CryOmni3DGameType {
+	GType_VERSAILLES
+};
+
+enum CryOmni3DGameFeatures {
+	GF_VERSAILLES_FONTS_MASK               = (3 << 0), // Fonts flag mask
+	GF_VERSAILLES_FONTS_NUMERIC            = (0 << 0), // Fonts are font01.crf, ...
+	GF_VERSAILLES_FONTS_SET_A              = (1 << 0), // Fonts are for French Macintosh (development version)
+	GF_VERSAILLES_FONTS_SET_B              = (2 << 0), // Standard set (Helvet12 is used for debugging docs)
+	GF_VERSAILLES_FONTS_SET_C              = (3 << 0), // Fonts for Italian version (Helvet12 is used for docs texts)
+
+	GF_VERSAILLES_AUDIOPADDING_NO          = (0 << 2), // Audio files have underscore padding before extension
+	GF_VERSAILLES_AUDIOPADDING_YES         = (1 << 2), // Audio files have underscore padding before extension
+
+	GF_VERSAILLES_LINK_STANDARD            = (0 << 3), // Links file is lien_doc.txt
+	GF_VERSAILLES_LINK_LOCALIZED           = (1 << 3)  // Links file is taken from cryomni3d.dat
+};
+
 struct CryOmni3DGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/cryomni3d/detection_enums.h b/engines/cryomni3d/detection_enums.h
deleted file mode 100644
index b619443c99..0000000000
--- a/engines/cryomni3d/detection_enums.h
+++ /dev/null
@@ -1,48 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef CRYOMNI3D_DETECTION_ENUMS_H
-#define CRYOMNI3D_DETECTION_ENUMS_H
-
-namespace CryOmni3D {
-
-enum CryOmni3DGameType {
-	GType_VERSAILLES
-};
-
-enum CryOmni3DGameFeatures {
-	GF_VERSAILLES_FONTS_MASK               = (3 << 0), // Fonts flag mask
-	GF_VERSAILLES_FONTS_NUMERIC            = (0 << 0), // Fonts are font01.crf, ...
-	GF_VERSAILLES_FONTS_SET_A              = (1 << 0), // Fonts are for French Macintosh (development version)
-	GF_VERSAILLES_FONTS_SET_B              = (2 << 0), // Standard set (Helvet12 is used for debugging docs)
-	GF_VERSAILLES_FONTS_SET_C              = (3 << 0), // Fonts for Italian version (Helvet12 is used for docs texts)
-
-	GF_VERSAILLES_AUDIOPADDING_NO          = (0 << 2), // Audio files have underscore padding before extension
-	GF_VERSAILLES_AUDIOPADDING_YES         = (1 << 2), // Audio files have underscore padding before extension
-
-	GF_VERSAILLES_LINK_STANDARD            = (0 << 3), // Links file is lien_doc.txt
-	GF_VERSAILLES_LINK_LOCALIZED           = (1 << 3)  // Links file is taken from cryomni3d.dat
-};
-
-} // End of namespace CryOmni3D
-
-#endif // CRYOMNI3D_DETECTION_ENUMS_H
diff --git a/engines/director/detection.cpp b/engines/director/detection.cpp
index 662ee94b83..6f4bce2f79 100644
--- a/engines/director/detection.cpp
+++ b/engines/director/detection.cpp
@@ -26,7 +26,6 @@
 
 #include "common/file.h"
 
-#include "director/detection_enums.h"
 #include "director/detection.h"
 
 static const PlainGameDescriptor directorGames[] = {
diff --git a/engines/director/detection.h b/engines/director/detection.h
index 7f4b7441c5..39f4e72fe6 100644
--- a/engines/director/detection.h
+++ b/engines/director/detection.h
@@ -23,8 +23,16 @@
 #ifndef DIRECTOR_DETECTION_H
 #define DIRECTOR_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Director {
 
+enum DirectorGameGID {
+	GID_GENERIC,
+	GID_TEST,
+	GID_TESTALL
+};
+
 struct DirectorGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/director/detection_enums.h b/engines/director/detection_enums.h
deleted file mode 100644
index 21630a4fcd..0000000000
--- a/engines/director/detection_enums.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef DIRECTOR_DETECTION_ENUMS_H
-#define DIRECTOR_DETECTION_ENUMS_H
-
-namespace Director {
-
-enum DirectorGameGID {
-	GID_GENERIC,
-	GID_TEST,
-	GID_TESTALL
-};
-
-} // End of namespace Director
-
-#endif // DIRECTOR_DETECTION_ENUMS_H
diff --git a/engines/director/director.h b/engines/director/director.h
index 1b20960b97..37e33b057b 100644
--- a/engines/director/director.h
+++ b/engines/director/director.h
@@ -36,7 +36,7 @@
 
 #include "director/types.h"
 #include "director/util.h"
-#include "director/detection_enums.h"
+#include "director/detection.h"
 
 namespace Common {
 class MacResManager;
@@ -56,7 +56,6 @@ namespace Director {
 
 class Archive;
 class Cast;
-struct DirectorGameDescription;
 class DirectorSound;
 class Lingo;
 class Movie;
diff --git a/engines/dm/detection.cpp b/engines/dm/detection.cpp
index aa051815f8..0a36556b1f 100644
--- a/engines/dm/detection.cpp
+++ b/engines/dm/detection.cpp
@@ -29,7 +29,6 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "dm/detection_enums.h"
 #include "dm/detection.h"
 
 namespace DM {
diff --git a/engines/dm/detection.h b/engines/dm/detection.h
index 9cc1e4f09a..4a40f02e68 100644
--- a/engines/dm/detection.h
+++ b/engines/dm/detection.h
@@ -28,8 +28,46 @@
 #ifndef DM_DETECTION_H
 #define DM_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace DM {
 
+enum OriginalSaveFormat {
+	kDMSaveFormatAcceptAny = -1,
+	kDMSaveFormatEndOfList = 0,
+	kDMSaveFormatNone = 0,
+	kDMSaveFormatAtari = 1,
+	kDMSaveFormatAmigaPC98FmTowns = 2,
+	kCSBSaveFormatAtari = 2,
+	kDMSaveFormatAppleIIgs = 3,
+	kDMSaveFormatAmiga36PC = 5,
+	kCSBSaveFormatAmigaPC98FmTowns = 5,
+	kDMSaveFormatTotal
+};
+
+enum OriginalSavePlatform {
+	kDMSavePlatformAcceptAny = -1,
+	kDMSavePlatformEndOfList = 0,
+	kDMSavePlatformNone = 0,
+	kDMSavePlatformAtariSt = 1, // @ C1_PLATFORM_ATARI_ST
+	kDMSavePlatformAppleIIgs = 2, // @ C2_PLATFORM_APPLE_IIGS
+	kDMSavePlatformAmiga = 3, // @ C3_PLATFORM_AMIGA
+	kDMSavePlatformPC98 = 5, // @ C5_PLATFORM_PC98
+	kDMSavePlatformX68000 = 6, // @ C6_PLATFORM_X68000
+	kDMSavePlatformFmTownsEN = 7, // @ C7_PLATFORM_FM_TOWNS_EN
+	kDMSavePlatformFmTownsJP = 8, // @ C8_PLATFORM_FM_TOWNS_JP
+	kDMSavePlatformPC = 9, // @ C9_PLATFORM_PC
+	kDMSavePlatformTotal
+};
+
+enum SaveTarget {
+	kDMSaveTargetAcceptAny = -1,
+	kDMSaveTargetEndOfList = 0,
+	kDMSaveTargetNone = 0,
+	kDMSaveTargetDM21 = 1,
+	kDMSaveTargetTotal
+};
+
 struct DMADGameDescription {
 	ADGameDescription _desc;
 
diff --git a/engines/dm/detection_enums.h b/engines/dm/detection_enums.h
deleted file mode 100644
index ae9978b691..0000000000
--- a/engines/dm/detection_enums.h
+++ /dev/null
@@ -1,71 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
-*
-* ScummVM is the legal property of its developers, whose names
-* are too numerous to list here. Please refer to the COPYRIGHT
-* file distributed with this source distribution.
-*
-* This program is free software; you can redistribute it and/or
-* modify it under the terms of the GNU General Public License
-* as published by the Free Software Foundation; either version 2
-* of the License, or (at your option) any later version.
-*
-* This program is distributed in the hope that it will be useful,
-* but WITHOUT ANY WARRANTY; without even the implied warranty of
-* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-* GNU General Public License for more details.
-*
-* You should have received a copy of the GNU General Public License
-* along with this program; if not, write to the Free Software
-* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
-*
-*/
-
-/*
-* Based on the Reverse Engineering work of Christophe Fontanel,
-* maintainer of the Dungeon Master Encyclopaedia (http://dmweb.free.fr/)
-*/
-
-#ifndef DM_DETECTION_ENUMS_H
-#define DM_DETECTION_ENUMS_H
-
-namespace DM {
-
-enum OriginalSaveFormat {
-	kDMSaveFormatAcceptAny = -1,
-	kDMSaveFormatEndOfList = 0,
-	kDMSaveFormatNone = 0,
-	kDMSaveFormatAtari = 1,
-	kDMSaveFormatAmigaPC98FmTowns = 2,
-	kCSBSaveFormatAtari = 2,
-	kDMSaveFormatAppleIIgs = 3,
-	kDMSaveFormatAmiga36PC = 5,
-	kCSBSaveFormatAmigaPC98FmTowns = 5,
-	kDMSaveFormatTotal
-};
-
-enum OriginalSavePlatform {
-	kDMSavePlatformAcceptAny = -1,
-	kDMSavePlatformEndOfList = 0,
-	kDMSavePlatformNone = 0,
-	kDMSavePlatformAtariSt = 1, // @ C1_PLATFORM_ATARI_ST
-	kDMSavePlatformAppleIIgs = 2, // @ C2_PLATFORM_APPLE_IIGS
-	kDMSavePlatformAmiga = 3, // @ C3_PLATFORM_AMIGA
-	kDMSavePlatformPC98 = 5, // @ C5_PLATFORM_PC98
-	kDMSavePlatformX68000 = 6, // @ C6_PLATFORM_X68000
-	kDMSavePlatformFmTownsEN = 7, // @ C7_PLATFORM_FM_TOWNS_EN
-	kDMSavePlatformFmTownsJP = 8, // @ C8_PLATFORM_FM_TOWNS_JP
-	kDMSavePlatformPC = 9, // @ C9_PLATFORM_PC
-	kDMSavePlatformTotal
-};
-
-enum SaveTarget {
-	kDMSaveTargetAcceptAny = -1,
-	kDMSaveTargetEndOfList = 0,
-	kDMSaveTargetNone = 0,
-	kDMSaveTargetDM21 = 1,
-	kDMSaveTargetTotal
-};
-
-} // End of namespace DM
-
-#endif // DM_DETECTION_ENUMS_H
diff --git a/engines/dm/dm.h b/engines/dm/dm.h
index 029b671c23..aa46979ad1 100644
--- a/engines/dm/dm.h
+++ b/engines/dm/dm.h
@@ -39,11 +39,8 @@
 #include "advancedDetector.h"
 
 #include "dm/console.h"
-#include "dm/detection_enums.h"
 #include "dm/detection.h"
 
-struct ADGameDescription;
-
 namespace DM {
 
 class DisplayMan;
diff --git a/engines/dragons/detection.cpp b/engines/dragons/detection.cpp
index 75c6f1861a..7356a4b0d8 100644
--- a/engines/dragons/detection.cpp
+++ b/engines/dragons/detection.cpp
@@ -22,7 +22,6 @@
 
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
-#include "dragons/detection_enums.h"
 #include "dragons/detection.h"
 
 static const PlainGameDescriptor dragonsGames[] = {
diff --git a/engines/dragons/detection.h b/engines/dragons/detection.h
index 958b4c4c50..8533667a42 100644
--- a/engines/dragons/detection.h
+++ b/engines/dragons/detection.h
@@ -23,8 +23,15 @@
 #ifndef DRAGONS_DETECTION_H
 #define DRAGONS_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Dragons {
 
+enum {
+	kGameIdDragons = 1,
+	kGameIdDragonsBadExtraction = 2
+};
+
 struct DragonsGameDescription {
 	ADGameDescription desc;
 	int gameId;
diff --git a/engines/dragons/detection_enums.h b/engines/dragons/detection_enums.h
deleted file mode 100644
index 5822ad99ba..0000000000
--- a/engines/dragons/detection_enums.h
+++ /dev/null
@@ -1,35 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
-
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
-
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef DRAGONS_DETECTION_ENUMS_H
-#define DRAGONS_DETECTION_ENUMS_H
-
-namespace Dragons {
-
-enum {
-	kGameIdDragons = 1,
-	kGameIdDragonsBadExtraction = 2
-};
-
-} // End of namespace Dragons
-
-#endif // DRAGONS_DETECTION_ENUMS_H
diff --git a/engines/dragons/dragons.h b/engines/dragons/dragons.h
index c3b2883c93..182d5164bb 100644
--- a/engines/dragons/dragons.h
+++ b/engines/dragons/dragons.h
@@ -25,7 +25,6 @@
 #include "gui/EventRecorder.h"
 #include "engines/engine.h"
 #include "dragons/specialopcodes.h"
-#include "dragons/detection_enums.h"
 #include "dragons/detection.h"
 
 namespace Dragons {
diff --git a/engines/drascula/detection.cpp b/engines/drascula/detection.cpp
index d8eb9b0a5a..98a4f7c5e1 100644
--- a/engines/drascula/detection.cpp
+++ b/engines/drascula/detection.cpp
@@ -26,7 +26,6 @@
 
 #include "engines/advancedDetector.h"
 
-#include "drascula/detection_enums.h"
 #include "drascula/detection.h"
 
 static const PlainGameDescriptor drasculaGames[] = {
diff --git a/engines/drascula/detection.h b/engines/drascula/detection.h
index 9e8550bac8..73576a18c6 100644
--- a/engines/drascula/detection.h
+++ b/engines/drascula/detection.h
@@ -20,10 +20,21 @@
  *
  */
 
+#ifndef DRASCULA_DETECTION_H
+#define DRASCULA_DETECTION_H
+
+#include "engines/advancedDetector.h"
+
 namespace Drascula {
 
+enum DrasculaGameFeatures {
+	GF_PACKED = (1 << 0)
+};
+
 struct DrasculaGameDescription {
 	ADGameDescription desc;
 };
 
 } // End of namespace Drascula
+
+#endif // DRASCULA_DETECTION_H
diff --git a/engines/drascula/detection_enums.h b/engines/drascula/detection_enums.h
deleted file mode 100644
index ba46883146..0000000000
--- a/engines/drascula/detection_enums.h
+++ /dev/null
@@ -1,29 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-namespace Drascula {
-
-enum DrasculaGameFeatures {
-	GF_PACKED = (1 << 0)
-};
-
-} // End of namespace Drascula
diff --git a/engines/drascula/drascula.h b/engines/drascula/drascula.h
index 749f9c3033..f49d30bfd5 100644
--- a/engines/drascula/drascula.h
+++ b/engines/drascula/drascula.h
@@ -39,7 +39,7 @@
 #include "engines/savestate.h"
 
 #include "drascula/console.h"
-#include "drascula/detection_enums.h"
+#include "drascula/detection.h"
 
 #include "audio/mixer.h"
 
diff --git a/engines/gob/detection/detection.cpp b/engines/gob/detection/detection.cpp
index 9cb9fea4ec..d408dbd093 100644
--- a/engines/gob/detection/detection.cpp
+++ b/engines/gob/detection/detection.cpp
@@ -24,7 +24,7 @@
 #include "engines/advancedDetector.h"
 
 #include "gob/dataio.h"
-#include "gob/detection/detection_enums.h"
+#include "gob/detection/detection.h"
 #include "gob/detection/tables.h"
 
 class GobMetaEngine : public AdvancedMetaEngine {
diff --git a/engines/gob/detection/detection.h b/engines/gob/detection/detection.h
index 073b04a65e..15ee5dd714 100644
--- a/engines/gob/detection/detection.h
+++ b/engines/gob/detection/detection.h
@@ -23,8 +23,52 @@
 #ifndef GOB_DETECTION_H
 #define GOB_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Gob {
 
+// WARNING: Reordering these will invalidate save games!
+//          Add new games to the bottom of the list.
+enum GameType {
+	kGameTypeNone = 0,
+	kGameTypeGob1,
+	kGameTypeGob2,
+	kGameTypeGob3,
+	kGameTypeWoodruff,
+	kGameTypeBargon,
+	kGameTypeWeen,
+	kGameTypeLostInTime,
+	kGameTypeInca2,
+	kGameTypeDynasty,
+	kGameTypeUrban,
+	kGameTypePlaytoons,
+	kGameTypeBambou,
+	kGameTypeFascination,
+	kGameTypeGeisha,
+	kGameTypeAdi2,
+	kGameTypeAdi4,
+	kGameTypeAdibou2,
+	kGameTypeAdibou1,
+	kGameTypeAbracadabra,
+	kGameTypeBabaYaga,
+	kGameTypeLittleRed,
+	kGameTypeOnceUponATime, // Need more inspection to see if Baba Yaga or Abracadabra
+	kGameTypeAJWorld,
+	kGameTypeCrousti
+};
+
+enum Features {
+	kFeaturesNone      =      0,
+	kFeaturesCD        = 1 << 0,
+	kFeaturesEGA       = 1 << 1,
+	kFeaturesAdLib     = 1 << 2,
+	kFeaturesSCNDemo   = 1 << 3,
+	kFeaturesBATDemo   = 1 << 4,
+	kFeatures640x480   = 1 << 5,
+	kFeatures800x600   = 1 << 6,
+	kFeaturesTrueColor = 1 << 7
+};
+
 struct GOBGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/gob/detection/detection_enums.h b/engines/gob/detection/detection_enums.h
deleted file mode 100644
index d3cb3c55b6..0000000000
--- a/engines/gob/detection/detection_enums.h
+++ /dev/null
@@ -1,72 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef GOB_DETECTION_ENUMS_H
-#define GOB_DETECTION_ENUMS_H
-
-namespace Gob {
-
-// WARNING: Reordering these will invalidate save games!
-//          Add new games to the bottom of the list.
-enum GameType {
-	kGameTypeNone = 0,
-	kGameTypeGob1,
-	kGameTypeGob2,
-	kGameTypeGob3,
-	kGameTypeWoodruff,
-	kGameTypeBargon,
-	kGameTypeWeen,
-	kGameTypeLostInTime,
-	kGameTypeInca2,
-	kGameTypeDynasty,
-	kGameTypeUrban,
-	kGameTypePlaytoons,
-	kGameTypeBambou,
-	kGameTypeFascination,
-	kGameTypeGeisha,
-	kGameTypeAdi2,
-	kGameTypeAdi4,
-	kGameTypeAdibou2,
-	kGameTypeAdibou1,
-	kGameTypeAbracadabra,
-	kGameTypeBabaYaga,
-	kGameTypeLittleRed,
-	kGameTypeOnceUponATime, // Need more inspection to see if Baba Yaga or Abracadabra
-	kGameTypeAJWorld,
-	kGameTypeCrousti
-};
-
-enum Features {
-	kFeaturesNone      =      0,
-	kFeaturesCD        = 1 << 0,
-	kFeaturesEGA       = 1 << 1,
-	kFeaturesAdLib     = 1 << 2,
-	kFeaturesSCNDemo   = 1 << 3,
-	kFeaturesBATDemo   = 1 << 4,
-	kFeatures640x480   = 1 << 5,
-	kFeatures800x600   = 1 << 6,
-	kFeaturesTrueColor = 1 << 7
-};
-
-} // End of namespace Gob
-
-#endif // GOB_DETECTION_ENUMS_H
diff --git a/engines/gob/gob.h b/engines/gob/gob.h
index a5275fbb77..cdf87391d9 100644
--- a/engines/gob/gob.h
+++ b/engines/gob/gob.h
@@ -31,7 +31,7 @@
 #include "engines/engine.h"
 
 #include "gob/console.h"
-#include "gob/detection/detection_enums.h"
+#include "gob/detection/detection.h"
 
 /**
  * This is the namespace of the Gob engine.
@@ -126,8 +126,6 @@ enum {
 	kDebugDemo       = 1 << 11
 };
 
-struct GOBGameDescription;
-
 class GobEngine : public Engine {
 private:
 	GameType _gameType;
diff --git a/engines/groovie/detection.cpp b/engines/groovie/detection.cpp
index c607181551..e0e4479860 100644
--- a/engines/groovie/detection.cpp
+++ b/engines/groovie/detection.cpp
@@ -24,7 +24,6 @@
 #include "common/translation.h"
 
 #include "engines/advancedDetector.h"
-#include "groovie/detection_enums.h"
 #include "groovie/detection.h"
 
 namespace Groovie {
diff --git a/engines/groovie/detection.h b/engines/groovie/detection.h
index d840d06f15..dc13950aa9 100644
--- a/engines/groovie/detection.h
+++ b/engines/groovie/detection.h
@@ -27,6 +27,11 @@
 
 namespace Groovie {
 
+enum EngineVersion {
+	kGroovieT7G,
+	kGroovieV2
+};
+
 struct GroovieGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/groovie/detection_enums.h b/engines/groovie/detection_enums.h
deleted file mode 100644
index 57bcb89567..0000000000
--- a/engines/groovie/detection_enums.h
+++ /dev/null
@@ -1,35 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef GROOVIE_DETECTION_ENUMS_H
-#define GROOVIE_DETECTION_ENUMS_H
-
-namespace Groovie {
-
-enum EngineVersion {
-	kGroovieT7G,
-	kGroovieV2
-};
-
-} // End of namespace Groovie
-
-#endif // !GROOVIE_DETECTION_ENUMS_H
diff --git a/engines/groovie/groovie.h b/engines/groovie/groovie.h
index 4d26552bf8..26d4af116b 100644
--- a/engines/groovie/groovie.h
+++ b/engines/groovie/groovie.h
@@ -28,7 +28,7 @@
 
 #include "engines/engine.h"
 #include "graphics/pixelformat.h"
-#include "groovie/detection_enums.h"
+#include "groovie/detection.h"
 
 namespace Common {
 class MacResManager;
diff --git a/engines/groovie/script.h b/engines/groovie/script.h
index 4b82a8ef50..2a09cc4a0f 100644
--- a/engines/groovie/script.h
+++ b/engines/groovie/script.h
@@ -24,7 +24,6 @@
 #define GROOVIE_SCRIPT_H
 
 #include "groovie/groovie.h"
-#include "groovie/detection_enums.h"
 
 #include "common/random.h"
 #include "common/rect.h"
diff --git a/engines/hdb/detection.cpp b/engines/hdb/detection.cpp
index 8f995787ae..e199a90fa9 100644
--- a/engines/hdb/detection.cpp
+++ b/engines/hdb/detection.cpp
@@ -24,7 +24,7 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "hdb/detection_enums.h"
+#include "hdb/detection.h"
 
 static const PlainGameDescriptor hdbGames[] = {
 	{"hdb", "Hyperspace Delivery Boy!"},
diff --git a/engines/hdb/detection_enums.h b/engines/hdb/detection.h
similarity index 100%
rename from engines/hdb/detection_enums.h
rename to engines/hdb/detection.h
diff --git a/engines/hdb/metaengine.cpp b/engines/hdb/metaengine.cpp
index a83a0402fa..6627db9c84 100644
--- a/engines/hdb/metaengine.cpp
+++ b/engines/hdb/metaengine.cpp
@@ -34,7 +34,7 @@
 
 #include "hdb/hdb.h"
 #include "hdb/input.h"
-#include "hdb/detection_enums.h"
+#include "hdb/detection.h"
 
 namespace HDB {
 
diff --git a/engines/hugo/detection.cpp b/engines/hugo/detection.cpp
index 1b261eeb2d..2559582a25 100644
--- a/engines/hugo/detection.cpp
+++ b/engines/hugo/detection.cpp
@@ -23,7 +23,6 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "hugo/detection_enums.h"
 #include "hugo/detection.h"
 
 namespace Hugo {
diff --git a/engines/hugo/detection.h b/engines/hugo/detection.h
index ef12c47312..d3836dc11c 100644
--- a/engines/hugo/detection.h
+++ b/engines/hugo/detection.h
@@ -23,8 +23,31 @@
 #ifndef HUGO_DETECTION_H
 #define HUGO_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Hugo {
 
+enum HugoGameFeatures {
+	GF_PACKED = (1 << 0) // Database
+};
+
+enum GameType {
+	kGameTypeNone  = 0,
+	kGameTypeHugo1,
+	kGameTypeHugo2,
+	kGameTypeHugo3
+};
+
+enum GameVariant {
+	kGameVariantH1Win = 0,
+	kGameVariantH2Win,
+	kGameVariantH3Win,
+	kGameVariantH1Dos,
+	kGameVariantH2Dos,
+	kGameVariantH3Dos,
+	kGameVariantNone
+};
+
 struct HugoGameDescription {
 	ADGameDescription desc;
 	GameType gameType;
diff --git a/engines/hugo/detection_enums.h b/engines/hugo/detection_enums.h
deleted file mode 100644
index 5e051f4388..0000000000
--- a/engines/hugo/detection_enums.h
+++ /dev/null
@@ -1,51 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef HUGO_DETECTION_ENUMS_H
-#define HUGO_DETECTION_ENUMS_H
-
-namespace Hugo {
-
-enum HugoGameFeatures {
-	GF_PACKED = (1 << 0) // Database
-};
-
-enum GameType {
-	kGameTypeNone  = 0,
-	kGameTypeHugo1,
-	kGameTypeHugo2,
-	kGameTypeHugo3
-};
-
-enum GameVariant {
-	kGameVariantH1Win = 0,
-	kGameVariantH2Win,
-	kGameVariantH3Win,
-	kGameVariantH1Dos,
-	kGameVariantH2Dos,
-	kGameVariantH3Dos,
-	kGameVariantNone
-};
-
-} // End of namespace Hugo
-
-#endif // HUGO_DETECTION_ENUMS_H
diff --git a/engines/hugo/hugo.h b/engines/hugo/hugo.h
index 288d73b20c..95d4c49cdb 100644
--- a/engines/hugo/hugo.h
+++ b/engines/hugo/hugo.h
@@ -27,7 +27,7 @@
 
 // This include is here temporarily while the engine is being refactored.
 #include "hugo/game.h"
-#include "hugo/detection_enums.h"
+#include "hugo/detection.h"
 
 #define HUGO_DAT_VER_MAJ 0                          // 1 byte
 #define HUGO_DAT_VER_MIN 42                         // 1 byte
@@ -146,8 +146,6 @@ enum seqTextEngine {
 	kEsAdvertise = 0
 };
 
-struct HugoGameDescription;
-
 struct Status {                                     // Game status (not saved)
 	bool     _storyModeFl;                          // Game is telling story - no commands
 	bool     _gameOverFl;                           // Game is over - hero knobbled
diff --git a/engines/illusions/detection.cpp b/engines/illusions/detection.cpp
index 4d04a6f7db..207dbee649 100644
--- a/engines/illusions/detection.cpp
+++ b/engines/illusions/detection.cpp
@@ -24,7 +24,6 @@
 
 #include "base/plugins.h"
 
-#include "illusions/detection_enums.h"
 #include "illusions/detection.h"
 
 static const PlainGameDescriptor illusionsGames[] = {
diff --git a/engines/illusions/detection.h b/engines/illusions/detection.h
index 7a3164298d..e7528e77a5 100644
--- a/engines/illusions/detection.h
+++ b/engines/illusions/detection.h
@@ -23,8 +23,15 @@
 #ifndef ILLUSIONS_DETECTION_H
 #define ILLUSIONS_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Illusions {
 
+enum {
+	kGameIdBBDOU   = 1,
+	kGameIdDuckman = 2
+};
+
 struct IllusionsGameDescription {
 	ADGameDescription desc;
 	int gameId;
diff --git a/engines/illusions/detection_enums.h b/engines/illusions/detection_enums.h
deleted file mode 100644
index 7a61817c4d..0000000000
--- a/engines/illusions/detection_enums.h
+++ /dev/null
@@ -1,35 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
-
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
-
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef ILLUSIONS_DETECTION_ENUMS_H
-#define ILLUSIONS_DETECTION_ENUMS_H
-
-namespace Illusions {
-
-enum {
-	kGameIdBBDOU   = 1,
-	kGameIdDuckman = 2
-};
-
-} // End of namespace Illusions
-
-#endif // ILLUSIONS_DETECTION_ENUMS_H
diff --git a/engines/illusions/illusions.h b/engines/illusions/illusions.h
index 73d6eced49..2e2dcfb4d6 100644
--- a/engines/illusions/illusions.h
+++ b/engines/illusions/illusions.h
@@ -38,7 +38,7 @@
 
 #include "engines/engine.h"
 #include "graphics/surface.h"
-#include "illusions/detection_enums.h"
+#include "illusions/detection.h"
 
 namespace Illusions {
 
@@ -63,7 +63,6 @@ class Cursor;
 class Dictionary;
 struct Fader;
 class FramesList;
-struct IllusionsGameDescription;
 class Input;
 class Screen;
 class ScreenText;
diff --git a/engines/kyra/detection.cpp b/engines/kyra/detection.cpp
index 295ddd7309..63443bb446 100644
--- a/engines/kyra/detection.cpp
+++ b/engines/kyra/detection.cpp
@@ -24,7 +24,6 @@
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
 
-#include "kyra/detection_enums.h"
 #include "kyra/detection.h"
 #include "kyra/detection_tables.h"
 
diff --git a/engines/kyra/detection.h b/engines/kyra/detection.h
index 18a3b7b563..a1e94410dd 100644
--- a/engines/kyra/detection.h
+++ b/engines/kyra/detection.h
@@ -23,6 +23,43 @@
 #ifndef KYRA_DETECTION_H
 #define KYRA_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
+namespace Kyra {
+
+enum {
+	GI_KYRA1 = 0,
+	GI_KYRA2 = 1,
+	GI_KYRA3 = 2,
+	GI_LOL = 4,
+	GI_EOB1 = 5,
+	GI_EOB2 = 6
+};
+
+struct GameFlags {
+	Common::Language lang;
+
+	// language overwrites of fan translations (only needed for multilingual games)
+	Common::Language fanLang;
+	Common::Language replacedLang;
+
+	Common::Platform platform;
+
+	bool isDemo               : 1;
+	bool useAltShapeHeader    : 1;    // alternative shape header (uses 2 bytes more, those are unused though)
+	bool isTalkie             : 1;
+	bool isOldFloppy          : 1;
+	bool useHiRes             : 1;
+	bool use16ColorMode       : 1;
+	bool useHiColorMode       : 1;
+	bool useDigSound          : 1;
+	bool useInstallerPackage  : 1;
+
+	byte gameID;
+};
+
+} // End of namespace Kyra
+
 namespace {
 
 struct KYRAGameDescription {
diff --git a/engines/kyra/detection_enums.h b/engines/kyra/detection_enums.h
deleted file mode 100644
index 2f603aed84..0000000000
--- a/engines/kyra/detection_enums.h
+++ /dev/null
@@ -1,61 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef KYRA_DETECTION_ENUMS_H
-#define KYRA_DETECTION_ENUMS_H
-
-namespace Kyra {
-
-enum {
-	GI_KYRA1 = 0,
-	GI_KYRA2 = 1,
-	GI_KYRA3 = 2,
-	GI_LOL = 4,
-	GI_EOB1 = 5,
-	GI_EOB2 = 6
-};
-
-struct GameFlags {
-	Common::Language lang;
-
-	// language overwrites of fan translations (only needed for multilingual games)
-	Common::Language fanLang;
-	Common::Language replacedLang;
-
-	Common::Platform platform;
-
-	bool isDemo               : 1;
-	bool useAltShapeHeader    : 1;    // alternative shape header (uses 2 bytes more, those are unused though)
-	bool isTalkie             : 1;
-	bool isOldFloppy          : 1;
-	bool useHiRes             : 1;
-	bool use16ColorMode       : 1;
-	bool useHiColorMode       : 1;
-	bool useDigSound          : 1;
-	bool useInstallerPackage  : 1;
-
-	byte gameID;
-};
-
-} // End of namespace Kyra
-
-#endif // KYRA_DETECTION_ENUMS_H
diff --git a/engines/kyra/kyra_v1.h b/engines/kyra/kyra_v1.h
index 65d02ebf25..315708033c 100644
--- a/engines/kyra/kyra_v1.h
+++ b/engines/kyra/kyra_v1.h
@@ -36,7 +36,7 @@
 
 #include "kyra/script/script.h"
 #include "kyra/engine/item.h"
-#include "kyra/detection_enums.h"
+#include "kyra/detection.h"
 
 namespace Common {
 class OutSaveFile;
diff --git a/engines/lab/detection.cpp b/engines/lab/detection.cpp
index 8a63ca3604..6985a46695 100644
--- a/engines/lab/detection.cpp
+++ b/engines/lab/detection.cpp
@@ -29,7 +29,7 @@
  */
 
 #include "engines/advancedDetector.h"
-#include "lab/detection_enums.h"
+#include "lab/detection.h"
 
 static const PlainGameDescriptor lab_setting[] = {
 	{ "lab", "Labyrinth of Time" },
diff --git a/engines/lab/detection_enums.h b/engines/lab/detection.h
similarity index 92%
rename from engines/lab/detection_enums.h
rename to engines/lab/detection.h
index a6ce1cbeec..5126fc40e7 100644
--- a/engines/lab/detection_enums.h
+++ b/engines/lab/detection.h
@@ -20,8 +20,8 @@
  *
  */
 
-#ifndef LAB_DETECTION_ENUMS_H
-#define LAB_DETECTION_ENUMS_H
+#ifndef LAB_DETECTION_H
+#define LAB_DETECTION_H
 
 namespace Lab {
 
@@ -32,4 +32,4 @@ enum GameFeatures {
 
 } // End of namespace Lab
 
-#endif // LAB_DETECTION_ENUMS_H
+#endif // LAB_DETECTION_H
diff --git a/engines/lab/lab.h b/engines/lab/lab.h
index 17667cc70f..f7200cfe6e 100644
--- a/engines/lab/lab.h
+++ b/engines/lab/lab.h
@@ -41,7 +41,7 @@
 #include "lab/console.h"
 #include "lab/image.h"
 #include "lab/labsets.h"
-#include "lab/detection_enums.h"
+#include "lab/detection.h"
 
 struct ADGameDescription;
 
diff --git a/engines/lilliput/detection.cpp b/engines/lilliput/detection.cpp
index 74d582efb7..356fceef35 100644
--- a/engines/lilliput/detection.cpp
+++ b/engines/lilliput/detection.cpp
@@ -24,7 +24,6 @@
 #include "engines/advancedDetector.h"
 #include "common/textconsole.h"
 
-#include "lilliput/detection_enums.h"
 #include "lilliput/detection.h"
 
 namespace Lilliput {
diff --git a/engines/lilliput/detection.h b/engines/lilliput/detection.h
index c86f97a219..ef077dd370 100644
--- a/engines/lilliput/detection.h
+++ b/engines/lilliput/detection.h
@@ -23,8 +23,16 @@
 #ifndef LILLIPUT_DETECTION_H
 #define LILLIPUT_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Lilliput {
 
+enum GameType {
+	kGameTypeNone  = 0,
+	kGameTypeRobin,
+	kGameTypeRome
+};
+
 struct LilliputGameDescription {
 	ADGameDescription desc;
 	GameType gameType;
diff --git a/engines/lilliput/detection_enums.h b/engines/lilliput/detection_enums.h
deleted file mode 100644
index 4de4ec857e..0000000000
--- a/engines/lilliput/detection_enums.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
-
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
-
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef LILLIPUT_DETECTION_ENUMS_H
-#define LILLIPUT_DETECTION_ENUMS_H
-
-namespace Lilliput {
-
-enum GameType {
-	kGameTypeNone  = 0,
-	kGameTypeRobin,
-	kGameTypeRome
-};
-
-} // End of namespace Lilliput
-
-#endif // LILLIPUT_DETECTION_ENUMS_H
diff --git a/engines/lilliput/lilliput.h b/engines/lilliput/lilliput.h
index b4e90a0afb..57d8140a9f 100644
--- a/engines/lilliput/lilliput.h
+++ b/engines/lilliput/lilliput.h
@@ -27,7 +27,7 @@
 #include "lilliput/script.h"
 #include "lilliput/sound.h"
 #include "lilliput/stream.h"
-#include "lilliput/detection_enums.h"
+#include "lilliput/detection.h"
 
 #include "common/file.h"
 #include "common/rect.h"
diff --git a/engines/lure/detection.cpp b/engines/lure/detection.cpp
index 017b7d9b52..92619e1179 100644
--- a/engines/lure/detection.cpp
+++ b/engines/lure/detection.cpp
@@ -26,7 +26,6 @@
 
 #include "common/translation.h"
 
-#include "lure/detection_enums.h"
 #include "lure/detection.h"
 
 static const PlainGameDescriptor lureGames[] = {
diff --git a/engines/lure/detection.h b/engines/lure/detection.h
index e35f578a1c..94090c39e0 100644
--- a/engines/lure/detection.h
+++ b/engines/lure/detection.h
@@ -23,8 +23,16 @@
 #ifndef LURE_DETECTION_H
 #define LURE_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Lure {
 
+enum {
+	GF_FLOPPY	= 1 <<  0,
+	GF_EGA		= 1 <<  1,
+	GF_LNGUNK	= 1 << 15
+};
+
 struct LureGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/lure/detection_enums.h b/engines/lure/detection_enums.h
deleted file mode 100644
index bfa8d641b8..0000000000
--- a/engines/lure/detection_enums.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef LURE_DETECTION_ENUMS_H
-#define LURE_DETECTION_ENUMS_H
-
-namespace Lure {
-
-enum {
-	GF_FLOPPY	= 1 <<  0,
-	GF_EGA		= 1 <<  1,
-	GF_LNGUNK	= 1 << 15
-};
-
-} // End of namespace Lure
-
-#endif // LURE_DETECTION_ENUMS_H
diff --git a/engines/lure/lure.h b/engines/lure/lure.h
index c2ec5a5328..6abb5c7530 100644
--- a/engines/lure/lure.h
+++ b/engines/lure/lure.h
@@ -40,7 +40,7 @@
 #include "lure/strings.h"
 #include "lure/room.h"
 #include "lure/fights.h"
-#include "lure/detection_enums.h"
+#include "lure/detection.h"
 
 /**
  * This is the namespace of the Lure engine.
diff --git a/engines/made/detection.cpp b/engines/made/detection.cpp
index 02dbc5763a..3c04d58df1 100644
--- a/engines/made/detection.cpp
+++ b/engines/made/detection.cpp
@@ -23,7 +23,6 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "made/detection_enums.h"
 #include "made/detection.h"
 
 static const PlainGameDescriptor madeGames[] = {
diff --git a/engines/made/detection.h b/engines/made/detection.h
index 39dfacaf05..d787131e44 100644
--- a/engines/made/detection.h
+++ b/engines/made/detection.h
@@ -23,8 +23,24 @@
 #ifndef MADE_DETECTION_H
 #define MADE_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Made {
 
+enum MadeGameID {
+	GID_RTZ		= 0,
+	GID_MANHOLE	= 1,
+	GID_LGOP2	= 2,
+	GID_RODNEY	= 3
+};
+
+enum MadeGameFeatures {
+	GF_DEMO				= 1 << 0,
+	GF_CD				= 1 << 1,
+	GF_CD_COMPRESSED	= 1 << 2,
+	GF_FLOPPY			= 1 << 3
+};
+
 struct MadeGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/made/detection_enums.h b/engines/made/detection_enums.h
deleted file mode 100644
index 050efe08be..0000000000
--- a/engines/made/detection_enums.h
+++ /dev/null
@@ -1,44 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef MADE_DETECTION_ENUMS_H
-#define MADE_DETECTION_ENUMS_H
-
-namespace Made {
-
-enum MadeGameID {
-	GID_RTZ		= 0,
-	GID_MANHOLE	= 1,
-	GID_LGOP2	= 2,
-	GID_RODNEY	= 3
-};
-
-enum MadeGameFeatures {
-	GF_DEMO				= 1 << 0,
-	GF_CD				= 1 << 1,
-	GF_CD_COMPRESSED	= 1 << 2,
-	GF_FLOPPY			= 1 << 3
-};
-
-} // End of namespace Made
-
-#endif // MADE_DETECTION_ENUMS_H
diff --git a/engines/made/made.h b/engines/made/made.h
index 3f7007f24e..5950812740 100644
--- a/engines/made/made.h
+++ b/engines/made/made.h
@@ -24,7 +24,7 @@
 #define MADE_MADE_H
 
 #include "made/sound.h"
-#include "made/detection_enums.h"
+#include "made/detection.h"
 
 #include "engines/engine.h"
 
@@ -45,8 +45,6 @@ namespace Made {
 
 const uint32 kTimerResolution = 40;
 
-struct MadeGameDescription;
-
 class ResourceReader;
 class PmvPlayer;
 class Screen;
diff --git a/engines/mads/detection.cpp b/engines/mads/detection.cpp
index f8c31ab64a..f7d8111c9d 100644
--- a/engines/mads/detection.cpp
+++ b/engines/mads/detection.cpp
@@ -27,7 +27,6 @@
 #include "common/system.h"
 #include "common/translation.h"
 
-#include "mads/detection_enums.h"
 #include "mads/detection.h"
 
 static const PlainGameDescriptor MADSGames[] = {
diff --git a/engines/mads/detection.h b/engines/mads/detection.h
index 1dc2d5ef13..d06d1d3f11 100644
--- a/engines/mads/detection.h
+++ b/engines/mads/detection.h
@@ -24,8 +24,16 @@
 #ifndef MADS_DETECTION_H
 #define MADS_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace MADS {
 
+enum {
+	GType_RexNebular = 0,
+	GType_Dragonsphere = 1,
+	GType_Phantom = 2
+};
+
 struct MADSGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/mads/detection_enums.h b/engines/mads/detection_enums.h
deleted file mode 100644
index 3e595e8f86..0000000000
--- a/engines/mads/detection_enums.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef MADS_DETECTION_ENUMS_H
-#define MADS_DETECTION_ENUMS_H
-
-namespace MADS {
-
-enum {
-	GType_RexNebular = 0,
-	GType_Dragonsphere = 1,
-	GType_Phantom = 2
-};
-
-} // End of namespace MADS
-
-#endif // MADS_DETECTION_ENUMS_H
diff --git a/engines/mads/mads.h b/engines/mads/mads.h
index 9cda26e63a..a2c2c4d50d 100644
--- a/engines/mads/mads.h
+++ b/engines/mads/mads.h
@@ -40,7 +40,7 @@
 #include "mads/msurface.h"
 #include "mads/resources.h"
 #include "mads/sound.h"
-#include "mads/detection_enums.h"
+#include "mads/detection.h"
 
 /**
  * This is the namespace of the MADS engine.
@@ -68,8 +68,6 @@ enum ScreenFade {
 	SCREEN_FADE_FAST = 2
 };
 
-struct MADSGameDescription;
-
 
 class MADSEngine : public Engine {
 private:
diff --git a/engines/mohawk/detection.cpp b/engines/mohawk/detection.cpp
index d766a3e4d5..1d7dcbd44c 100644
--- a/engines/mohawk/detection.cpp
+++ b/engines/mohawk/detection.cpp
@@ -28,7 +28,6 @@
 #include "common/translation.h"
 
 #include "mohawk/detection.h"
-#include "mohawk/detection_enums.h"
 
 #include "mohawk/riven_metaengine.h"
 #include "mohawk/myst_metaengine.h"
diff --git a/engines/mohawk/detection.h b/engines/mohawk/detection.h
index aa9d2c96fc..11c0d866f9 100644
--- a/engines/mohawk/detection.h
+++ b/engines/mohawk/detection.h
@@ -23,8 +23,34 @@
 #ifndef MOHAWK_DETECTION_H
 #define MOHAWK_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Mohawk {
 
+enum MohawkGameType {
+	GType_MYST,
+	GType_MAKINGOF,
+	GType_RIVEN,
+	GType_CSTIME,
+	GType_LIVINGBOOKSV1,
+	GType_LIVINGBOOKSV2,
+	GType_LIVINGBOOKSV3,
+	GType_LIVINGBOOKSV4,
+	GType_LIVINGBOOKSV5
+};
+
+#define GAMEOPTION_ME   GUIO_GAMEOPTIONS1
+#define GAMEOPTION_25TH GUIO_GAMEOPTIONS2
+#define GAMEOPTION_DEMO GUIO_GAMEOPTIONS3
+
+enum MohawkGameFeatures {
+	GF_ME             = (1 << 0), // Myst Masterpiece Edition
+	GF_25TH           = (1 << 1), // Myst and Riven 25th Anniversary
+	GF_DVD            = (1 << 2),
+	GF_DEMO           = (1 << 3),
+	GF_LB_10          = (1 << 4)  // very early Living Books 1.0 games
+};
+
 struct MohawkGameDescription {
 	ADGameDescription desc;
 
@@ -35,4 +61,4 @@ struct MohawkGameDescription {
 
 } // End of namespace Mohawk
 
-#endif
+#endif // MOHAWK_DETECTION_H
diff --git a/engines/mohawk/detection_enums.h b/engines/mohawk/detection_enums.h
deleted file mode 100644
index 5f844c2531..0000000000
--- a/engines/mohawk/detection_enums.h
+++ /dev/null
@@ -1,54 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef MOHAWK_DETECTION_ENUMS_H
-#define MOHAWK_DETECTION_ENUMS_H
-
-namespace Mohawk {
-
-enum MohawkGameType {
-	GType_MYST,
-	GType_MAKINGOF,
-	GType_RIVEN,
-	GType_CSTIME,
-	GType_LIVINGBOOKSV1,
-	GType_LIVINGBOOKSV2,
-	GType_LIVINGBOOKSV3,
-	GType_LIVINGBOOKSV4,
-	GType_LIVINGBOOKSV5
-};
-
-#define GAMEOPTION_ME   GUIO_GAMEOPTIONS1
-#define GAMEOPTION_25TH GUIO_GAMEOPTIONS2
-#define GAMEOPTION_DEMO GUIO_GAMEOPTIONS3
-
-enum MohawkGameFeatures {
-	GF_ME             = (1 << 0), // Myst Masterpiece Edition
-	GF_25TH           = (1 << 1), // Myst and Riven 25th Anniversary
-	GF_DVD            = (1 << 2),
-	GF_DEMO           = (1 << 3),
-	GF_LB_10          = (1 << 4)  // very early Living Books 1.0 games
-};
-
-} // End of namespace Mohawk
-
-#endif
diff --git a/engines/mohawk/mohawk.h b/engines/mohawk/mohawk.h
index 55a0f667f4..1e7197eb0c 100644
--- a/engines/mohawk/mohawk.h
+++ b/engines/mohawk/mohawk.h
@@ -28,7 +28,7 @@
 
 #include "engines/engine.h"
 
-#include "mohawk/detection_enums.h"
+#include "mohawk/detection.h"
 
 class OSystem;
 
@@ -47,7 +47,6 @@ class SeekableReadStream;
  */
 namespace Mohawk {
 
-struct MohawkGameDescription;
 class Sound;
 class PauseDialog;
 class Archive;
diff --git a/engines/mortevielle/detection.cpp b/engines/mortevielle/detection.cpp
index a0d85c7ae0..99a324964f 100644
--- a/engines/mortevielle/detection.cpp
+++ b/engines/mortevielle/detection.cpp
@@ -24,7 +24,6 @@
 #include "engines/advancedDetector.h"
 
 #include "mortevielle/detection.h"
-#include "mortevielle/detection_enums.h"
 
 static const PlainGameDescriptor MortevielleGame[] = {
 	{"mortevielle", "Mortville Manor"},
diff --git a/engines/mortevielle/detection.h b/engines/mortevielle/detection.h
index d86daca3bd..681893fbf2 100644
--- a/engines/mortevielle/detection.h
+++ b/engines/mortevielle/detection.h
@@ -23,8 +23,15 @@
 #ifndef MORTEVIELLE_DETECTION_H
 #define MORTEVIELLE_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Mortevielle {
 
+enum {
+	kUseOriginalData = 0,
+	kUseEngineDataFile = 1
+};
+
 struct MortevielleGameDescription {
 	ADGameDescription desc;
 	Common::Language originalLanguage;
diff --git a/engines/mortevielle/detection_enums.h b/engines/mortevielle/detection_enums.h
deleted file mode 100644
index 43f28e8bb7..0000000000
--- a/engines/mortevielle/detection_enums.h
+++ /dev/null
@@ -1,35 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef MORTEVIELLE_DETECTION_ENUMS_H
-#define MORTEVIELLE_DETECTION_ENUMS_H
-
-namespace Mortevielle {
-
-enum {
-	kUseOriginalData = 0,
-	kUseEngineDataFile = 1
-};
-
-} // End of namespace Mortevielle
-
-#endif // MORTEVIELLE_DETECTION_ENUMS_H
diff --git a/engines/mortevielle/mortevielle.h b/engines/mortevielle/mortevielle.h
index 93872c8f43..a91189404a 100644
--- a/engines/mortevielle/mortevielle.h
+++ b/engines/mortevielle/mortevielle.h
@@ -44,7 +44,7 @@
 #include "mortevielle/saveload.h"
 #include "mortevielle/sound.h"
 #include "mortevielle/outtext.h"
-#include "mortevielle/detection_enums.h"
+#include "mortevielle/detection.h"
 
 namespace Mortevielle {
 
@@ -154,8 +154,6 @@ struct Hint {
 	byte _point;
 };
 
-struct MortevielleGameDescription;
-
 class MortevielleEngine : public Engine {
 private:
 	const MortevielleGameDescription *_gameDescription;
diff --git a/engines/parallaction/detection.cpp b/engines/parallaction/detection.cpp
index 0ca0dfc7aa..6f38b981da 100644
--- a/engines/parallaction/detection.cpp
+++ b/engines/parallaction/detection.cpp
@@ -27,7 +27,6 @@
 #include "common/system.h"
 #include "common/textconsole.h"
 
-#include "parallaction/detection_enums.h"
 #include "parallaction/detection.h"
 
 static const PlainGameDescriptor parallactionGames[] = {
diff --git a/engines/parallaction/detection.h b/engines/parallaction/detection.h
index 99ba602969..79c5158de0 100644
--- a/engines/parallaction/detection.h
+++ b/engines/parallaction/detection.h
@@ -23,8 +23,24 @@
 #ifndef PARALLACTION_DETECTION_H
 #define PARALLACTION_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Parallaction {
 
+enum {
+	GF_DEMO = 1 << 0,
+	GF_LANG_EN = 1 << 1,
+	GF_LANG_FR = 1 << 2,
+	GF_LANG_DE = 1 << 3,
+	GF_LANG_IT = 1 << 4,
+	GF_LANG_MULT = 1 << 5
+};
+
+enum ParallactionGameType {
+	GType_Nippon = 1,
+	GType_BRA
+};
+
 struct PARALLACTIONGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/parallaction/detection_enums.h b/engines/parallaction/detection_enums.h
deleted file mode 100644
index 9ab631a916..0000000000
--- a/engines/parallaction/detection_enums.h
+++ /dev/null
@@ -1,44 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef PARALLACTION_DETECTION_ENUMS_H
-#define PARALLACTION_DETECTION_ENUMS_H
-
-namespace Parallaction {
-
-enum {
-	GF_DEMO = 1 << 0,
-	GF_LANG_EN = 1 << 1,
-	GF_LANG_FR = 1 << 2,
-	GF_LANG_DE = 1 << 3,
-	GF_LANG_IT = 1 << 4,
-	GF_LANG_MULT = 1 << 5
-};
-
-enum ParallactionGameType {
-	GType_Nippon = 1,
-	GType_BRA
-};
-
-} // End of namespace Parallaction
-
-#endif // PARALLACTION_DETECTION_ENUMS_H
diff --git a/engines/parallaction/parallaction.h b/engines/parallaction/parallaction.h
index ed907fc4b4..694007bfe2 100644
--- a/engines/parallaction/parallaction.h
+++ b/engines/parallaction/parallaction.h
@@ -37,7 +37,7 @@
 #include "parallaction/inventory.h"
 #include "parallaction/objects.h"
 #include "parallaction/disk.h"
-#include "parallaction/detection_enums.h"
+#include "parallaction/detection.h"
 
 #define PATH_LEN	200
 
@@ -85,7 +85,6 @@ enum {
 	kEvIngameMenu   = 8000
 };
 
-struct PARALLACTIONGameDescription;
 
 
 
diff --git a/engines/pegasus/detection.cpp b/engines/pegasus/detection.cpp
index 035527230e..090f7935d2 100644
--- a/engines/pegasus/detection.cpp
+++ b/engines/pegasus/detection.cpp
@@ -26,7 +26,6 @@
 #include "common/config-manager.h"
 #include "common/file.h"
 
-#include "pegasus/detection_enums.h"
 #include "pegasus/detection.h"
 
 static const PlainGameDescriptor pegasusGames[] = {
diff --git a/engines/pegasus/detection.h b/engines/pegasus/detection.h
index 2ca5ec6c81..0c6a66056c 100644
--- a/engines/pegasus/detection.h
+++ b/engines/pegasus/detection.h
@@ -23,8 +23,14 @@
 #ifndef PEGASUS_DETECTION_H
 #define PEGASUS_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Pegasus {
 
+enum {
+	GF_DVD = (1 << 1)
+};
+
 struct PegasusGameDescription {
 	ADGameDescription desc;
 };
diff --git a/engines/pegasus/detection_enums.h b/engines/pegasus/detection_enums.h
deleted file mode 100644
index 9797435940..0000000000
--- a/engines/pegasus/detection_enums.h
+++ /dev/null
@@ -1,37 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * Additional copyright for this file:
- * Copyright (C) 1995-1997 Presto Studios, Inc.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef PEGASUS_DETECTION_ENUMS_h
-#define PEGASUS_DETECTION_ENUMS_h
-
-namespace Pegasus {
-
-enum {
-	GF_DVD = (1 << 1)
-};
-
-} // End of namespace Pegasus
-
-#endif // PEGASUS_DETECTION_ENUMS_h
diff --git a/engines/pegasus/metaengine.cpp b/engines/pegasus/metaengine.cpp
index e0b780fb6b..d6616ec67c 100644
--- a/engines/pegasus/metaengine.cpp
+++ b/engines/pegasus/metaengine.cpp
@@ -28,7 +28,6 @@
 #include "common/savefile.h"
 
 #include "pegasus/pegasus.h"
-#include "pegasus/detection_enums.h"
 #include "pegasus/detection.h"
 
 namespace Pegasus {
diff --git a/engines/prince/detection.cpp b/engines/prince/detection.cpp
index f0f9b5984c..e04048e5fb 100644
--- a/engines/prince/detection.cpp
+++ b/engines/prince/detection.cpp
@@ -22,7 +22,6 @@
 
 #include "engines/advancedDetector.h"
 
-#include "prince/detection_enums.h"
 #include "prince/detection.h"
 
 static const PlainGameDescriptor princeGames[] = {
diff --git a/engines/prince/detection.h b/engines/prince/detection.h
index 5f7bcc897f..6e5f8ced8f 100644
--- a/engines/prince/detection.h
+++ b/engines/prince/detection.h
@@ -23,8 +23,22 @@
 #ifndef PRINCE_DETECTION_H
 #define PRINCE_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Prince {
 
+enum PrinceGameType {
+	kPrinceDataUNK,
+	kPrinceDataDE,
+	kPrinceDataPL
+};
+
+enum {
+	GF_TRANSLATED = 1 << 0,
+	GF_EXTRACTED  = 1 << 1,
+	GF_NOVOICES   = 1 << 2
+};
+
 struct PrinceGameDescription {
 	ADGameDescription desc;
 	PrinceGameType gameType;
diff --git a/engines/prince/detection_enums.h b/engines/prince/detection_enums.h
deleted file mode 100644
index b381ede907..0000000000
--- a/engines/prince/detection_enums.h
+++ /dev/null
@@ -1,42 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef PRINCE_DETECTION_ENUMS_H
-#define PRINCE_DETECTION_ENUMS_H
-
-namespace Prince {
-
-enum PrinceGameType {
-	kPrinceDataUNK,
-	kPrinceDataDE,
-	kPrinceDataPL
-};
-
-enum {
-	GF_TRANSLATED = 1 << 0,
-	GF_EXTRACTED  = 1 << 1,
-	GF_NOVOICES   = 1 << 2
-};
-
-} // End of namespace Prince
-
-#endif // PRINCE_DETECTION_ENUMS_H
diff --git a/engines/prince/prince.h b/engines/prince/prince.h
index bbcb97edaa..978256f79c 100644
--- a/engines/prince/prince.h
+++ b/engines/prince/prince.h
@@ -48,14 +48,13 @@
 #include "prince/mob.h"
 #include "prince/object.h"
 #include "prince/pscr.h"
-#include "prince/detection_enums.h"
+#include "prince/detection.h"
 
 namespace Prince {
 
 struct SavegameHeader;
 
 class PrinceEngine;
-struct PrinceGameDescription;
 class GraphicsMan;
 class Script;
 class Interpreter;
diff --git a/engines/saga/detection.cpp b/engines/saga/detection.cpp
index e58d6689b1..dec4adde27 100644
--- a/engines/saga/detection.cpp
+++ b/engines/saga/detection.cpp
@@ -25,7 +25,6 @@
 #include "base/plugins.h"
 #include "engines/advancedDetector.h"
 
-#include "saga/detection_enums.h"
 #include "saga/detection.h"
 
 static const PlainGameDescriptor sagaGames[] = {
diff --git a/engines/saga/detection.h b/engines/saga/detection.h
index b8a4700d71..fd001b5381 100644
--- a/engines/saga/detection.h
+++ b/engines/saga/detection.h
@@ -23,8 +23,75 @@
 #ifndef SAGA_DETECTION_H
 #define SAGA_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Saga {
 
+struct GameResourceDescription {
+	uint32 sceneLUTResourceId;
+	uint32 moduleLUTResourceId;
+	uint32 mainPanelResourceId;
+	uint32 conversePanelResourceId;
+	uint32 optionPanelResourceId;
+	uint32 mainSpritesResourceId;
+	uint32 mainPanelSpritesResourceId;
+	uint32 mainStringsResourceId;
+	// ITE specific resources
+	uint32 actorsStringsResourceId;
+	uint32 defaultPortraitsResourceId;
+	// IHNM specific resources
+	uint32 optionPanelSpritesResourceId;
+	uint32 warningPanelResourceId;
+	uint32 warningPanelSpritesResourceId;
+	uint32 psychicProfileResourceId;
+};
+
+struct GameFontDescription {
+	uint32 fontResourceId;
+};
+
+struct GamePatchDescription {
+	const char *fileName;
+	uint16 fileType;
+	uint32 resourceId;
+};
+
+enum GameIds {
+	GID_ITE = 0,
+	GID_IHNM = 1,
+	GID_DINO = 2,
+	GID_FTA2 = 3
+};
+
+enum GameFeatures {
+	GF_ITE_FLOPPY        = 1 << 0,
+	GF_ITE_DOS_DEMO      = 1 << 1,
+	GF_EXTRA_ITE_CREDITS = 1 << 2,
+	GF_8BIT_UNSIGNED_PCM = 1 << 3,
+	GF_IHNM_COLOR_FIX    = 1 << 4,
+	GF_SOME_MAC_RESOURCES= 1 << 5
+};
+
+enum GameFileTypes {
+	// Common
+	GAME_RESOURCEFILE     = 1 << 0,    // Game resources
+	GAME_SCRIPTFILE       = 1 << 1,    // Game scripts
+	GAME_SOUNDFILE        = 1 << 2,    // SFX (also contains voices and MIDI music in SAGA 2 games)
+	GAME_VOICEFILE        = 1 << 3,    // Voices (also contains SFX in the ITE floppy version)
+	// ITE specific
+	GAME_DIGITALMUSICFILE = 1 << 4,    // ITE digital music, added by Wyrmkeep
+	GAME_MACBINARY        = 1 << 5,    // ITE Mac CD Guild
+	GAME_DEMOFILE         = 1 << 6,    // Early ITE demo
+	GAME_SWAPENDIAN       = 1 << 7,    // Used to identify the BE voice file in the ITE combined version
+	// IHNM specific
+	GAME_MUSICFILE_FM     = 1 << 8,    // IHNM
+	GAME_MUSICFILE_GM     = 1 << 9,    // IHNM, ITE Mac CD Guild
+	GAME_PATCHFILE        = 1 << 10,   // IHNM patch file (patch.re_/patch.res)
+	// SAGA 2 (Dinotopia, FTA2)
+	GAME_IMAGEFILE        = 1 << 11,   // Game images
+	GAME_OBJRESOURCEFILE  = 1 << 12    // Game object data
+};
+
 struct SAGAGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/saga/detection_enums.h b/engines/saga/detection_enums.h
deleted file mode 100644
index 25e8c7d589..0000000000
--- a/engines/saga/detection_enums.h
+++ /dev/null
@@ -1,95 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef SAGA_DETECTION_ENUMS_H
-#define SAGA_DETECTION_ENUMS_H
-
-namespace Saga {
-
-struct GameResourceDescription {
-	uint32 sceneLUTResourceId;
-	uint32 moduleLUTResourceId;
-	uint32 mainPanelResourceId;
-	uint32 conversePanelResourceId;
-	uint32 optionPanelResourceId;
-	uint32 mainSpritesResourceId;
-	uint32 mainPanelSpritesResourceId;
-	uint32 mainStringsResourceId;
-	// ITE specific resources
-	uint32 actorsStringsResourceId;
-	uint32 defaultPortraitsResourceId;
-	// IHNM specific resources
-	uint32 optionPanelSpritesResourceId;
-	uint32 warningPanelResourceId;
-	uint32 warningPanelSpritesResourceId;
-	uint32 psychicProfileResourceId;
-};
-
-struct GameFontDescription {
-	uint32 fontResourceId;
-};
-
-struct GamePatchDescription {
-	const char *fileName;
-	uint16 fileType;
-	uint32 resourceId;
-};
-
-enum GameIds {
-	GID_ITE = 0,
-	GID_IHNM = 1,
-	GID_DINO = 2,
-	GID_FTA2 = 3
-};
-
-enum GameFeatures {
-	GF_ITE_FLOPPY        = 1 << 0,
-	GF_ITE_DOS_DEMO      = 1 << 1,
-	GF_EXTRA_ITE_CREDITS = 1 << 2,
-	GF_8BIT_UNSIGNED_PCM = 1 << 3,
-	GF_IHNM_COLOR_FIX    = 1 << 4,
-	GF_SOME_MAC_RESOURCES= 1 << 5
-};
-
-enum GameFileTypes {
-	// Common
-	GAME_RESOURCEFILE     = 1 << 0,    // Game resources
-	GAME_SCRIPTFILE       = 1 << 1,    // Game scripts
-	GAME_SOUNDFILE        = 1 << 2,    // SFX (also contains voices and MIDI music in SAGA 2 games)
-	GAME_VOICEFILE        = 1 << 3,    // Voices (also contains SFX in the ITE floppy version)
-	// ITE specific
-	GAME_DIGITALMUSICFILE = 1 << 4,    // ITE digital music, added by Wyrmkeep
-	GAME_MACBINARY        = 1 << 5,    // ITE Mac CD Guild
-	GAME_DEMOFILE         = 1 << 6,    // Early ITE demo
-	GAME_SWAPENDIAN       = 1 << 7,    // Used to identify the BE voice file in the ITE combined version
-	// IHNM specific
-	GAME_MUSICFILE_FM     = 1 << 8,    // IHNM
-	GAME_MUSICFILE_GM     = 1 << 9,    // IHNM, ITE Mac CD Guild
-	GAME_PATCHFILE        = 1 << 10,   // IHNM patch file (patch.re_/patch.res)
-	// SAGA 2 (Dinotopia, FTA2)
-	GAME_IMAGEFILE        = 1 << 11,   // Game images
-	GAME_OBJRESOURCEFILE  = 1 << 12    // Game object data
-};
-
-} // End of namespace Saga
-
-#endif // SAGA_DETECTION_ENUMS_H
diff --git a/engines/saga/saga.h b/engines/saga/saga.h
index 59a8ecf202..0d8b5634c6 100644
--- a/engines/saga/saga.h
+++ b/engines/saga/saga.h
@@ -31,7 +31,7 @@
 #include "common/textconsole.h"
 
 #include "saga/gfx.h"
-#include "saga/detection_enums.h"
+#include "saga/detection.h"
 
 struct ADGameFileDescription;
 
@@ -236,8 +236,6 @@ enum TextStringIds {
 
 struct GameDisplayInfo;
 
-struct SAGAGameDescription;
-
 enum GameObjectTypes {
 	kGameObjectNone = 0,
 	kGameObjectActor = 1,
diff --git a/engines/sci/detection.cpp b/engines/sci/detection.cpp
index 667c2d3176..d12b948b58 100644
--- a/engines/sci/detection.cpp
+++ b/engines/sci/detection.cpp
@@ -31,8 +31,7 @@
 #include "gui/widget.h"
 #include "gui/widgets/popup.h"
 
-#include "sci/detection_enums.h"
-#include "sci/detection_defines.h"
+#include "sci/detection.h"
 #include "sci/graphics/helpers_detection_enums.h"
 
 namespace Sci {
diff --git a/engines/sci/detection_enums.h b/engines/sci/detection.h
similarity index 79%
rename from engines/sci/detection_enums.h
rename to engines/sci/detection.h
index 6da06e5e0b..cb6a8a150f 100644
--- a/engines/sci/detection_enums.h
+++ b/engines/sci/detection.h
@@ -20,11 +20,27 @@
  *
  */
 
-#ifndef SCI_DETECTION_ENUMS_H
-#define SCI_DETECTION_ENUMS_H
+#ifndef SCI_DETECTION_H
+#define SCI_DETECTION_H
 
 namespace Sci {
 
+// GUI-options, primarily used by detection_tables.h
+#define GAMEOPTION_PREFER_DIGITAL_SFX       GUIO_GAMEOPTIONS1
+#define GAMEOPTION_ORIGINAL_SAVELOAD        GUIO_GAMEOPTIONS2
+#define GAMEOPTION_MIDI_MODE                GUIO_GAMEOPTIONS3
+#define GAMEOPTION_JONES_CDAUDIO            GUIO_GAMEOPTIONS4
+#define GAMEOPTION_KQ6_WINDOWS_CURSORS      GUIO_GAMEOPTIONS5
+#define GAMEOPTION_SQ4_SILVER_CURSORS       GUIO_GAMEOPTIONS6
+#define GAMEOPTION_EGA_UNDITHER             GUIO_GAMEOPTIONS7
+// HIGH_RESOLUTION_GRAPHICS availability is checked for in SciEngine::run()
+#define GAMEOPTION_HIGH_RESOLUTION_GRAPHICS GUIO_GAMEOPTIONS8
+#define GAMEOPTION_ENABLE_BLACK_LINED_VIDEO GUIO_GAMEOPTIONS9
+#define GAMEOPTION_HQ_VIDEO                 GUIO_GAMEOPTIONS10
+#define GAMEOPTION_ENABLE_CENSORING         GUIO_GAMEOPTIONS11
+#define GAMEOPTION_LARRYSCALE               GUIO_GAMEOPTIONS12
+#define GAMEOPTION_UPSCALE_VIDEOS           GUIO_GAMEOPTIONS13
+
 enum SciGameId {
 	GID_ASTROCHICKEN,
 	GID_CAMELOT,
@@ -128,4 +144,4 @@ enum SciVersion {
 
 } // End of namespace Sci
 
-#endif
+#endif // SCI_DETECTION_H
diff --git a/engines/sci/detection_defines.h b/engines/sci/detection_defines.h
deleted file mode 100644
index 143b7b203e..0000000000
--- a/engines/sci/detection_defines.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef SCI_DETECTION_DEFINES_H
-#define SCI_DETECTION_DEFINES_H
-
-namespace Sci {
-
-// GUI-options, primarily used by detection_tables.h
-#define GAMEOPTION_PREFER_DIGITAL_SFX       GUIO_GAMEOPTIONS1
-#define GAMEOPTION_ORIGINAL_SAVELOAD        GUIO_GAMEOPTIONS2
-#define GAMEOPTION_MIDI_MODE                GUIO_GAMEOPTIONS3
-#define GAMEOPTION_JONES_CDAUDIO            GUIO_GAMEOPTIONS4
-#define GAMEOPTION_KQ6_WINDOWS_CURSORS      GUIO_GAMEOPTIONS5
-#define GAMEOPTION_SQ4_SILVER_CURSORS       GUIO_GAMEOPTIONS6
-#define GAMEOPTION_EGA_UNDITHER             GUIO_GAMEOPTIONS7
-// HIGH_RESOLUTION_GRAPHICS availability is checked for in SciEngine::run()
-#define GAMEOPTION_HIGH_RESOLUTION_GRAPHICS GUIO_GAMEOPTIONS8
-#define GAMEOPTION_ENABLE_BLACK_LINED_VIDEO GUIO_GAMEOPTIONS9
-#define GAMEOPTION_HQ_VIDEO                 GUIO_GAMEOPTIONS10
-#define GAMEOPTION_ENABLE_CENSORING         GUIO_GAMEOPTIONS11
-#define GAMEOPTION_LARRYSCALE               GUIO_GAMEOPTIONS12
-#define GAMEOPTION_UPSCALE_VIDEOS           GUIO_GAMEOPTIONS13
-
-} // End of namespace Sci
-
-#endif
diff --git a/engines/sci/graphics/helpers_detection_enums.h b/engines/sci/graphics/helpers_detection_enums.h
index cdd9b51777..18b00120b5 100644
--- a/engines/sci/graphics/helpers_detection_enums.h
+++ b/engines/sci/graphics/helpers_detection_enums.h
@@ -20,8 +20,8 @@
  *
  */
 
-#ifndef SCI_HELPERES_DETECTION_ENUMS_H
-#define SCI_HELPERES_DETECTION_ENUMS_H
+#ifndef SCI_HELPERS_DETECTION_ENUMS_H
+#define SCI_HELPERS_DETECTION_ENUMS_H
 
 namespace Sci {
 // Game view types, sorted by the number of colors
@@ -36,4 +36,4 @@ enum ViewType {
 
 } // End of namespace Sci
 
-#endif
+#endif // SCI_HELPERS_DETECTION_ENUMS_H
diff --git a/engines/sci/sci.h b/engines/sci/sci.h
index 7ea28b38f7..dd70eab191 100644
--- a/engines/sci/sci.h
+++ b/engines/sci/sci.h
@@ -29,8 +29,7 @@
 #include "common/random.h"
 #include "sci/engine/vm_types.h"	// for Selector
 #include "sci/debug.h"	// for DebugState
-#include "sci/detection_enums.h" // for shared enums between detection/engine
-#include "sci/detection_defines.h" // for shared defines between detection/engine
+#include "sci/detection.h" // Shared code between detection and engine
 
 struct ADGameDescription;
 
diff --git a/engines/sherlock/detection.cpp b/engines/sherlock/detection.cpp
index 2454b54899..7047838e24 100644
--- a/engines/sherlock/detection.cpp
+++ b/engines/sherlock/detection.cpp
@@ -23,7 +23,6 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "sherlock/detection_enums.h"
 #include "sherlock/detection.h"
 
 static const PlainGameDescriptor sherlockGames[] = {
diff --git a/engines/sherlock/detection.h b/engines/sherlock/detection.h
index 00ee8199dd..44c6fc2852 100644
--- a/engines/sherlock/detection.h
+++ b/engines/sherlock/detection.h
@@ -23,8 +23,15 @@
 #ifndef SHERLOCK_DETECTION_H
 #define SHERLOCK_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Sherlock {
 
+enum GameType {
+	GType_SerratedScalpel = 0,
+	GType_RoseTattoo = 1
+};
+
 struct SherlockGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/sherlock/detection_enums.h b/engines/sherlock/detection_enums.h
deleted file mode 100644
index 9a4a04c156..0000000000
--- a/engines/sherlock/detection_enums.h
+++ /dev/null
@@ -1,35 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef SHERLOCK_DETECTION_ENUMS_H
-#define SHERLOCK_DETECTION_ENUMS_H
-
-namespace Sherlock {
-
-enum GameType {
-	GType_SerratedScalpel = 0,
-	GType_RoseTattoo = 1
-};
-
-} // End of namespace Sherlock
-
-#endif // SHERLOCK_DETECTION_ENUMS_H
diff --git a/engines/sherlock/sherlock.h b/engines/sherlock/sherlock.h
index 06a28af8bb..901b8ebe6d 100644
--- a/engines/sherlock/sherlock.h
+++ b/engines/sherlock/sherlock.h
@@ -50,7 +50,7 @@
 #include "sherlock/sound.h"
 #include "sherlock/talk.h"
 #include "sherlock/user_interface.h"
-#include "sherlock/detection_enums.h"
+#include "sherlock/detection.h"
 
 namespace Sherlock {
 
@@ -72,8 +72,6 @@ enum {
 #define COL_PEN_COLOR (IS_SERRATED_SCALPEL ? (byte)Scalpel::PEN_COLOR : (byte)Tattoo::PEN_COLOR)
 #define COL_PEN_HIGHLIGHT (IS_SERRATED_SCALPEL ? 15 : 129)
 
-struct SherlockGameDescription;
-
 class Resource;
 
 class SherlockEngine : public Engine {
diff --git a/engines/startrek/detection.cpp b/engines/startrek/detection.cpp
index 26480182a3..587fda7115 100644
--- a/engines/startrek/detection.cpp
+++ b/engines/startrek/detection.cpp
@@ -28,7 +28,6 @@
 #include "common/file.h"
 
 #include "startrek/detection.h"
-#include "startrek/detection_enums.h"
 
 static const PlainGameDescriptor starTrekGames[] = {
 	{"st25", "Star Trek: 25th Anniversary"},
diff --git a/engines/startrek/detection.h b/engines/startrek/detection.h
index 998860039b..eadeb87874 100644
--- a/engines/startrek/detection.h
+++ b/engines/startrek/detection.h
@@ -23,8 +23,20 @@
 #ifndef STARTTREK_DETECTION_H
 #define STARTTREK_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace StarTrek {
 
+enum StarTrekGameType {
+	GType_ST25 = 1,
+	GType_STJR = 2
+};
+
+enum StarTrekGameFeatures {
+	GF_DEMO  = (1 << 0),
+	GF_CDROM = (1 << 1)
+};
+
 struct StarTrekGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/startrek/detection_enums.h b/engines/startrek/detection_enums.h
deleted file mode 100644
index f1aa1f30c7..0000000000
--- a/engines/startrek/detection_enums.h
+++ /dev/null
@@ -1,40 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
-
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
-
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef STARTTREK_DETECTION_ENUMS_H
-#define STARTTREK_DETECTION_ENUMS_H
-
-namespace StarTrek {
-
-enum StarTrekGameType {
-	GType_ST25 = 1,
-	GType_STJR = 2
-};
-
-enum StarTrekGameFeatures {
-	GF_DEMO  = (1 << 0),
-	GF_CDROM = (1 << 1)
-};
-
-} // End of namespace StarTrek
-
-#endif // STARTTREK_DETECTION_ENUMS_H
diff --git a/engines/startrek/startrek.h b/engines/startrek/startrek.h
index 804878da59..2fbe93078b 100644
--- a/engines/startrek/startrek.h
+++ b/engines/startrek/startrek.h
@@ -48,7 +48,7 @@
 #include "startrek/object.h"
 #include "startrek/sound.h"
 #include "startrek/space.h"
-#include "startrek/detection_enums.h"
+#include "startrek/detection.h"
 
 
 using Common::SharedPtr;
@@ -212,7 +212,6 @@ struct TrekEvent {
 };
 
 
-struct StarTrekGameDescription;
 class Graphics;
 class IWFile;
 class Sound;
diff --git a/engines/sword2/detection.cpp b/engines/sword2/detection.cpp
index c7b7134155..9f7abb1fea 100644
--- a/engines/sword2/detection.cpp
+++ b/engines/sword2/detection.cpp
@@ -26,7 +26,7 @@
 
 #include "engines/metaengine.h"
 
-#include "sword2/detection_enums.h"
+#include "sword2/detection.h"
 #include "sword2/detection_internal.h"
 
 static const ExtraGuiOption sword2ExtraGuiOption = {
diff --git a/engines/sword2/detection_enums.h b/engines/sword2/detection.h
similarity index 91%
rename from engines/sword2/detection_enums.h
rename to engines/sword2/detection.h
index b9266c3298..75ccfdc948 100644
--- a/engines/sword2/detection_enums.h
+++ b/engines/sword2/detection.h
@@ -22,8 +22,8 @@
  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
  */
 
-#ifndef SWORD2_DETECTION_ENUMS_H
-#define SWORD2_DETECTION_ENUMS_H
+#ifndef SWORD2_DETECTION_H
+#define SWORD2_DETECTION_H
 
 namespace Sword2 {
 
@@ -34,4 +34,4 @@ enum {
 
 } // End of namespace Sword2
 
-#endif // SWORD2_DETECTION_ENUMS_H
+#endif // SWORD2_DETECTION_H
diff --git a/engines/sword2/detection_internal.h b/engines/sword2/detection_internal.h
index 02861d6fb0..5886a19f28 100644
--- a/engines/sword2/detection_internal.h
+++ b/engines/sword2/detection_internal.h
@@ -27,7 +27,7 @@
 
 #include "engines/metaengine.h"
 #include "common/gui_options.h"
-#include "sword2/detection_enums.h"
+#include "sword2/detection.h"
 
 /**
  * The contents of this file are helpful in detecting games, 
diff --git a/engines/sword2/sword2.h b/engines/sword2/sword2.h
index 044f0d4032..ab28817d63 100644
--- a/engines/sword2/sword2.h
+++ b/engines/sword2/sword2.h
@@ -39,7 +39,7 @@
 #include "common/events.h"
 #include "common/util.h"
 #include "common/random.h"
-#include "sword2/detection_enums.h"
+#include "sword2/detection.h"
 
 #define	MAX_starts	100
 #define	MAX_description	100
diff --git a/engines/sword25/detection.cpp b/engines/sword25/detection.cpp
index 7825fa9977..40ac500ea2 100644
--- a/engines/sword25/detection.cpp
+++ b/engines/sword25/detection.cpp
@@ -24,7 +24,7 @@
 #include "common/translation.h"
 #include "engines/advancedDetector.h"
 
-#include "sword25/detection_enums.h"
+#include "sword25/detection.h"
 #include "sword25/detection_tables.h"
 
 static const PlainGameDescriptor sword25Game[] = {
diff --git a/engines/sword25/detection_enums.h b/engines/sword25/detection.h
similarity index 90%
rename from engines/sword25/detection_enums.h
rename to engines/sword25/detection.h
index e4e21ffecd..46e83bf8e9 100644
--- a/engines/sword25/detection_enums.h
+++ b/engines/sword25/detection.h
@@ -20,8 +20,8 @@
  *
  */
 
-#ifndef SWORD25_DETECTION_ENUMS_H
-#define SWORD25_DETECTION_ENUMS_H
+#ifndef SWORD25_DETECTION_H
+#define SWORD25_DETECTION_H
 
 namespace Sword25 {
 
@@ -31,4 +31,4 @@ enum GameFlags {
 
 } // End of namespace Sword25
 
-#endif // SWORD25_DETECTION_ENUMS_H
+#endif // SWORD25_DETECTION_H
diff --git a/engines/sword25/sword25.h b/engines/sword25/sword25.h
index ead4c28fcf..84aea740f1 100644
--- a/engines/sword25/sword25.h
+++ b/engines/sword25/sword25.h
@@ -27,7 +27,7 @@
 #include "engines/engine.h"
 
 #include "sword25/console.h"
-#include "sword25/detection_enums.h"
+#include "sword25/detection.h"
 
 namespace Common {
 class Error;
diff --git a/engines/tinsel/detection.cpp b/engines/tinsel/detection.cpp
index e4e364539a..e39e82c8c8 100644
--- a/engines/tinsel/detection.cpp
+++ b/engines/tinsel/detection.cpp
@@ -27,7 +27,6 @@
 #include "common/md5.h"
 
 #include "tinsel/detection.h"
-#include "tinsel/detection_enums.h"
 
 static const PlainGameDescriptor tinselGames[] = {
 	{"dw", "Discworld"},
diff --git a/engines/tinsel/detection.h b/engines/tinsel/detection.h
index 50010c810a..61c3a53bc4 100644
--- a/engines/tinsel/detection.h
+++ b/engines/tinsel/detection.h
@@ -23,8 +23,45 @@
 #ifndef TINSEL_DETECTION_H
 #define TINSEL_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Tinsel {
 
+enum TinselGameID {
+	GID_DW1 = 0,
+	GID_DW2 = 1
+};
+
+enum TinselGameFeatures {
+	GF_SCNFILES = 1 << 0,
+	GF_ENHANCED_AUDIO_SUPPORT = 1 << 1,
+	GF_ALT_MIDI = 1 << 2,		// Alternate sequence in midi.dat file
+
+	// The GF_USE_?FLAGS values specify how many country flags are displayed
+	// in the subtitles options dialog.
+	// None of these defined -> 1 language, in ENGLISH.TXT
+	GF_USE_3FLAGS = 1 << 3,	// French, German, Spanish
+	GF_USE_4FLAGS = 1 << 4,	// French, German, Spanish, Italian
+	GF_USE_5FLAGS = 1 << 5	// All 5 flags
+};
+
+/**
+ * The following is the ScummVM definitions of the various Tinsel versions:
+ * TINSEL_V0 - This was an early engine version that was only used in the Discworld 1
+ *			demo.
+ * TINSEL_V1 - This was the engine version used by Discworld 1. Note that there were two
+ *			major releases: an earlier version that used *.gra files, and a later one that
+ *			used *.scn files, and contained certain script and engine bugfixes. In ScummVM,
+ *			we treat both releases as 'Tinsel 1', since the engine fixes from the later
+ *			version work equally well the earlier version data.
+ * TINSEL_V2 - This is the engine used for the Discworld 2 game.
+ */
+enum TinselEngineVersion {
+	TINSEL_V0 = 0,
+	TINSEL_V1 = 1,
+	TINSEL_V2 = 2
+};
+
 struct TinselGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/tinsel/detection_enums.h b/engines/tinsel/detection_enums.h
deleted file mode 100644
index 46f5ef0659..0000000000
--- a/engines/tinsel/detection_enums.h
+++ /dev/null
@@ -1,65 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef TINSEL_DETECTION_ENUMS_H
-#define TINSEL_DETECTION_ENUMS_H
-
-namespace Tinsel {
-
-enum TinselGameID {
-	GID_DW1 = 0,
-	GID_DW2 = 1
-};
-
-enum TinselGameFeatures {
-	GF_SCNFILES = 1 << 0,
-	GF_ENHANCED_AUDIO_SUPPORT = 1 << 1,
-	GF_ALT_MIDI = 1 << 2,		// Alternate sequence in midi.dat file
-
-	// The GF_USE_?FLAGS values specify how many country flags are displayed
-	// in the subtitles options dialog.
-	// None of these defined -> 1 language, in ENGLISH.TXT
-	GF_USE_3FLAGS = 1 << 3,	// French, German, Spanish
-	GF_USE_4FLAGS = 1 << 4,	// French, German, Spanish, Italian
-	GF_USE_5FLAGS = 1 << 5	// All 5 flags
-};
-
-/**
- * The following is the ScummVM definitions of the various Tinsel versions:
- * TINSEL_V0 - This was an early engine version that was only used in the Discworld 1
- *			demo.
- * TINSEL_V1 - This was the engine version used by Discworld 1. Note that there were two
- *			major releases: an earlier version that used *.gra files, and a later one that
- *			used *.scn files, and contained certain script and engine bugfixes. In ScummVM,
- *			we treat both releases as 'Tinsel 1', since the engine fixes from the later
- *			version work equally well the earlier version data.
- * TINSEL_V2 - This is the engine used for the Discworld 2 game.
- */
-enum TinselEngineVersion {
-	TINSEL_V0 = 0,
-	TINSEL_V1 = 1,
-	TINSEL_V2 = 2
-};
-
-} // End of namespace Tinsel
-
-#endif // TINSEL_DETECTION_ENUMS_H
diff --git a/engines/tinsel/tinsel.h b/engines/tinsel/tinsel.h
index ad529d15ef..32f47255cd 100644
--- a/engines/tinsel/tinsel.h
+++ b/engines/tinsel/tinsel.h
@@ -38,7 +38,7 @@
 #include "tinsel/graphics.h"
 #include "tinsel/sound.h"
 #include "tinsel/dw.h"
-#include "tinsel/detection_enums.h"
+#include "tinsel/detection.h"
 
 /**
  * This is the namespace of the Tinsel engine.
@@ -75,8 +75,6 @@ enum {
 #define DEBUG_INTERMEDIATE 2
 #define DEBUG_DETAILED 3
 
-struct TinselGameDescription;
-
 enum TinselKeyDirection {
 	MSK_LEFT = 1, MSK_RIGHT = 2, MSK_UP = 4, MSK_DOWN = 8,
 	MSK_DIRECTION = MSK_LEFT | MSK_RIGHT | MSK_UP | MSK_DOWN
diff --git a/engines/tony/detection.cpp b/engines/tony/detection.cpp
index fa6d8d15e5..d02ddea22c 100644
--- a/engines/tony/detection.cpp
+++ b/engines/tony/detection.cpp
@@ -25,7 +25,6 @@
 #include "engines/advancedDetector.h"
 
 #include "tony/detection.h"
-#include "tony/detection_enums.h"
 
 static const PlainGameDescriptor tonyGames[] = {
 	{"tony", "Tony Tough and the Night of Roasted Moths"},
diff --git a/engines/tony/detection.h b/engines/tony/detection.h
index 608c921201..f1998da41e 100644
--- a/engines/tony/detection.h
+++ b/engines/tony/detection.h
@@ -25,6 +25,10 @@
 
 namespace Tony {
 
+enum {
+	GF_COMPRESSED = (1 << 0)
+};
+
 struct TonyGameDescription {
 	ADGameDescription desc;
 };
diff --git a/engines/tony/detection_enums.h b/engines/tony/detection_enums.h
deleted file mode 100644
index c04308b4ca..0000000000
--- a/engines/tony/detection_enums.h
+++ /dev/null
@@ -1,34 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef TONY_DETECTION_ENUMS_H
-#define TONY_DETECTION_ENUMS_H
-
-namespace Tony {
-
-enum {
-	GF_COMPRESSED = (1 << 0)
-};
-
-} // End of namespace Tony
-
-#endif // TONY_DETECTION_ENUMS_H
diff --git a/engines/tony/metaengine.cpp b/engines/tony/metaengine.cpp
index 4d592d90bb..8c2f6949de 100644
--- a/engines/tony/metaengine.cpp
+++ b/engines/tony/metaengine.cpp
@@ -30,7 +30,6 @@
 #include "tony/tony.h"
 #include "tony/game.h"
 #include "tony/detection.h"
-#include "tony/detection_enums.h"
 
 namespace Tony {
 
diff --git a/engines/tsage/detection.cpp b/engines/tsage/detection.cpp
index 4ca63dbc19..5d5c5f6284 100644
--- a/engines/tsage/detection.cpp
+++ b/engines/tsage/detection.cpp
@@ -25,7 +25,6 @@
 #include "base/plugins.h"
 
 #include "tsage/detection.h"
-#include "tsage/detection_enums.h"
 
 static const PlainGameDescriptor tSageGameTitles[] = {
 	{ "ringworld", "Ringworld: Revenge of the Patriarch" },
diff --git a/engines/tsage/detection.h b/engines/tsage/detection.h
index ed0e9fb9db..e9afc97126 100644
--- a/engines/tsage/detection.h
+++ b/engines/tsage/detection.h
@@ -23,8 +23,24 @@
 #ifndef TSAGE_DETECTION_H
 #define TSAGE_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace TsAGE {
 
+enum {
+	GType_Ringworld = 0,
+	GType_BlueForce = 1,
+	GType_Ringworld2 = 2,
+	GType_Sherlock1 = 5
+};
+
+enum {
+	GF_DEMO = 1 << 0,
+	GF_CD = 1 << 1,
+	GF_FLOPPY = 1 << 2,
+	GF_ALT_REGIONS = 1 << 3
+};
+
 struct tSageGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/tsage/detection_enums.h b/engines/tsage/detection_enums.h
deleted file mode 100644
index fbd055dd6f..0000000000
--- a/engines/tsage/detection_enums.h
+++ /dev/null
@@ -1,44 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef TSAGE_DETECTION_ENUMS_H
-#define TSAGE_DETECTION_ENUMS_H
-
-namespace TsAGE {
-
-enum {
-	GType_Ringworld = 0,
-	GType_BlueForce = 1,
-	GType_Ringworld2 = 2,
-	GType_Sherlock1 = 5
-};
-
-enum {
-	GF_DEMO = 1 << 0,
-	GF_CD = 1 << 1,
-	GF_FLOPPY = 1 << 2,
-	GF_ALT_REGIONS = 1 << 3
-};
-
-} // End of namespace TsAGE
-
-#endif // TSAGE_DETECTION_ENUMS_H
diff --git a/engines/tsage/tsage.h b/engines/tsage/tsage.h
index 06b6f53ae3..3396d2655e 100644
--- a/engines/tsage/tsage.h
+++ b/engines/tsage/tsage.h
@@ -32,7 +32,7 @@
 #include "tsage/events.h"
 #include "tsage/graphics.h"
 #include "tsage/resources.h"
-#include "tsage/detection_enums.h"
+#include "tsage/detection.h"
 
 
 namespace TsAGE {
@@ -44,8 +44,6 @@ enum {
 	ktSageDebugGraphics = 1 << 3
 };
 
-struct tSageGameDescription;
-
 class TSageEngine : public Engine {
 private:
 	const tSageGameDescription *_gameDescription;
diff --git a/engines/tucker/detection.cpp b/engines/tucker/detection.cpp
index 50d618721e..ebacb19e41 100644
--- a/engines/tucker/detection.cpp
+++ b/engines/tucker/detection.cpp
@@ -23,7 +23,7 @@
 #include "common/config-manager.h"
 #include "engines/advancedDetector.h"
 #include "base/plugins.h"
-#include "tucker/detection_enums.h"
+#include "tucker/detection.h"
 
 static const PlainGameDescriptor tuckerGames[] = {
 	{ "tucker", "Bud Tucker in Double Trouble" },
diff --git a/engines/tucker/detection_enums.h b/engines/tucker/detection.h
similarity index 91%
rename from engines/tucker/detection_enums.h
rename to engines/tucker/detection.h
index 7b39c546af..971e1579fc 100644
--- a/engines/tucker/detection_enums.h
+++ b/engines/tucker/detection.h
@@ -20,8 +20,8 @@
  *
  */
 
-#ifndef TUCKER_DETECTION_ENUMS_H
-#define TUCKER_DETECTION_ENUMS_H
+#ifndef TUCKER_DETECTION_H
+#define TUCKER_DETECTION_H
 
 namespace Tucker {
 
@@ -34,4 +34,4 @@ enum GameFlag {
 
 } // End of namespace Tucker
 
-#endif // TUCKER_DETECTION_ENUMS_H
+#endif // TUCKER_DETECTION_H
diff --git a/engines/tucker/tucker.h b/engines/tucker/tucker.h
index 9340d9a3cf..8447789ddd 100644
--- a/engines/tucker/tucker.h
+++ b/engines/tucker/tucker.h
@@ -38,7 +38,7 @@
 #include "engines/engine.h"
 
 #include "tucker/console.h"
-#include "tucker/detection_enums.h"
+#include "tucker/detection.h"
 
 namespace Audio {
 class RewindableAudioStream;
diff --git a/engines/wintermute/base/base_detection_enums.h b/engines/wintermute/base/base_detection_enums.h
deleted file mode 100644
index f0c903aca3..0000000000
--- a/engines/wintermute/base/base_detection_enums.h
+++ /dev/null
@@ -1,114 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-namespace Wintermute {
-
-enum WMETargetExecutable {
-	OLDEST_VERSION,
-	WME_1_0_12, // DEAD:CODE 2003
-	WME_1_0_19, // DEAD:CODE 2003
-	WME_1_0_20, // DEAD:CODE 2003
-	WME_1_0_22, // DEAD:CODE 2003
-	WME_1_0_24, // DEAD:CODE 2003
-	WME_1_0_25, // DEAD:CODE 2003
-	WME_1_0_28, // DEAD:CODE 2003
-	WME_1_0_30, // DEAD:CODE 2003
-	WME_1_0_31, // DEAD:CODE 2003
-	WME_1_1_33, // DEAD:CODE 2003
-	WME_1_1_35, // DEAD:CODE 2003
-	WME_1_1_37, // DEAD:CODE 2003
-	WME_1_1_39, // DEAD:CODE 2004
-	WME_1_2_43, // DEAD:CODE 2004
-	WME_1_2_44, // DEAD:CODE 2004
-	WME_1_3_0,  // DEAD:CODE 2004
-	WME_1_3_2,  // DEAD:CODE 2004
-	WME_1_3_3,  // DEAD:CODE 2004
-	WME_1_4_0,  // DEAD:CODE 2005
-	WME_1_4_1,  // DEAD:CODE 2005
-	WME_1_5_0,  // DEAD:CODE 2005
-	WME_1_5_2,  // DEAD:CODE 2005
-	WME_1_6_0,  // DEAD:CODE 2006
-	WME_1_6_1,  // DEAD:CODE 2006
-	WME_1_7_0,  // DEAD:CODE 2007
-	WME_1_7_1,  // DEAD:CODE 2007
-	WME_1_7_2,  // DEAD:CODE 2007
-	WME_1_7_3,  // DEAD:CODE 2007
-	WME_1_7_93, // DEAD:CODE 2007
-	WME_1_7_94, // DEAD:CODE 2007
-	WME_1_8_0,  // DEAD:CODE 2007
-	WME_1_8_1,  // DEAD:CODE 2007
-	WME_1_8_2,  // DEAD:CODE 2008
-	WME_1_8_3,  // DEAD:CODE 2008
-	WME_1_8_4,  // DEAD:CODE 2008
-	WME_1_8_5,  // DEAD:CODE 2008
-	WME_1_8_6,  // DEAD:CODE 2008
-	WME_1_8_7,  // DEAD:CODE 2008, released as "1.8.7 beta"
-	WME_1_8_8,  // DEAD:CODE 2008, released as "1.8.8 beta"
-	WME_1_8_9,  // DEAD:CODE 2008, released as "1.8.9 beta"
-	WME_1_8_10, // DEAD:CODE 2009
-
-	// fork of WME_1_8_10
-	WME_ANDISHE_VARAN, // Andishe Varan Engine 1.0.0.0
-
-	WME_1_8_11, // DEAD:CODE 2009
-	WME_1_9_0,  // DEAD:CODE 2009, released as "1.9.0 beta"
-
-	// fork of WME_1_9_0
-	WME_KINJAL_1_0,
-	WME_KINJAL_1_1,
-	WME_KINJAL_1_2,
-	WME_KINJAL_1_3,
-	WME_KINJAL_1_4,
-
-	// fork of WME_KINJAL_1_4
-	WME_HEROCRAFT,
-
-	WME_1_9_1,  // DEAD:CODE 2010
-
-	// fork of WME_1_9_1
-	WME_KINJAL_1_5,
-	WME_KINJAL_1_6,
-	WME_KINJAL_1_7,
-	WME_KINJAL_1_7a,
-	WME_KINJAL_1_7b,
-	WME_KINJAL_1_8,
-	WME_KINJAL_1_9,
-	WME_KINJAL_2_0,
-
-	WME_1_9_2,  // DEAD:CODE 2010
-	WME_1_9_3,  // DEAD:CODE 2012, released as "1.10.1 beta"
-	WME_LITE,
-	LATEST_VERSION,
-
-	// fork of WME_LITE
-	FOXTAIL_OLDEST_VERSION,
-	FOXTAIL_1_2_227,
-	FOXTAIL_1_2_230,
-	FOXTAIL_1_2_304,
-	FOXTAIL_1_2_362,
-	FOXTAIL_1_2_527,
-	FOXTAIL_1_2_896,
-	FOXTAIL_1_2_902,
-	FOXTAIL_LATEST_VERSION
-};
-
-} // End of namespace Wintermute
diff --git a/engines/wintermute/base/base_engine.h b/engines/wintermute/base/base_engine.h
index 0691240bd1..582c426d1b 100644
--- a/engines/wintermute/base/base_engine.h
+++ b/engines/wintermute/base/base_engine.h
@@ -34,7 +34,7 @@
 #include "common/random.h"
 #include "common/language.h"
 
-#include "engines/wintermute/base/base_detection_enums.h"
+#include "engines/wintermute/detection.h"
 
 namespace Wintermute {
 
diff --git a/engines/wintermute/detection.cpp b/engines/wintermute/detection.cpp
index ccea897d96..b59caf3cae 100644
--- a/engines/wintermute/detection.cpp
+++ b/engines/wintermute/detection.cpp
@@ -30,8 +30,6 @@
 
 #include "engines/metaengine.h"
 
-#include "wintermute/base/base_detection_enums.h"
-#include "wintermute/detection_enums.h"
 #include "wintermute/detection.h"
 #include "wintermute/detection_tables.h"
 
diff --git a/engines/wintermute/detection.h b/engines/wintermute/detection.h
index 0d75a58f27..b1ca73ee1a 100644
--- a/engines/wintermute/detection.h
+++ b/engines/wintermute/detection.h
@@ -27,6 +27,103 @@
 
 namespace Wintermute {
 
+enum WMETargetExecutable {
+	OLDEST_VERSION,
+	WME_1_0_12, // DEAD:CODE 2003
+	WME_1_0_19, // DEAD:CODE 2003
+	WME_1_0_20, // DEAD:CODE 2003
+	WME_1_0_22, // DEAD:CODE 2003
+	WME_1_0_24, // DEAD:CODE 2003
+	WME_1_0_25, // DEAD:CODE 2003
+	WME_1_0_28, // DEAD:CODE 2003
+	WME_1_0_30, // DEAD:CODE 2003
+	WME_1_0_31, // DEAD:CODE 2003
+	WME_1_1_33, // DEAD:CODE 2003
+	WME_1_1_35, // DEAD:CODE 2003
+	WME_1_1_37, // DEAD:CODE 2003
+	WME_1_1_39, // DEAD:CODE 2004
+	WME_1_2_43, // DEAD:CODE 2004
+	WME_1_2_44, // DEAD:CODE 2004
+	WME_1_3_0,  // DEAD:CODE 2004
+	WME_1_3_2,  // DEAD:CODE 2004
+	WME_1_3_3,  // DEAD:CODE 2004
+	WME_1_4_0,  // DEAD:CODE 2005
+	WME_1_4_1,  // DEAD:CODE 2005
+	WME_1_5_0,  // DEAD:CODE 2005
+	WME_1_5_2,  // DEAD:CODE 2005
+	WME_1_6_0,  // DEAD:CODE 2006
+	WME_1_6_1,  // DEAD:CODE 2006
+	WME_1_7_0,  // DEAD:CODE 2007
+	WME_1_7_1,  // DEAD:CODE 2007
+	WME_1_7_2,  // DEAD:CODE 2007
+	WME_1_7_3,  // DEAD:CODE 2007
+	WME_1_7_93, // DEAD:CODE 2007
+	WME_1_7_94, // DEAD:CODE 2007
+	WME_1_8_0,  // DEAD:CODE 2007
+	WME_1_8_1,  // DEAD:CODE 2007
+	WME_1_8_2,  // DEAD:CODE 2008
+	WME_1_8_3,  // DEAD:CODE 2008
+	WME_1_8_4,  // DEAD:CODE 2008
+	WME_1_8_5,  // DEAD:CODE 2008
+	WME_1_8_6,  // DEAD:CODE 2008
+	WME_1_8_7,  // DEAD:CODE 2008, released as "1.8.7 beta"
+	WME_1_8_8,  // DEAD:CODE 2008, released as "1.8.8 beta"
+	WME_1_8_9,  // DEAD:CODE 2008, released as "1.8.9 beta"
+	WME_1_8_10, // DEAD:CODE 2009
+
+	// fork of WME_1_8_10
+	WME_ANDISHE_VARAN, // Andishe Varan Engine 1.0.0.0
+
+	WME_1_8_11, // DEAD:CODE 2009
+	WME_1_9_0,  // DEAD:CODE 2009, released as "1.9.0 beta"
+
+	// fork of WME_1_9_0
+	WME_KINJAL_1_0,
+	WME_KINJAL_1_1,
+	WME_KINJAL_1_2,
+	WME_KINJAL_1_3,
+	WME_KINJAL_1_4,
+
+	// fork of WME_KINJAL_1_4
+	WME_HEROCRAFT,
+
+	WME_1_9_1,  // DEAD:CODE 2010
+
+	// fork of WME_1_9_1
+	WME_KINJAL_1_5,
+	WME_KINJAL_1_6,
+	WME_KINJAL_1_7,
+	WME_KINJAL_1_7a,
+	WME_KINJAL_1_7b,
+	WME_KINJAL_1_8,
+	WME_KINJAL_1_9,
+	WME_KINJAL_2_0,
+
+	WME_1_9_2,  // DEAD:CODE 2010
+	WME_1_9_3,  // DEAD:CODE 2012, released as "1.10.1 beta"
+	WME_LITE,
+	LATEST_VERSION,
+
+	// fork of WME_LITE
+	FOXTAIL_OLDEST_VERSION,
+	FOXTAIL_1_2_227,
+	FOXTAIL_1_2_230,
+	FOXTAIL_1_2_304,
+	FOXTAIL_1_2_362,
+	FOXTAIL_1_2_527,
+	FOXTAIL_1_2_896,
+	FOXTAIL_1_2_902,
+	FOXTAIL_LATEST_VERSION
+};
+
+enum WintermuteGameFeatures {
+	/** A game with low-spec resources. */
+	GF_LOWSPEC_ASSETS       = 1 << 0,
+	GF_IGNORE_SD_FILES      = 1 << 1,
+	GF_IGNORE_HD_FILES      = 1 << 2,
+	GF_3D                   = 1 << 3
+};
+
 struct WMEGameDescription {
 	ADGameDescription adDesc;
 	WMETargetExecutable targetExecutable;
diff --git a/engines/wintermute/detection_enums.h b/engines/wintermute/detection_enums.h
deleted file mode 100644
index 3b3bf05e32..0000000000
--- a/engines/wintermute/detection_enums.h
+++ /dev/null
@@ -1,38 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef WINTERMUTE_DETECTION_ENUMS_H
-#define WINTERMUTE_DETECTION_ENUMS_H
-
-namespace Wintermute {
-
-enum WintermuteGameFeatures {
-	/** A game with low-spec resources. */
-	GF_LOWSPEC_ASSETS       = 1 << 0,
-	GF_IGNORE_SD_FILES      = 1 << 1,
-	GF_IGNORE_HD_FILES      = 1 << 2,
-	GF_3D                   = 1 << 3
-};
-
-} // End of namespace Wintermute
-
-#endif // WINTERMUTE_DETECTION_ENUMS_H
diff --git a/engines/wintermute/metaengine.cpp b/engines/wintermute/metaengine.cpp
index baafb427aa..7c92d3b10b 100644
--- a/engines/wintermute/metaengine.cpp
+++ b/engines/wintermute/metaengine.cpp
@@ -29,7 +29,6 @@
 #include "engines/wintermute/achievements_tables.h"
 
 // Detection related files.
-#include "wintermute/base/base_detection_enums.h"
 #include "wintermute/detection.h"
 #include "wintermute/detection_tables.h"
 
diff --git a/engines/wintermute/wintermute.h b/engines/wintermute/wintermute.h
index 08bfa4f6e8..890c39c833 100644
--- a/engines/wintermute/wintermute.h
+++ b/engines/wintermute/wintermute.h
@@ -26,7 +26,7 @@
 #include "engines/engine.h"
 #include "gui/debugger.h"
 #include "common/fs.h"
-#include "wintermute/detection_enums.h"
+#include "wintermute/detection.h"
 
 namespace Wintermute {
 
@@ -34,7 +34,6 @@ class Console;
 class BaseGame;
 class SystemClassRegistry;
 class DebuggerController;
-struct WMEGameDescription;
 
 const int INT_MAX_VALUE = 0x7fffffff;
 
diff --git a/engines/xeen/detection.cpp b/engines/xeen/detection.cpp
index 79343db575..9a17c5b971 100644
--- a/engines/xeen/detection.cpp
+++ b/engines/xeen/detection.cpp
@@ -25,7 +25,6 @@
 #include "common/translation.h"
 
 #include "xeen/detection.h"
-#include "xeen/detection_enums.h"
 
 static const PlainGameDescriptor XeenGames[] = {
 	{ "cloudsofxeen", "Might and Magic IV: Clouds of Xeen" },
diff --git a/engines/xeen/detection.h b/engines/xeen/detection.h
index bb9f06cffd..78012e5da6 100644
--- a/engines/xeen/detection.h
+++ b/engines/xeen/detection.h
@@ -23,8 +23,17 @@
 #ifndef XEEN_DETECTION_H
 #define XEEN_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace Xeen {
 
+enum {
+	GType_Clouds = 1,
+	GType_DarkSide = 2,
+	GType_WorldOfXeen = 3,
+	GType_Swords = 4
+};
+
 struct XeenGameDescription {
 	ADGameDescription desc;
 
diff --git a/engines/xeen/detection_enums.h b/engines/xeen/detection_enums.h
deleted file mode 100644
index f173db1713..0000000000
--- a/engines/xeen/detection_enums.h
+++ /dev/null
@@ -1,37 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef XEEN_DETECTION_ENUMS_H
-#define XEEN_DETECTION_ENUMS_H
-
-namespace Xeen {
-
-enum {
-	GType_Clouds = 1,
-	GType_DarkSide = 2,
-	GType_WorldOfXeen = 3,
-	GType_Swords = 4
-};
-
-} // End of namespace Xeen
-
-#endif // XEEN_DETECTION_ENUMS_H
diff --git a/engines/xeen/xeen.h b/engines/xeen/xeen.h
index 503d6a5a99..d7387e6da6 100644
--- a/engines/xeen/xeen.h
+++ b/engines/xeen/xeen.h
@@ -47,7 +47,7 @@
 #include "xeen/sound.h"
 #include "xeen/spells.h"
 #include "xeen/window.h"
-#include "xeen/detection_enums.h"
+#include "xeen/detection.h"
 
 /**
  * This is the namespace of the Xeen engine.
@@ -96,8 +96,6 @@ enum GameMode {
 	GMODE_QUIT = 4
 };
 
-struct XeenGameDescription;
-
 #define XEEN_SAVEGAME_VERSION 2
 
 class XeenEngine : public Engine {
diff --git a/engines/zvision/detection.cpp b/engines/zvision/detection.cpp
index 25a9c2ca18..c70f8d546d 100644
--- a/engines/zvision/detection.cpp
+++ b/engines/zvision/detection.cpp
@@ -29,7 +29,6 @@
 #include "common/translation.h"
 #include "common/str-array.h"
 
-#include "zvision/detection_enums.h"
 #include "zvision/detection.h"
 #include "zvision/detection_tables.h"
 
diff --git a/engines/zvision/detection.h b/engines/zvision/detection.h
index c47243a912..6871c8ede1 100644
--- a/engines/zvision/detection.h
+++ b/engines/zvision/detection.h
@@ -23,8 +23,20 @@
 #ifndef ZVISION_DETECTION_H
 #define ZVISION_DETECTION_H
 
+#include "engines/advancedDetector.h"
+
 namespace ZVision {
 
+enum ZVisionGameId {
+	GID_NONE = 0,
+	GID_NEMESIS = 1,
+	GID_GRANDINQUISITOR = 2
+};
+
+enum ZVisionFeatures {
+	GF_DVD = (1 << 0) // ZGI DVD version
+};
+
 struct ZVisionGameDescription {
 	ADGameDescription desc;
 	ZVisionGameId gameId;
diff --git a/engines/zvision/detection_enums.h b/engines/zvision/detection_enums.h
deleted file mode 100644
index 47553aa340..0000000000
--- a/engines/zvision/detection_enums.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/* ScummVM - Graphic Adventure Engine
- *
- * ScummVM is the legal property of its developers, whose names
- * are too numerous to list here. Please refer to the COPYRIGHT
- * file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- *
- */
-
-#ifndef ZVISION_DETECTION_ENUMS_H
-#define ZVISION_DETECTION_ENUMS_H
-
-namespace ZVision {
-
-enum ZVisionGameId {
-	GID_NONE = 0,
-	GID_NEMESIS = 1,
-	GID_GRANDINQUISITOR = 2
-};
-
-enum ZVisionFeatures {
-	GF_DVD = (1 << 0) // ZGI DVD version
-};
-
-} // End of namespace ZVision
-
-#endif // ZVISION_DETECTION_ENUMS_H
diff --git a/engines/zvision/zvision.h b/engines/zvision/zvision.h
index 5cdb4ea9cb..19358441ca 100644
--- a/engines/zvision/zvision.h
+++ b/engines/zvision/zvision.h
@@ -26,7 +26,7 @@
 
 #include "zvision/core/clock.h"
 #include "zvision/file/search_manager.h"
-#include "zvision/detection_enums.h"
+#include "zvision/detection.h"
 
 #include "common/random.h"
 #include "common/events.h"
@@ -57,7 +57,6 @@ class VideoDecoder;
  */
 namespace ZVision {
 
-struct ZVisionGameDescription;
 class Console;
 class ScriptManager;
 class RenderManager;


Commit: 973526a4d3b9d424eca91738faf1e4ebd8a9e7e2
    https://github.com/scummvm/scummvm/commit/973526a4d3b9d424eca91738faf1e4ebd8a9e7e2
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BBVS: Fix compilation

Changed paths:
    engines/bbvs/detection.cpp
    engines/bbvs/detection.h
    engines/bbvs/metaengine.cpp


diff --git a/engines/bbvs/detection.cpp b/engines/bbvs/detection.cpp
index a5d30d8806..4b50e7ce7d 100644
--- a/engines/bbvs/detection.cpp
+++ b/engines/bbvs/detection.cpp
@@ -30,16 +30,8 @@ static const PlainGameDescriptor bbvsGames[] = {
 	{ 0, 0 }
 };
 
-enum BBVSGameFeatures {
-	GF_LOOGIE_DEMO = (1 << 0)
-};
-
 namespace Bbvs {
 
-bool BbvsEngine::isLoogieDemo() const {
-	return _gameDescription->flags & GF_LOOGIE_DEMO;
-}
-
 static const ADGameDescription gameDescriptions[] = {
 	{
 		"bbvs",
diff --git a/engines/bbvs/detection.h b/engines/bbvs/detection.h
index 01d75218d7..c798c0222d 100644
--- a/engines/bbvs/detection.h
+++ b/engines/bbvs/detection.h
@@ -31,4 +31,8 @@ enum {
 
 } // End of namespace Bbvs
 
+enum BBVSGameFeatures {
+	GF_LOOGIE_DEMO = (1 << 0)
+};
+
 #endif // BBVS_DETECTION_H
diff --git a/engines/bbvs/metaengine.cpp b/engines/bbvs/metaengine.cpp
index e1c335d45a..c888af3fe5 100644
--- a/engines/bbvs/metaengine.cpp
+++ b/engines/bbvs/metaengine.cpp
@@ -29,6 +29,14 @@
 #include "base/plugins.h"
 #include "graphics/thumbnail.h"
 
+namespace Bbvs {
+
+bool BbvsEngine::isLoogieDemo() const {
+	return _gameDescription->flags & GF_LOOGIE_DEMO;
+}
+
+} // End of namespace Bbvs
+
 class BbvsMetaEngineConnect : public AdvancedMetaEngineConnect {
 public:
 	const char *getName() const override {


Commit: 2c2f21b0cdea1db912f242c7d26be84e8700eb43
    https://github.com/scummvm/scummvm/commit/2c2f21b0cdea1db912f242c7d26be84e8700eb43
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
NEVERHOOD: Fix compilation

Changed paths:
    engines/neverhood/detection.h
    engines/neverhood/metaengine.cpp


diff --git a/engines/neverhood/detection.h b/engines/neverhood/detection.h
index 143165b720..45852fd42c 100644
--- a/engines/neverhood/detection.h
+++ b/engines/neverhood/detection.h
@@ -25,13 +25,8 @@
 
 namespace Neverhood {
 
-struct NeverhoodGameDescription {
-	ADGameDescription desc;
-
-	int gameID;
-	int gameType;
-	uint32 features;
-	uint16 version;
+enum NeverhoodGameFeatures {
+	GF_BIG_DEMO = (1 << 0)
 };
 
 } // End of namespace Neverhood
diff --git a/engines/neverhood/metaengine.cpp b/engines/neverhood/metaengine.cpp
index 239a1955d6..3f7ed7aca3 100644
--- a/engines/neverhood/metaengine.cpp
+++ b/engines/neverhood/metaengine.cpp
@@ -29,10 +29,6 @@
 #include "neverhood/neverhood.h"
 #include "neverhood/detection.h"
 
-enum NeverhoodGameFeatures {
-	GF_BIG_DEMO = (1 << 0)
-};
-
 namespace Neverhood {
 
 const char *NeverhoodEngine::getGameId() const {


Commit: ceabaf3b0dbc9ed68d8cfa1ab76c5a87e84d97db
    https://github.com/scummvm/scummvm/commit/ceabaf3b0dbc9ed68d8cfa1ab76c5a87e84d97db
Author: Eugene Sandulenko (sev at scummvm.org)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: Added override keywords

Changed paths:
    base/plugins.h
    engines/advancedDetector.h


diff --git a/base/plugins.h b/base/plugins.h
index 45f7a2d381..f7d7308762 100644
--- a/base/plugins.h
+++ b/base/plugins.h
@@ -397,16 +397,16 @@ protected:
 	bool loadPluginByFileName(const Common::String &filename);
 
 public:
-	virtual void init();
-	virtual void loadFirstPlugin();
-	virtual bool loadNextPlugin();
-	virtual bool loadPluginFromEngineId(const Common::String &engineId);
-	virtual void updateConfigWithFileName(const Common::String &engineId);
+	virtual void init() override;
+	virtual void loadFirstPlugin() override;
+	virtual bool loadNextPlugin() override;
+	virtual bool loadPluginFromEngineId(const Common::String &engineId) override;
+	virtual void updateConfigWithFileName(const Common::String &engineId) override;
 	virtual void loadDetectionPlugin() override;
 	virtual void unloadDetectionPlugin() override;
 
-	virtual void loadAllPlugins() {} 	// we don't allow these
-	virtual void loadAllPluginsOfType(PluginType type) {}
+	virtual void loadAllPlugins() override {} 	// we don't allow these
+	virtual void loadAllPluginsOfType(PluginType type) override {}
 };
 
 #endif
diff --git a/engines/advancedDetector.h b/engines/advancedDetector.h
index 972b214644..8cda4b27d2 100644
--- a/engines/advancedDetector.h
+++ b/engines/advancedDetector.h
@@ -349,7 +349,7 @@ public:
 	 *
 	 * @see MetaEngineConnect::getName().
 	 */
-	virtual const char *getName() const = 0;
+	virtual const char *getName() const override = 0;
 
 public:
 	typedef Common::HashMap<Common::String, Common::FSNode, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> FileMap;


Commit: 32799c1ee89f5b1571cd22293525b984ee0e47ed
    https://github.com/scummvm/scummvm/commit/32799c1ee89f5b1571cd22293525b984ee0e47ed
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCUMM: Fix naming for ScummMetaEngineConnect

Changed paths:
    engines/scumm/metaengine.cpp


diff --git a/engines/scumm/metaengine.cpp b/engines/scumm/metaengine.cpp
index 18a76618d1..027287ede0 100644
--- a/engines/scumm/metaengine.cpp
+++ b/engines/scumm/metaengine.cpp
@@ -246,7 +246,7 @@ bool ScummEngine::hasFeature(EngineFeature f) const {
  *
  * This is heavily based on our MD5 detection scheme.
  */
-Common::Error ScummMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
+Common::Error ScummMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
 	assert(syst);
 	assert(engine);
 	const char *gameid = ConfMan.get("gameid").c_str();


Commit: 9eb564b89f577700bf9aaccb975e68e4ef6764b8
    https://github.com/scummvm/scummvm/commit/9eb564b89f577700bf9aaccb975e68e4ef6764b8
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCI: Move common enum -> detection.h

Changed paths:
    engines/sci/detection.h
    engines/sci/sci.h


diff --git a/engines/sci/detection.h b/engines/sci/detection.h
index cb6a8a150f..ec81fc0e36 100644
--- a/engines/sci/detection.h
+++ b/engines/sci/detection.h
@@ -142,6 +142,13 @@ enum SciVersion {
 	SCI_VERSION_3 // LSL7, Lighthouse, RAMA, Phantasmagoria 2
 };
 
+/** MIDI devices */
+enum kMidiMode {
+	kMidiModeStandard,
+	kMidiModeFB01,
+	kMidiModeD110
+};
+
 } // End of namespace Sci
 
 #endif // SCI_DETECTION_H
diff --git a/engines/sci/sci.h b/engines/sci/sci.h
index dd70eab191..9df0063917 100644
--- a/engines/sci/sci.h
+++ b/engines/sci/sci.h
@@ -132,13 +132,6 @@ enum kLanguage {
 	K_LANG_PORTUGUESE = 351
 };
 
-/** MIDI devices */
-enum kMidiMode {
-	kMidiModeStandard,
-	kMidiModeFB01,
-	kMidiModeD110
-};
-
 class SciEngine : public Engine {
 	friend class Console;
 public:


Commit: 102b22f4a8ebf4ddeb6fea0c077b26c588974731
    https://github.com/scummvm/scummvm/commit/102b22f4a8ebf4ddeb6fea0c077b26c588974731
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCI: Fix naming for SciMetaEngineConnect

Changed paths:
    engines/sci/metaengine.cpp


diff --git a/engines/sci/metaengine.cpp b/engines/sci/metaengine.cpp
index 2596211318..c5ec465f60 100644
--- a/engines/sci/metaengine.cpp
+++ b/engines/sci/metaengine.cpp
@@ -352,7 +352,7 @@ bool SciEngine::hasFeature(EngineFeature f) const {
 		//  and some other times it won't work.
 }
 
-SaveStateList SciMetaEngine::listSaves(const char *target) const {
+SaveStateList SciMetaEngineConnect::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;


Commit: 6679c7e72e9e60aa19c72c4185b3414b2e550caa
    https://github.com/scummvm/scummvm/commit/6679c7e72e9e60aa19c72c4185b3414b2e550caa
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GLK: Fix modules to build

- Creating an instance of GLK requires searching through all sub-engine detection lists.
- So, these must be there at the time of creating an instance of GLK.
- Hence, all these objects will ONLY be skipped from static-detection, if GLK itself is static.
- The above point is because it will need to avoid duplicate symbols.

Changed paths:
    engines/glk/module.mk


diff --git a/engines/glk/module.mk b/engines/glk/module.mk
index d9892b3bb4..24492c8c10 100644
--- a/engines/glk/module.mk
+++ b/engines/glk/module.mk
@@ -296,7 +296,25 @@ MODULE_OBJS := \
 	zcode/quetzal.o \
 	zcode/screen.o \
 	zcode/sound_folder.o \
-	zcode/windows.o
+	zcode/windows.o \
+	detection.o \
+	adrift/detection.o \
+	advsys/detection.o \
+	agt/detection.o \
+	alan2/detection.o \
+	alan3/detection.o \
+	archetype/detection.o \
+	comprehend/detection.o \
+	glulx/detection.o \
+	hugo/detection.o \
+	jacl/detection.o \
+	level9/detection.o \
+	magnetic/detection.o \
+	quest/detection.o \
+	scott/detection.o \
+	tads/detection.o \
+	zcode/detection.o
+
 
 # This module can be built as a plugin
 ifeq ($(ENABLE_GLK), DYNAMIC_PLUGIN)
@@ -306,6 +324,9 @@ endif
 # Include common rules
 include $(srcdir)/rules.mk
 
+# Skip building the following objects if a static
+# module is enabled, because it already has the contents.
+ifneq ($(ENABLE_GLK), STATIC_PLUGIN)
 # Detection objects
 DETECT_OBJS += $(MODULE)/detection.o
 
@@ -327,9 +348,6 @@ DETECT_OBJS += $(MODULE)/scott/detection.o
 DETECT_OBJS += $(MODULE)/tads/detection.o
 DETECT_OBJS += $(MODULE)/zcode/detection.o
 
-# Skip building the following objects if a static
-# module is enabled, because it already has the contents.
-ifneq ($(ENABLE_GLK), STATIC_PLUGIN)
 # Dependencies of detection objects
 DETECT_OBJS += $(MODULE)/blorb.o
 DETECT_OBJS += $(MODULE)/advsys/game.o


Commit: a9841622e00634859e2bc34e1e7031658077e5cd
    https://github.com/scummvm/scummvm/commit/a9841622e00634859e2bc34e1e7031658077e5cd
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: DETECTION: Use inheritance hierarchy and mimic existing plugins.

Changed paths:
    base/plugins.cpp
    engines/detection.cpp
    engines/detection.h


diff --git a/base/plugins.cpp b/base/plugins.cpp
index f3f5702c0d..79ba2b58cc 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -466,7 +466,8 @@ void PluginManagerUncached::loadDetectionPlugin() {
 
 	if (linkMetaEngines) {
 		_pluginsInMem[PLUGIN_TYPE_METAENGINE].clear();
-		PluginList &pl = (_detectionPlugin)->get<Detection>()._pl;
+		const Detection &detectionConnect = _detectionPlugin->get<Detection>();
+		const PluginList &pl = detectionConnect.getPlugins();
 		Common::for_each(pl.begin(), pl.end(), Common::bind1st(Common::mem_fun(&PluginManagerUncached::tryLoadPlugin), this));
 	}
 
diff --git a/engines/detection.cpp b/engines/detection.cpp
index 64d8a9b0db..905a63191a 100644
--- a/engines/detection.cpp
+++ b/engines/detection.cpp
@@ -26,22 +26,29 @@
 #include "engines/advanceddetector.h"
 #include "engines/detection.h"
 
-const char *Detection::getName() const {
-    return "detection";
-}
 
-Detection::Detection() {
+class DetectionConnect : public Detection {
+public:
+    DetectionConnect() {}
+    ~DetectionConnect() {}
 
-    #define LINK_PLUGIN(ID) \
+    const char *getName() const override {
+        return "detection";
+    }
+
+    PluginList getPlugins() const override {
+        PluginList pl;
+
+        #define LINK_PLUGIN(ID) \
 			extern PluginType g_##ID##_type; \
 			extern PluginObject *g_##ID##_getObject(); \
-			_pl.push_back(new StaticPlugin(g_##ID##_getObject(), g_##ID##_type));
+			pl.push_back(new StaticPlugin(g_##ID##_getObject(), g_##ID##_type));
 
-    #include "engines/detection_table.h"
-}
+        #include "engines/detection_table.h"
 
-Detection::~Detection() {
-}
+        return pl;
+    }
+};
 
-REGISTER_PLUGIN_DYNAMIC(DETECTION_DYNAMIC, PLUGIN_TYPE_DETECTION, Detection);
+REGISTER_PLUGIN_DYNAMIC(DETECTION_DYNAMIC, PLUGIN_TYPE_DETECTION, DetectionConnect);
 
diff --git a/engines/detection.h b/engines/detection.h
index da79b432a7..181afd5a4b 100644
--- a/engines/detection.h
+++ b/engines/detection.h
@@ -24,10 +24,9 @@
 
 class Detection : public PluginObject {
 public:
-    PluginList _pl;
-public:
-    Detection();
-    ~Detection();
+    Detection() {}
+    virtual ~Detection() {}
 
-    const char *getName() const override;
+    virtual const char *getName() const = 0;
+    virtual PluginList getPlugins() const = 0;
 };


Commit: e08748866e603ff2f6e02c48c5a964a3741c25b1
    https://github.com/scummvm/scummvm/commit/e08748866e603ff2f6e02c48c5a964a3741c25b1
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCI & WINTERMUTE: Fix unsafe code for fallbackDetect

- Using static for plugins will result in crash if the plugins are unloaded after being called for the first time.
- Good example is when UncachedPluginMan uses these.

Changed paths:
    engines/sci/detection.cpp
    engines/wintermute/detection.cpp


diff --git a/engines/sci/detection.cpp b/engines/sci/detection.cpp
index d12b948b58..14999583ff 100644
--- a/engines/sci/detection.cpp
+++ b/engines/sci/detection.cpp
@@ -450,10 +450,10 @@ ADDetectedGame SciMetaEngine::fallbackDetect(const FileMap &allFiles, const Comm
 	 * Fallback detection for Sci heavily depends on engine resources, so it's not possible
 	 * to use them without the engine present in a clean way.
 	 */
-	static const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
+	const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
 
 	if (metaEnginePlugin) {
-		static const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+		const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
 		if (enginePlugin) {
 			return enginePlugin->get<AdvancedMetaEngineConnect>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
 		} else {
diff --git a/engines/wintermute/detection.cpp b/engines/wintermute/detection.cpp
index b59caf3cae..6fb976924c 100644
--- a/engines/wintermute/detection.cpp
+++ b/engines/wintermute/detection.cpp
@@ -94,10 +94,10 @@ public:
 		 * Fallback detection for Wintermute heavily depends on engine resources, so it's not possible
 		 * to use them without the engine present in a clean way.
 		 */
-		static const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
+		const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
 
 		if (metaEnginePlugin) {
-			static const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+			const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
 			if (enginePlugin) {
 				return enginePlugin->get<AdvancedMetaEngineConnect>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
 			} else {


Commit: 13f2a0afb074456da35ece7509a933e704d5f52b
    https://github.com/scummvm/scummvm/commit/13f2a0afb074456da35ece7509a933e704d5f52b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCUMM: DETECTION: Remove sneaky main engine headers.

Changed paths:
    engines/scumm/detection_tables.h
    engines/scumm/file.cpp


diff --git a/engines/scumm/detection_tables.h b/engines/scumm/detection_tables.h
index 50bc9755ff..e4720c6bfb 100644
--- a/engines/scumm/detection_tables.h
+++ b/engines/scumm/detection_tables.h
@@ -29,7 +29,6 @@
 #include "common/util.h"
 
 #include "scumm/detection.h"
-#include "scumm/scumm.h"
 
 #include "scumm/scumm-md5.h"
 
diff --git a/engines/scumm/file.cpp b/engines/scumm/file.cpp
index 9e0dfeaff1..d1d8674d04 100644
--- a/engines/scumm/file.cpp
+++ b/engines/scumm/file.cpp
@@ -22,8 +22,6 @@
 
 #include "scumm/file.h"
 
-#include "scumm/scumm.h"
-
 #include "common/memstream.h"
 #include "common/substream.h"
 


Commit: 9624bfeb154d3d0691ca10233538046ceb741d80
    https://github.com/scummvm/scummvm/commit/9624bfeb154d3d0691ca10233538046ceb741d80
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCUMM: Move common detection/engine enums into detection.h

Changed paths:
    engines/scumm/detection.h
    engines/scumm/scumm.h


diff --git a/engines/scumm/detection.h b/engines/scumm/detection.h
index 0587c3fab1..11d3abf3c5 100644
--- a/engines/scumm/detection.h
+++ b/engines/scumm/detection.h
@@ -127,6 +127,103 @@ struct DetectorResult {
 	const char *extra;
 };
 
+/**
+ * SCUMM feature flags define for every game which specific set of engine
+ * features are used by that game.
+ * Note that some of them could be replaced by checks for the SCUMM version.
+ */
+enum GameFeatures {
+	/** A demo, not a full blown game. */
+	GF_DEMO = 1 << 0,
+
+	/** Games with the AKOS costume system (ScummEngine_v7 and subclasses, HE games). */
+	GF_NEW_COSTUMES = 1 << 2,
+
+	/** Games using XOR encrypted data files. */
+	GF_USE_KEY = 1 << 4,
+
+	/** Small header games (ScummEngine_v4 and subclasses). */
+	GF_SMALL_HEADER = 1 << 5,
+
+	/** Old bundle games (ScummEngine_v3old and subclasses). */
+	GF_OLD_BUNDLE = 1 << 6,
+
+	/** EGA games. */
+	GF_16COLOR = 1 << 7,
+
+	/** VGA versions of V3 games.  Equivalent to (version == 3 && not GF_16COLOR) */
+	GF_OLD256 = 1 << 8,
+
+	/** Games which have Audio CD tracks. */
+	GF_AUDIOTRACKS = 1 << 9,
+
+	/**
+	 * Games using only very few local variables in scripts.
+	 * Apparently that is only the case for 256 color version of Indy3.
+	 */
+	GF_FEW_LOCALS = 1 << 11,
+
+	/** HE games for which localized versions exist */
+	GF_HE_LOCALIZED = 1 << 13,
+
+	/**
+	 *  HE games with more global scripts and different sprite handling
+	 *  i.e. read it as HE version 9.85. Used for HE98 only.
+	 */
+	GF_HE_985 = 1 << 14,
+
+	/** HE games with 16 bit color */
+	GF_16BIT_COLOR = 1 << 15,
+
+	/**
+	 * SCUMM v5-v7 Mac games stored in a container file
+	 * Used to differentiate between m68k and PPC versions of Indy4
+	 */
+	GF_MAC_CONTAINER = 1 << 16
+};
+
+enum ScummGameId {
+	GID_CMI,
+	GID_DIG,
+	GID_FT,
+	GID_INDY3,
+	GID_INDY4,
+	GID_LOOM,
+	GID_MANIAC,
+	GID_MONKEY_EGA,
+	GID_MONKEY_VGA,
+	GID_MONKEY,
+	GID_MONKEY2,
+	GID_PASS,
+	GID_SAMNMAX,
+	GID_TENTACLE,
+	GID_ZAK,
+
+	GID_HEGAME,      // Generic name for all HE games with default behavior
+	GID_PUTTDEMO,
+	GID_FBEAR,
+	GID_PUTTMOON,
+	GID_FUNPACK,
+	GID_PUTTZOO,
+	GID_FREDDI3,
+	GID_BIRTHDAYRED,
+	GID_BIRTHDAYYELLOW,
+	GID_TREASUREHUNT,
+	GID_PUTTRACE,
+	GID_FUNSHOP,	// Used for all three funshops
+	GID_FOOTBALL,
+	GID_FOOTBALL2002,
+	GID_SOCCER,
+	GID_SOCCERMLS,
+	GID_SOCCER2004,
+	GID_BASEBALL2001,
+	GID_BASEBALL2003,
+	GID_BASKETBALL,
+	GID_MOONBASE,
+	GID_PJGAMES,
+	GID_HECUP		// CUP demos
+};
+
 } // End of namespace Scumm
 
 
diff --git a/engines/scumm/scumm.h b/engines/scumm/scumm.h
index 550ae0f6b1..cb9daad229 100644
--- a/engines/scumm/scumm.h
+++ b/engines/scumm/scumm.h
@@ -104,61 +104,6 @@ enum {
 	NUM_SHADOW_PALETTE = 8
 };
 
-/**
- * SCUMM feature flags define for every game which specific set of engine
- * features are used by that game.
- * Note that some of them could be replaced by checks for the SCUMM version.
- */
-enum GameFeatures {
-	/** A demo, not a full blown game. */
-	GF_DEMO                = 1 << 0,
-
-	/** Games with the AKOS costume system (ScummEngine_v7 and subclasses, HE games). */
-	GF_NEW_COSTUMES        = 1 << 2,
-
-	/** Games using XOR encrypted data files. */
-	GF_USE_KEY             = 1 << 4,
-
-	/** Small header games (ScummEngine_v4 and subclasses). */
-	GF_SMALL_HEADER        = 1 << 5,
-
-	/** Old bundle games (ScummEngine_v3old and subclasses). */
-	GF_OLD_BUNDLE          = 1 << 6,
-
-	/** EGA games. */
-	GF_16COLOR             = 1 << 7,
-
-	/** VGA versions of V3 games.  Equivalent to (version == 3 && not GF_16COLOR) */
-	GF_OLD256              = 1 << 8,
-
-	/** Games which have Audio CD tracks. */
-	GF_AUDIOTRACKS         = 1 << 9,
-
-	/**
-	 * Games using only very few local variables in scripts.
-	 * Apparently that is only the case for 256 color version of Indy3.
-	 */
-	GF_FEW_LOCALS          = 1 << 11,
-
-	/** HE games for which localized versions exist */
-	GF_HE_LOCALIZED        = 1 << 13,
-
-	/**
-	 *  HE games with more global scripts and different sprite handling
-	 *  i.e. read it as HE version 9.85. Used for HE98 only.
-	 */
-	GF_HE_985             = 1 << 14,
-
-	/** HE games with 16 bit color */
-	GF_16BIT_COLOR         = 1 << 15,
-
-	/**
-	 * SCUMM v5-v7 Mac games stored in a container file
-	 * Used to differentiate between m68k and PPC versions of Indy4
-	 */
-	GF_MAC_CONTAINER       = 1 << 16
-};
-
 /* SCUMM Debug Channels */
 void debugC(int level, const char *s, ...) GCC_PRINTF(2, 3);
 
@@ -219,48 +164,6 @@ enum {
 	MBS_MAX_KEY	= 0x0200
 };
 
-enum ScummGameId {
-	GID_CMI,
-	GID_DIG,
-	GID_FT,
-	GID_INDY3,
-	GID_INDY4,
-	GID_LOOM,
-	GID_MANIAC,
-	GID_MONKEY_EGA,
-	GID_MONKEY_VGA,
-	GID_MONKEY,
-	GID_MONKEY2,
-	GID_PASS,
-	GID_SAMNMAX,
-	GID_TENTACLE,
-	GID_ZAK,
-
-	GID_HEGAME,      // Generic name for all HE games with default behavior
-	GID_PUTTDEMO,
-	GID_FBEAR,
-	GID_PUTTMOON,
-	GID_FUNPACK,
-	GID_PUTTZOO,
-	GID_FREDDI3,
-	GID_BIRTHDAYRED,
-	GID_BIRTHDAYYELLOW,
-	GID_TREASUREHUNT,
-	GID_PUTTRACE,
-	GID_FUNSHOP,	// Used for all three funshops
-	GID_FOOTBALL,
-	GID_FOOTBALL2002,
-	GID_SOCCER,
-	GID_SOCCERMLS,
-	GID_SOCCER2004,
-	GID_BASEBALL2001,
-	GID_BASEBALL2003,
-	GID_BASKETBALL,
-	GID_MOONBASE,
-	GID_PJGAMES,
-	GID_HECUP		// CUP demos
-};
-
 struct SentenceTab {
 	byte verb;
 	byte preposition;


Commit: 1b3eec42526bd017c172243fa824ee87f5317cc4
    https://github.com/scummvm/scummvm/commit/1b3eec42526bd017c172243fa824ee87f5317cc4
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
SCI: Assign proper naming for building options widget

- The base class is temporarily named buildOptionsWidgetStatic.

Changed paths:
    engines/sci/detection.cpp


diff --git a/engines/sci/detection.cpp b/engines/sci/detection.cpp
index 14999583ff..24aedd3b79 100644
--- a/engines/sci/detection.cpp
+++ b/engines/sci/detection.cpp
@@ -431,7 +431,7 @@ public:
 
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
 	void registerDefaultSettings(const Common::String &target) const override;
-	GUI::OptionsContainerWidget *buildEngineOptionsWidget(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const override;
+	GUI::OptionsContainerWidget *buildEngineOptionsWidgetStatic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const override;
 };
 
 void SciMetaEngine::registerDefaultSettings(const Common::String &target) const {
@@ -441,7 +441,7 @@ void SciMetaEngine::registerDefaultSettings(const Common::String &target) const
 		ConfMan.registerDefault(entry->configOption, entry->defaultState);
 }
 
-GUI::OptionsContainerWidget *SciMetaEngine::buildEngineOptionsWidget(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
+GUI::OptionsContainerWidget *SciMetaEngine::buildEngineOptionsWidgetStatic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
 	return new OptionsWidget(boss, name, target);
 }
 


Commit: de56694f53d469451cb0354def05c6a804ad96e0
    https://github.com/scummvm/scummvm/commit/de56694f53d469451cb0354def05c6a804ad96e0
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DEVTOOLS: CREATE_PROJECT: Support static detection features

- This allows apps that use create_project to build with statically linked detection features.
- Also add support to write an addtional file - detection_tables.h inside engines/.

Changed paths:
    devtools/create_project/create_project.cpp
    devtools/create_project/create_project.h


diff --git a/devtools/create_project/create_project.cpp b/devtools/create_project/create_project.cpp
index e60b3957f8..5468435f52 100644
--- a/devtools/create_project/create_project.cpp
+++ b/devtools/create_project/create_project.cpp
@@ -103,6 +103,8 @@ enum ProjectType {
 	kProjectXcode
 };
 
+std::unordered_map<std::string, bool> isEngineEnabled;
+
 int main(int argc, char *argv[]) {
 #ifndef USE_WIN32_API
 	// Initialize random number generator for UUID creation
@@ -312,6 +314,7 @@ int main(int argc, char *argv[]) {
 					break;
 				}
 			}
+			isEngineEnabled[i->name] = true;
 		}
 	}
 
@@ -402,6 +405,10 @@ int main(int argc, char *argv[]) {
 		setup.defines.push_back("USE_SDL2");
 	}
 
+	if (setup.useStaticDetection) {
+		setup.defines.push_back("DETECTION_STATIC");
+	}
+
 	// List of global warnings and map of project-specific warnings
 	// FIXME: As shown below these two structures have different behavior for
 	// Code::Blocks and MSVC. In Code::Blocks this is used to enable *and*
@@ -1057,7 +1064,8 @@ const Feature s_features[] = {
 	                                                                                                           // is just no current way of properly detecting this...
 	{     "text-console", "USE_TEXT_CONSOLE_FOR_DEBUGGER", false, false, "Text console debugger" }, // This feature is always applied in xcode projects
 	{              "tts",                       "USE_TTS", false, true,  "Text to speech support"},
-	{"builtin-resources",             "BUILTIN_RESOURCES", false, true,  "include resources (e.g. engine data, fonts) into the binary"}
+	{"builtin-resources",             "BUILTIN_RESOURCES", false, true,  "include resources (e.g. engine data, fonts) into the binary"},
+	{"detection-static", "USE_DETECTION_FEATURES_STATIC",  "", true,  "Static linking of detection objects for engines."}
 };
 
 const Tool s_tools[] = {
@@ -1539,6 +1547,24 @@ void ProjectProvider::createProject(BuildSetup &setup) {
 		createModuleList(setup.srcDir + "/video", setup.defines, setup.testDirs, in, ex);
 		createModuleList(setup.srcDir + "/image", setup.defines, setup.testDirs, in, ex);
 
+		// Create engine-detection submodules.
+		if (setup.useStaticDetection) {
+			std::vector<std::string> detectionModuleDirs;
+			detectionModuleDirs.reserve(setup.engines.size());
+
+			for (EngineDescList::const_iterator i = setup.engines.begin(), end = setup.engines.end(); i != end; ++i) {
+				// We ignore all sub engines here because they require no special handling.
+				if (isSubEngine(i->name, setup.engines)) {
+					continue;
+				}
+				detectionModuleDirs.push_back(setup.srcDir + "/engines/" + i->name);
+			}
+
+			for (std::string &str : detectionModuleDirs) {
+				createModuleList(str, setup.defines, setup.testDirs, in, ex, true);
+			}
+		}
+
 		// Resource files
 		addResourceFiles(setup, in, ex);
 
@@ -1562,7 +1588,7 @@ void ProjectProvider::createProject(BuildSetup &setup) {
 	createOtherBuildFiles(setup);
 
 	// In case we create the main ScummVM project files we will need to
-	// generate engines/plugins_table.h too.
+	// generate engines/plugins_table.h & engines/detection_table.h
 	if (!setup.tests && !setup.devTools) {
 		createEnginePluginsTable(setup);
 	}
@@ -1740,7 +1766,7 @@ void ProjectProvider::addFilesToProject(const std::string &dir, std::ofstream &p
 	delete files;
 }
 
-void ProjectProvider::createModuleList(const std::string &moduleDir, const StringList &defines, StringList &testDirs, StringList &includeList, StringList &excludeList) const {
+void ProjectProvider::createModuleList(const std::string &moduleDir, const StringList &defines, StringList &testDirs, StringList &includeList, StringList &excludeList, bool forDetection) const {
 	const std::string moduleMkFile = moduleDir + "/module.mk";
 	std::ifstream moduleMk(moduleMkFile.c_str());
 	if (!moduleMk)
@@ -1752,6 +1778,7 @@ void ProjectProvider::createModuleList(const std::string &moduleDir, const Strin
 	shouldInclude.push(true);
 
 	StringList filesInVariableList;
+	std::string moduleRootDir;
 
 	bool hadModule = false;
 	std::string line;
@@ -1785,6 +1812,10 @@ void ProjectProvider::createModuleList(const std::string &moduleDir, const Strin
 				error("MODULE root " + moduleRoot + " does not match base dir " + moduleDir);
 
 			hadModule = true;
+			if (forDetection) {
+				moduleRootDir = moduleRoot;
+				break;
+			}
 		} else if (*i == "MODULE_OBJS") {
 			if (tokens.size() < 3)
 				error("Malformed MODULE_OBJS definition in " + moduleMkFile);
@@ -1952,12 +1983,95 @@ void ProjectProvider::createModuleList(const std::string &moduleDir, const Strin
 			shouldInclude.pop();
 		} else if (*i == "elif") {
 			error("Unsupported operation 'elif' in " + moduleMkFile);
-		} else if (*i == "ifeq") {
+		} else if (*i == "ifeq" || *i == "ifneq") {
 			//XXX
 			shouldInclude.push(false);
 		}
 	}
 
+	if (forDetection) {
+		int p = moduleRootDir.find('/');
+		std::string engineName = moduleRootDir.substr(p + 1);
+		std::string engineNameUpper;
+
+		for (char &c : engineName) {
+			engineNameUpper += toupper(c);
+		}
+		for (;;) {
+			std::getline(moduleMk, line);
+
+			if (moduleMk.eof())
+				break;
+
+			if (moduleMk.fail())
+				error("Failed while reading from " + moduleMkFile);
+
+			TokenList tokens = tokenize(line);
+			if (tokens.empty())
+				continue;
+
+			TokenList::const_iterator i = tokens.begin();
+
+			if (*i != "DETECT_OBJS" && *i != "ifneq") {
+				continue;
+			}
+
+			if (*i == "ifneq") {
+				++i;
+				if (*i != ("($(ENABLE_" + engineNameUpper + "),")) {
+					continue;
+				}
+
+				// If the engine is already enabled, skip the additional
+				// dependencies for detection objects.
+				if (isEngineEnabled[engineName]) {
+					bool breakEarly = false;
+					while (true) {
+						std::getline(moduleMk, line);
+						if (moduleMk.eof()) {
+							error("Unexpected EOF found, while parsing for " + engineName + " engine's module file.");
+						} else if (line != "endif") {
+							continue;
+						} else {
+							breakEarly = true;
+							break;
+						}
+					}
+					if (breakEarly) {
+						break;
+					}
+				}
+
+				while (*i != "DETECT_OBJS") {
+					std::getline(moduleMk, line);
+					if (moduleMk.eof()) {
+						break;
+					}
+
+					tokens = tokenize(line);
+
+					if (tokens.empty())
+						continue;
+					i = tokens.begin();
+				}
+			}
+
+
+			if (tokens.size() < 3)
+				error("Malformed DETECT_OBJS definition in " + moduleMkFile);
+			++i;
+
+			if (*i != "+=")
+				error("Malformed DETECT_OBJS definition in " + moduleMkFile);
+
+			++i;
+
+			p = (*i).find('/');
+			const std::string filename = moduleDir + "/" + (*i).substr(p + 1);
+
+			includeList.push_back(filename);
+		}
+	}
 	if (shouldInclude.size() != 1)
 		error("Malformed file " + moduleMkFile);
 }
@@ -1966,17 +2080,29 @@ void ProjectProvider::createEnginePluginsTable(const BuildSetup &setup) {
 	// First we need to create the "engines" directory.
 	createDirectory(setup.outputDir + "/engines");
 
-	// Then, we can generate the actual "plugins_table.h" file.
+	// Then, we can generate the actual "plugins_table.h" & "detection_table.h" file.
 	const std::string enginePluginsTableFile = setup.outputDir + "/engines/plugins_table.h";
+	const std::string detectionTableFile = setup.outputDir + "/engines/detection_table.h";
+
 	std::ofstream enginePluginsTable(enginePluginsTableFile.c_str());
+	std::ofstream detectionTable(detectionTableFile.c_str());
+
 	if (!enginePluginsTable) {
 		error("Could not open \"" + enginePluginsTableFile + "\" for writing");
 	}
 
+	if (!detectionTable) {
+		error("Could not open \"" + detectionTableFile + "\" for writing");
+	}
+
 	enginePluginsTable << "/* This file is automatically generated by create_project */\n"
 	                   << "/* DO NOT EDIT MANUALLY */\n"
 	                   << "// This file is being included by \"base/plugins.cpp\"\n";
 
+	detectionTable	   << "/* This file is automatically generated by create_project */\n"
+	                   << "/* DO NOT EDIT MANUALLY */\n"
+	                   << "// This file is being included by \"base/plugins.cpp\"\n";
+
 	for (EngineDescList::const_iterator i = setup.engines.begin(), end = setup.engines.end(); i != end; ++i) {
 		// We ignore all sub engines here because they require no special
 		// handling.
@@ -1991,6 +2117,8 @@ void ProjectProvider::createEnginePluginsTable(const BuildSetup &setup) {
 		enginePluginsTable << "#if PLUGIN_ENABLED_STATIC(" << engineName << ")\n"
 		                   << "LINK_PLUGIN(" << engineName << ")\n"
 		                   << "#endif\n";
+
+		detectionTable << "LINK_PLUGIN(" << engineName << "_DETECTION)\n";
 	}
 }
 } // namespace CreateProjectTool
diff --git a/devtools/create_project/create_project.h b/devtools/create_project/create_project.h
index a3a4fd20e8..231ca8c8bc 100644
--- a/devtools/create_project/create_project.h
+++ b/devtools/create_project/create_project.h
@@ -29,7 +29,9 @@
 
 #include <list>
 #include <map>
+#include <unordered_map>
 #include <string>
+#include <vector>
 
 #include <cassert>
 
@@ -238,6 +240,7 @@ struct BuildSetup {
 	bool createInstaller;      ///< Create installer after the build
 	bool useSDL2;              ///< Whether to use SDL2 or not.
 	bool useCanonicalLibNames; ///< Whether to use canonical libraries names or default ones
+	bool useStaticDetection;   ///< Whether to link detection features inside the executable or not.
 
 	BuildSetup() {
 		devTools = false;
@@ -246,6 +249,7 @@ struct BuildSetup {
 		createInstaller = false;
 		useSDL2 = true;
 		useCanonicalLibNames = false;
+		useStaticDetection = true;
 	}
 };
 
@@ -565,7 +569,7 @@ protected:
 	 * @param includeList Reference to a list, where included files should be added.
 	 * @param excludeList Reference to a list, where excluded files should be added.
 	 */
-	void createModuleList(const std::string &moduleDir, const StringList &defines, StringList &testDirs, StringList &includeList, StringList &excludeList) const;
+	void createModuleList(const std::string &moduleDir, const StringList &defines, StringList &testDirs, StringList &includeList, StringList &excludeList, bool forDetection = false) const;
 
 	/**
 	 * Creates an UUID for every enabled engine of the


Commit: abedaaa5aafa70f6509ca0861b6b9ad467af5374
    https://github.com/scummvm/scummvm/commit/abedaaa5aafa70f6509ca0861b6b9ad467af5374
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: Don't allow dynamic detection to be exposed when using static-detection.

Changed paths:
    engines/detection.cpp


diff --git a/engines/detection.cpp b/engines/detection.cpp
index 905a63191a..c8ea7c9b5b 100644
--- a/engines/detection.cpp
+++ b/engines/detection.cpp
@@ -20,6 +20,7 @@
  *
  */
 
+#ifndef DETECTION_STATIC
 
 #include "base/plugins.h"
 #include "engines/metaengine.h"
@@ -52,3 +53,4 @@ public:
 
 REGISTER_PLUGIN_DYNAMIC(DETECTION_DYNAMIC, PLUGIN_TYPE_DETECTION, DetectionConnect);
 
+#endif // !DETECTION_STATIC


Commit: 0b2428e7c58ea153c9c9afe3002a3e848fc2690b
    https://github.com/scummvm/scummvm/commit/0b2428e7c58ea153c9c9afe3002a3e848fc2690b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
NEVERHOOD: Temporarily rename module -> module_scene.cpp

- The name was clashing with one of the audio files.
- New changes were spread to the detection files, so no idea how this file is involved.
- In the meanwhile, this commit should fix a build error, if any.

Changed paths:
  A engines/neverhood/module_scene.cpp
  R engines/neverhood/module.cpp
    engines/neverhood/module.mk


diff --git a/engines/neverhood/module.mk b/engines/neverhood/module.mk
index 2ffef0c3bb..364df833c8 100644
--- a/engines/neverhood/module.mk
+++ b/engines/neverhood/module.mk
@@ -13,7 +13,7 @@ MODULE_OBJS = \
 	menumodule.o \
 	metaengine.o \
 	microtiles.o \
-	module.o \
+	module_scene.o \
 	modules/module1000.o \
 	modules/module1000_sprites.o \
 	modules/module1100.o \
diff --git a/engines/neverhood/module.cpp b/engines/neverhood/module_scene.cpp
similarity index 100%
rename from engines/neverhood/module.cpp
rename to engines/neverhood/module_scene.cpp


Commit: f4d4283f79481730aab72dfec086d8bfab4ba85f
    https://github.com/scummvm/scummvm/commit/f4d4283f79481730aab72dfec086d8bfab4ba85f
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
QUEEN: Add missing newline at EOF in modules.mk

- This should fix the build errors.

Changed paths:
    engines/queen/module.mk


diff --git a/engines/queen/module.mk b/engines/queen/module.mk
index efb4bb4a80..5eb011c777 100644
--- a/engines/queen/module.mk
+++ b/engines/queen/module.mk
@@ -41,4 +41,4 @@ ifneq ($(ENABLE_QUEEN), STATIC_PLUGIN)
 # External dependencies for detection.
 DETECT_OBJS += $(MODULE)/resource.o
 DETECT_OBJS += $(MODULE)/restables.o
-endif
\ No newline at end of file
+endif


Commit: 58a9de8092fcd35ed5f1e96963d8f01942dfc58c
    https://github.com/scummvm/scummvm/commit/58a9de8092fcd35ed5f1e96963d8f01942dfc58c
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
DEVTOOLS: CREATE_PROJECT: Use map instead of unordered_map

- No C11 support yet, revert to use map to fix build

Changed paths:
    devtools/create_project/create_project.cpp
    devtools/create_project/create_project.h


diff --git a/devtools/create_project/create_project.cpp b/devtools/create_project/create_project.cpp
index 5468435f52..e0e26675ce 100644
--- a/devtools/create_project/create_project.cpp
+++ b/devtools/create_project/create_project.cpp
@@ -103,7 +103,7 @@ enum ProjectType {
 	kProjectXcode
 };
 
-std::unordered_map<std::string, bool> isEngineEnabled;
+std::map<std::string, bool> isEngineEnabled;
 
 int main(int argc, char *argv[]) {
 #ifndef USE_WIN32_API
diff --git a/devtools/create_project/create_project.h b/devtools/create_project/create_project.h
index 231ca8c8bc..1c4aaac7ec 100644
--- a/devtools/create_project/create_project.h
+++ b/devtools/create_project/create_project.h
@@ -29,7 +29,7 @@
 
 #include <list>
 #include <map>
-#include <unordered_map>
+#include <map>
 #include <string>
 #include <vector>
 


Commit: a9fd54cffdba0733b0a3b6b9d754a8e1b56de35f
    https://github.com/scummvm/scummvm/commit/a9fd54cffdba0733b0a3b6b9d754a8e1b56de35f
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GLK: Fix missing header files to create engines

Changed paths:
    engines/glk/metaengine.cpp


diff --git a/engines/glk/metaengine.cpp b/engines/glk/metaengine.cpp
index 6df7d0bcd6..b30b55a0a8 100644
--- a/engines/glk/metaengine.cpp
+++ b/engines/glk/metaengine.cpp
@@ -20,30 +20,33 @@
  *
  */
 
-#include "base/plugins.h"
-#include "common/md5.h"
-#include "common/memstream.h"
-#include "common/str-array.h"
-#include "common/file.h"
-#include "common/translation.h"
-#include "common/config-manager.h"
-
+#include "glk/glk.h"
 #include "glk/detection.h"
-#include "glk/game_description.h"
-
+#include "glk/quetzal.h"
 #include "glk/adrift/detection.h"
+#include "glk/adrift/adrift.h"
 #include "glk/advsys/detection.h"
+#include "glk/advsys/advsys.h"
 #include "glk/agt/detection.h"
+#include "glk/agt/agt.h"
 #include "glk/alan2/detection.h"
+#include "glk/alan2/alan2.h"
 #include "glk/alan3/detection.h"
+#include "glk/alan3/alan3.h"
+#include "glk/archetype/archetype.h"
 #include "glk/archetype/detection.h"
 #include "glk/zcode/detection.h"
 #include "glk/zcode/zcode.h"
 #include "glk/hugo/detection.h"
+#include "glk/hugo/hugo.h"
 #include "glk/jacl/detection.h"
+#include "glk/jacl/jacl.h"
 #include "glk/level9/detection.h"
+#include "glk/level9/level9.h"
 #include "glk/magnetic/detection.h"
+#include "glk/magnetic/magnetic.h"
 #include "glk/quest/detection.h"
+#include "glk/quest/quest.h"
 #include "glk/scott/detection.h"
 #include "glk/scott/scott.h"
 


Commit: 73af65eedbb9bf59a429a93d5cba1b1795669bc1
    https://github.com/scummvm/scummvm/commit/73af65eedbb9bf59a429a93d5cba1b1795669bc1
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GRIFFON: Add missing header for translations

Changed paths:
    engines/griffon/metaengine.cpp


diff --git a/engines/griffon/metaengine.cpp b/engines/griffon/metaengine.cpp
index 1d63afd814..53caf64a88 100644
--- a/engines/griffon/metaengine.cpp
+++ b/engines/griffon/metaengine.cpp
@@ -22,6 +22,7 @@
 
 #include "base/plugins.h"
 #include "common/config-manager.h"
+#include "common/translation.h"
 #include "engines/advancedDetector.h"
 
 #include "backends/keymapper/action.h"


Commit: 2f0596091353d176d95479e5d82cd9d7a10e6a08
    https://github.com/scummvm/scummvm/commit/2f0596091353d176d95479e5d82cd9d7a10e6a08
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BUILD: MAKEFILES: Rename USE_RULES -> LOAD_RULES_MK

Changed paths:
    Makefile
    Makefile.common
    rules.mk


diff --git a/Makefile b/Makefile
index fdb969a158..2ab2f4fdbd 100644
--- a/Makefile
+++ b/Makefile
@@ -17,7 +17,7 @@ MODULE_DIRS :=
 
 # All game detection-related object files for engines
 DETECT_OBJS :=
-USE_RULES   := 1
+LOAD_RULES_MK   := 1
 
 # Load the make rules generated by configure
 -include config.mk
diff --git a/Makefile.common b/Makefile.common
index 7bd2827c5a..43812b6617 100644
--- a/Makefile.common
+++ b/Makefile.common
@@ -57,8 +57,8 @@ MODULES_ORIG:= $(MODULES)
 MODULE_DIRS_ORIG := $(MODULE_DIRS)
 KYRARPG_COMMON_OBJ_ORIG := $(KYRARPG_COMMON_OBJ)
 
-# Skip rules for these files, by resetting the use_rules
-USE_RULES :=
+# Skip rules for these files, by resetting the LOAD_RULES_MK
+LOAD_RULES_MK :=
 
 # Reset detection objects, which uptill now are filled with only
 # enabled engines.
@@ -76,7 +76,7 @@ PLUGIN :=
 KYRARPG_COMMON_OBJ := $(KYRARPG_COMMON_OBJ_ORIG)
 
 # Enable-rules again
-USE_RULES := 1
+LOAD_RULES_MK := 1
 
 ifneq "$(DETECTION_STATIC)" "1"
 -include $(srcdir)/engines/detect_modules.mk
diff --git a/rules.mk b/rules.mk
index 6ebf055c2c..1bbc7ee35e 100644
--- a/rules.mk
+++ b/rules.mk
@@ -3,7 +3,7 @@
 #
 ###############################################
 
-ifeq "$(USE_RULES)" "1"
+ifeq "$(LOAD_RULES_MK)" "1"
 
 # Copy the list of objects to a new variable. The name of the new variable
 # contains the module name, a trick we use so we can keep multiple different
@@ -105,4 +105,4 @@ endif
 
 .PHONY: clean-$(MODULE) $(MODULE)
 
-endif # USE_RULES
+endif # LOAD_RULES_MK


Commit: 02730ee1766150ef736dbecd0b5a8b572c495393
    https://github.com/scummvm/scummvm/commit/02730ee1766150ef736dbecd0b5a8b572c495393
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BUILD: MAKEFILES: Improve syntax of if checks

Changed paths:
    Makefile.common
    rules.mk


diff --git a/Makefile.common b/Makefile.common
index 43812b6617..9e3a4145f5 100644
--- a/Makefile.common
+++ b/Makefile.common
@@ -78,7 +78,7 @@ KYRARPG_COMMON_OBJ := $(KYRARPG_COMMON_OBJ_ORIG)
 # Enable-rules again
 LOAD_RULES_MK := 1
 
-ifneq "$(DETECTION_STATIC)" "1"
+ifneq ($(DETECTION_STATIC), 1)
 -include $(srcdir)/engines/detect_modules.mk
 endif
 
diff --git a/rules.mk b/rules.mk
index 1bbc7ee35e..a3bbec5977 100644
--- a/rules.mk
+++ b/rules.mk
@@ -3,7 +3,7 @@
 #
 ###############################################
 
-ifeq "$(LOAD_RULES_MK)" "1"
+ifeq ($(LOAD_RULES_MK), 1)
 
 # Copy the list of objects to a new variable. The name of the new variable
 # contains the module name, a trick we use so we can keep multiple different


Commit: c48719404a55b9b77a7b347f3d28e3fac93e12c6
    https://github.com/scummvm/scummvm/commit/c48719404a55b9b77a7b347f3d28e3fac93e12c6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Rename plugin matching helpers

- give*From* -> get*From*

Changed paths:
    base/commandLine.cpp
    base/main.cpp
    base/plugins.cpp
    base/plugins.h
    engines/advancedDetector.cpp
    engines/engine.cpp
    engines/sci/detection.cpp
    engines/wintermute/detection.cpp
    gui/editgamedialog.cpp
    gui/launcher.cpp
    gui/saveload.cpp


diff --git a/base/commandLine.cpp b/base/commandLine.cpp
index d2b8ad3314..306a2fe96b 100644
--- a/base/commandLine.cpp
+++ b/base/commandLine.cpp
@@ -895,7 +895,7 @@ static Common::Error listSaves(const Common::String &singleTarget) {
 			printf("MetaEnginePlugin could not be loaded for target '%s'\n", i->c_str());
 			continue;
 		} else {
-			enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+			enginePlugin = PluginMan.getEngineFromMetaEngine(metaEnginePlugin);
 
 			if (!enginePlugin) {
 				// If the target was specified, treat this as an error, and otherwise skip it.
diff --git a/base/main.cpp b/base/main.cpp
index 3b91095438..9651715f68 100644
--- a/base/main.cpp
+++ b/base/main.cpp
@@ -192,7 +192,7 @@ static Common::Error runGame(const Plugin *plugin, OSystem &system, const Common
 
 	// Right now we have a MetaEngine plugin. We must find the matching engine plugin to
 	// call createInstance and other connecting functions.
-	Plugin *enginePluginToLaunchGame = PluginMan.giveEngineFromMetaEngine(plugin);
+	Plugin *enginePluginToLaunchGame = PluginMan.getEngineFromMetaEngine(plugin);
 
 	if (!enginePluginToLaunchGame) {
 		err = Common::kEnginePluginNotFound;
@@ -550,7 +550,7 @@ extern "C" int scummvm_main(int argc, const char * const argv[]) {
 
 			// Right now, we have a MetaEngine plugin, and we want to unload all except Engine.
 			// First, get the relevant Engine plugin from MetaEngine.
-			const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(plugin);
+			const Plugin *enginePlugin = PluginMan.getEngineFromMetaEngine(plugin);
 
 			// Then, pass in the pointer to enginePlugin, with the matching type, so our function behaves as-is.
 			PluginManager::instance().unloadPluginsExcept(PLUGIN_TYPE_ENGINE, enginePlugin);
diff --git a/base/plugins.cpp b/base/plugins.cpp
index 79ba2b58cc..14f6d2d1cc 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -271,7 +271,7 @@ void PluginManager::addPluginProvider(PluginProvider *pp) {
 	_providers.push_back(pp);
 }
 
-Plugin *PluginManager::giveEngineFromMetaEngine(const Plugin *plugin) {
+Plugin *PluginManager::getEngineFromMetaEngine(const Plugin *plugin) {
 	assert(plugin->getType() == PLUGIN_TYPE_METAENGINE);
 
 	Plugin *enginePlugin = nullptr;
@@ -305,7 +305,7 @@ Plugin *PluginManager::giveEngineFromMetaEngine(const Plugin *plugin) {
 	return nullptr;
 }
 
-Plugin *PluginManager::giveMetaEngineFromEngine(const Plugin *plugin) {
+Plugin *PluginManager::getMetaEngineFromEngine(const Plugin *plugin) {
 	assert(plugin->getType() == PLUGIN_TYPE_ENGINE);
 
 	Plugin *metaEngine = nullptr;
diff --git a/base/plugins.h b/base/plugins.h
index f7d7308762..9ae3011b52 100644
--- a/base/plugins.h
+++ b/base/plugins.h
@@ -347,7 +347,7 @@ public:
 	 *
 	 * @return A plugin of type METAENGINE.
 	 */
-	Plugin *giveMetaEngineFromEngine(const Plugin *plugin);
+	Plugin *getMetaEngineFromEngine(const Plugin *plugin);
 
 	/**
 	 * A method which takes in a plugin of type METAENGINE,
@@ -359,7 +359,7 @@ public:
 	 *
 	 * @return A plugin of type ENGINE.
 	 */
-	Plugin *giveEngineFromMetaEngine(const Plugin *plugin);
+	Plugin *getEngineFromMetaEngine(const Plugin *plugin);
 
 	// Functions used by the uncached PluginManager
 	virtual void init()	{}
diff --git a/engines/advancedDetector.cpp b/engines/advancedDetector.cpp
index 8ffdc55dc8..943fd351b5 100644
--- a/engines/advancedDetector.cpp
+++ b/engines/advancedDetector.cpp
@@ -681,7 +681,7 @@ void AdvancedMetaEngine::initSubSystems(const ADGameDescription *gameDesc) const
 Common::Error AdvancedMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
 	PluginList pl = PluginMan.getPlugins(PLUGIN_TYPE_ENGINE);
 	if (pl.size() == 1) {
-		Plugin *metaEnginePlugin = PluginMan.giveMetaEngineFromEngine(pl[0]);
+		Plugin *metaEnginePlugin = PluginMan.getMetaEngineFromEngine(pl[0]);
 		if (metaEnginePlugin) {
 			return metaEnginePlugin->get<AdvancedMetaEngine>().createInstance(syst, engine);
 		}
diff --git a/engines/engine.cpp b/engines/engine.cpp
index dd14db771e..1a646355fb 100644
--- a/engines/engine.cpp
+++ b/engines/engine.cpp
@@ -875,7 +875,7 @@ MetaEngineConnect &Engine::getMetaEngineConnect() {
 	const Plugin *metaEnginePlugin = EngineMan.findPlugin(ConfMan.get("engineid"));
 	assert(metaEnginePlugin);
 
-	const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+	const Plugin *enginePlugin = PluginMan.getEngineFromMetaEngine(metaEnginePlugin);
 	assert(enginePlugin);
 
 	return enginePlugin->get<MetaEngineConnect>();
diff --git a/engines/sci/detection.cpp b/engines/sci/detection.cpp
index 24aedd3b79..fab0ccd906 100644
--- a/engines/sci/detection.cpp
+++ b/engines/sci/detection.cpp
@@ -453,7 +453,7 @@ ADDetectedGame SciMetaEngine::fallbackDetect(const FileMap &allFiles, const Comm
 	const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
 
 	if (metaEnginePlugin) {
-		const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+		const Plugin *enginePlugin = PluginMan.getEngineFromMetaEngine(metaEnginePlugin);
 		if (enginePlugin) {
 			return enginePlugin->get<AdvancedMetaEngineConnect>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
 		} else {
diff --git a/engines/wintermute/detection.cpp b/engines/wintermute/detection.cpp
index 6fb976924c..525342dfa6 100644
--- a/engines/wintermute/detection.cpp
+++ b/engines/wintermute/detection.cpp
@@ -97,7 +97,7 @@ public:
 		const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
 
 		if (metaEnginePlugin) {
-			const Plugin *enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+			const Plugin *enginePlugin = PluginMan.getEngineFromMetaEngine(metaEnginePlugin);
 			if (enginePlugin) {
 				return enginePlugin->get<AdvancedMetaEngineConnect>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
 			} else {
diff --git a/gui/editgamedialog.cpp b/gui/editgamedialog.cpp
index 65fe06dfdb..8ff7a8d321 100644
--- a/gui/editgamedialog.cpp
+++ b/gui/editgamedialog.cpp
@@ -115,7 +115,7 @@ EditGameDialog::EditGameDialog(const String &domain)
 	if (!metaEnginePlugin) {
 		warning("MetaEnginePlugin for target \"%s\" not found!", domain.c_str());
 	} else {
-		enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+		enginePlugin = PluginMan.getEngineFromMetaEngine(metaEnginePlugin);
 		if (!enginePlugin) {
 			warning("Engine Plugin for target \"%s\" not found! Game specific settings might be missing.", domain.c_str());
 		}
diff --git a/gui/launcher.cpp b/gui/launcher.cpp
index 87f5866bb1..062f7a681b 100644
--- a/gui/launcher.cpp
+++ b/gui/launcher.cpp
@@ -475,7 +475,7 @@ void LauncherDialog::loadGame(int item) {
 
 	// If we found a relevant plugin, find the matching engine plugin.
 	if (metaEnginePlugin) {
-		enginePlugin = PluginMan.giveEngineFromMetaEngine(metaEnginePlugin);
+		enginePlugin = PluginMan.getEngineFromMetaEngine(metaEnginePlugin);
 	}
 
 	if (enginePlugin) {
diff --git a/gui/saveload.cpp b/gui/saveload.cpp
index 80680bf934..db026eb68d 100644
--- a/gui/saveload.cpp
+++ b/gui/saveload.cpp
@@ -81,7 +81,7 @@ int SaveLoadChooser::runModalWithCurrentTarget() {
 	if (!plugin) {
 		error("SaveLoadChooser::runModalWithCurrentTarget(): Cannot find plugin");
 	} else {
-		enginePlugin = PluginMan.giveEngineFromMetaEngine(plugin);
+		enginePlugin = PluginMan.getEngineFromMetaEngine(plugin);
 
 		if (!enginePlugin) {
 			error("SaveLoadChooser::runModalWithCurrentTarget(): Couldn't match a Engine from the MetaEngine. \


Commit: 71a820caffe2f810d26cca63c4ec1b6d9f0a0ac6
    https://github.com/scummvm/scummvm/commit/71a820caffe2f810d26cca63c4ec1b6d9f0a0ac6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: Begin class renaming of ME & AME

- ME -> MetaEngineStatic (static parts)
- MEC -> MetaEngine (dynamic parts)

Changed paths:
    base/commandLine.cpp
    base/main.cpp
    base/plugins.cpp
    engines/advancedDetector.cpp
    engines/advancedDetector.h
    engines/dialogs.cpp
    engines/engine.cpp
    engines/engine.h
    engines/metaengine.cpp
    engines/metaengine.h
    gui/about.cpp
    gui/editgamedialog.cpp
    gui/launcher.cpp
    gui/saveload-dialog.cpp
    gui/saveload-dialog.h
    gui/saveload.cpp
    gui/saveload.h


diff --git a/base/commandLine.cpp b/base/commandLine.cpp
index 306a2fe96b..dac2580708 100644
--- a/base/commandLine.cpp
+++ b/base/commandLine.cpp
@@ -784,7 +784,7 @@ static void listGames() {
 
 	const PluginList &plugins = EngineMan.getPlugins();
 	for (PluginList::const_iterator iter = plugins.begin(); iter != plugins.end(); ++iter) {
-		const MetaEngine &metaengine = (*iter)->get<MetaEngine>();
+		const MetaEngineStatic &metaengine = (*iter)->get<MetaEngineStatic>();
 
 		PlainGameList list = metaengine.getSupportedGames();
 		for (PlainGameList::const_iterator v = list.begin(); v != list.end(); ++v) {
@@ -800,7 +800,7 @@ static void listEngines() {
 
 	const PluginList &plugins = EngineMan.getPlugins();
 	for (PluginList::const_iterator iter = plugins.begin(); iter != plugins.end(); ++iter) {
-		const MetaEngine &metaEngine = (*iter)->get<MetaEngine>();
+		const MetaEngineStatic &metaEngine = (*iter)->get<MetaEngineStatic>();
 		printf("%-15s %s\n", metaEngine.getEngineId(), metaEngine.getName());
 	}
 }
@@ -907,10 +907,10 @@ static Common::Error listSaves(const Common::String &singleTarget) {
 			}
 		}
 
-		const MetaEngineConnect &metaEngine = enginePlugin->get<MetaEngineConnect>();
+		const MetaEngine &metaEngine = enginePlugin->get<MetaEngine>();
 		Common::String qualifiedGameId = buildQualifiedGameName(game.engineId, game.gameId);
 
-		if (!metaEngine.hasFeature(MetaEngineConnect::kSupportsListSaves)) {
+		if (!metaEngine.hasFeature(MetaEngine::kSupportsListSaves)) {
 			// If the target was specified, treat this as an error, and otherwise skip it.
 			if (!singleTarget.empty())
 				// TODO: Include more info about the target (desc, engine name, ...) ???
diff --git a/base/main.cpp b/base/main.cpp
index 9651715f68..0528746277 100644
--- a/base/main.cpp
+++ b/base/main.cpp
@@ -133,7 +133,7 @@ static const Plugin *detectPlugin() {
 
 	// Query the plugin for the game descriptor
 	printf("   Looking for a plugin supporting this target... %s\n", plugin->getName());
-	PlainGameDescriptor game = plugin->get<MetaEngine>().findGame(gameId.c_str());
+	PlainGameDescriptor game = plugin->get<MetaEngineStatic>().findGame(gameId.c_str());
 	if (!game.gameId) {
 		warning("'%s' is an invalid game ID for the engine '%s'. Use the --list-games option to list supported game IDs", gameId.c_str(), engineId.c_str());
 		return 0;
@@ -182,7 +182,7 @@ static Common::Error runGame(const Plugin *plugin, OSystem &system, const Common
 	}
 
 	// Create the game's MetaEngine.
-	const MetaEngine &metaEngine = plugin->get<MetaEngine>();
+	const MetaEngineStatic &metaEngine = plugin->get<MetaEngineStatic>();
 	if (err.getCode() == Common::kNoError) {
 		// Set default values for all of the custom engine options
 		// Apparently some engines query them in their constructor, thus we
@@ -200,7 +200,7 @@ static Common::Error runGame(const Plugin *plugin, OSystem &system, const Common
 	}
 
 	// Create the game's MetaEngineConnect.
-	const MetaEngineConnect &metaEngineConnect = enginePluginToLaunchGame->get<MetaEngineConnect>();
+	const MetaEngine &metaEngineConnect = enginePluginToLaunchGame->get<MetaEngine>();
 	err = metaEngineConnect.createInstance(&system, &engine);
 
 	// Check for errors
diff --git a/base/plugins.cpp b/base/plugins.cpp
index 14f6d2d1cc..18161c14bc 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -634,7 +634,7 @@ QualifiedGameList EngineManager::findGamesMatching(const Common::String &engineI
 		// If we got an engine name, look for THE game only in that engine
 		const Plugin *p = EngineMan.findPlugin(engineId);
 		if (p) {
-			const MetaEngine &engine = p->get<MetaEngine>();
+			const MetaEngineStatic &engine = p->get<MetaEngineStatic>();
 
 			PlainGameDescriptor pluginResult = engine.findGame(gameId.c_str());
 			if (pluginResult.gameId) {
@@ -663,7 +663,7 @@ QualifiedGameList EngineManager::findGameInLoadedPlugins(const Common::String &g
 	PluginList::const_iterator iter;
 
 	for (iter = plugins.begin(); iter != plugins.end(); ++iter) {
-		const MetaEngine &engine = (*iter)->get<MetaEngine>();
+		const MetaEngineStatic &engine = (*iter)->get<MetaEngineStatic>();
 		PlainGameDescriptor pluginResult = engine.findGame(gameId.c_str());
 
 		if (pluginResult.gameId) {
@@ -686,7 +686,7 @@ DetectionResults EngineManager::detectGames(const Common::FSList &fslist) const
 	// Iterate over all known games and for each check if it might be
 	// the game in the presented directory.
 	for (iter = plugins.begin(); iter != plugins.end(); ++iter) {
-		const MetaEngine &metaEngine = (*iter)->get<MetaEngine>();
+		const MetaEngineStatic &metaEngine = (*iter)->get<MetaEngineStatic>();
 		DetectedGames engineCandidates = metaEngine.detectGames(fslist);
 
 		for (uint i = 0; i < engineCandidates.size(); i++) {
@@ -764,7 +764,7 @@ const Plugin *EngineManager::findLoadedPlugin(const Common::String &engineId) co
 	const PluginList &plugins = getPlugins();
 
 	for (PluginList::const_iterator iter = plugins.begin(); iter != plugins.end(); iter++)
-		if (engineId == (*iter)->get<MetaEngine>().getEngineId())
+		if (engineId == (*iter)->get<MetaEngineStatic>().getEngineId())
 			return *iter;
 
 	return 0;
@@ -816,7 +816,7 @@ QualifiedGameDescriptor EngineManager::findTarget(const Common::String &target,
 	}
 
 	// Make sure it does support the game ID
-	const MetaEngine &engine = foundPlugin->get<MetaEngine>();
+	const MetaEngineStatic &engine = foundPlugin->get<MetaEngineStatic>();
 	PlainGameDescriptor desc = engine.findGame(domain->getVal("gameid").c_str());
 	if (!desc.gameId) {
 		return QualifiedGameDescriptor();
@@ -873,7 +873,7 @@ void EngineManager::upgradeTargetForEngineId(const Common::String &target) const
 		}
 
 		// Take the first detection entry
-		const MetaEngine &metaEngine = plugin->get<MetaEngine>();
+		const MetaEngineStatic &metaEngine = plugin->get<MetaEngineStatic>();
 		DetectedGames candidates = metaEngine.detectGames(files);
 		if (candidates.empty()) {
 			warning("No games supported by the engine '%s' were found in path '%s' when upgrading target '%s'",
diff --git a/engines/advancedDetector.cpp b/engines/advancedDetector.cpp
index 943fd351b5..1d579ab7c7 100644
--- a/engines/advancedDetector.cpp
+++ b/engines/advancedDetector.cpp
@@ -40,7 +40,7 @@
  */
 class FileMapArchive : public Common::Archive {
 public:
-	FileMapArchive(const AdvancedMetaEngine::FileMap &fileMap) : _fileMap(fileMap) {}
+	FileMapArchive(const AdvancedMetaEngineStatic::FileMap &fileMap) : _fileMap(fileMap) {}
 
 	bool hasFile(const Common::String &name) const override {
 		return _fileMap.contains(name);
@@ -48,7 +48,7 @@ public:
 
 	int listMembers(Common::ArchiveMemberList &list) const override {
 		int files = 0;
-		for (AdvancedMetaEngine::FileMap::const_iterator it = _fileMap.begin(); it != _fileMap.end(); ++it) {
+		for (AdvancedMetaEngineStatic::FileMap::const_iterator it = _fileMap.begin(); it != _fileMap.end(); ++it) {
 			list.push_back(Common::ArchiveMemberPtr(new Common::FSNode(it->_value)));
 			++files;
 		}
@@ -57,7 +57,7 @@ public:
 	}
 
 	const Common::ArchiveMemberPtr getMember(const Common::String &name) const override {
-		AdvancedMetaEngine::FileMap::const_iterator it = _fileMap.find(name);
+		AdvancedMetaEngineStatic::FileMap::const_iterator it = _fileMap.find(name);
 		if (it == _fileMap.end()) {
 			return Common::ArchiveMemberPtr();
 		}
@@ -71,7 +71,7 @@ public:
 	}
 
 private:
-	const AdvancedMetaEngine::FileMap &_fileMap;
+	const AdvancedMetaEngineStatic::FileMap &_fileMap;
 };
 
 static Common::String sanitizeName(const char *name) {
@@ -120,7 +120,7 @@ static Common::String generatePreferredTarget(const ADGameDescription *desc) {
 	return res;
 }
 
-DetectedGame AdvancedMetaEngine::toDetectedGame(const ADDetectedGame &adGame) const {
+DetectedGame AdvancedMetaEngineStatic::toDetectedGame(const ADDetectedGame &adGame) const {
 	const ADGameDescription *desc = adGame.desc;
 
 	const char *title;
@@ -186,7 +186,7 @@ bool cleanupPirated(ADDetectedGames &matched) {
 }
 
 
-DetectedGames AdvancedMetaEngine::detectGames(const Common::FSList &fslist) const {
+DetectedGames AdvancedMetaEngineStatic::detectGames(const Common::FSList &fslist) const {
 	FileMap allFiles;
 
 	if (fslist.empty())
@@ -232,7 +232,7 @@ DetectedGames AdvancedMetaEngine::detectGames(const Common::FSList &fslist) cons
 	return detectedGames;
 }
 
-const ExtraGuiOptions AdvancedMetaEngine::getExtraGuiOptions(const Common::String &target) const {
+const ExtraGuiOptions AdvancedMetaEngineStatic::getExtraGuiOptions(const Common::String &target) const {
 	if (!_extraGuiOptions)
 		return ExtraGuiOptions();
 
@@ -260,7 +260,7 @@ const ExtraGuiOptions AdvancedMetaEngine::getExtraGuiOptions(const Common::Strin
 	return options;
 }
 
-Common::Error AdvancedMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
+Common::Error AdvancedMetaEngineStatic::createInstance(OSystem *syst, Engine **engine) const {
 	assert(engine);
 
 	Common::Language language = Common::UNK_LANG;
@@ -359,7 +359,7 @@ Common::Error AdvancedMetaEngine::createInstance(OSystem *syst, Engine **engine)
 
 	if (plugin) {
 		// Call child class's createInstanceMethod.
-		if (plugin->get<AdvancedMetaEngineConnect>().createInstance(syst, engine, agdDesc.desc)) {
+		if (plugin->get<AdvancedMetaEngine>().createInstance(syst, engine, agdDesc.desc)) {
 			return Common::Error(Common::kNoError);
 		}
 	}
@@ -367,7 +367,7 @@ Common::Error AdvancedMetaEngine::createInstance(OSystem *syst, Engine **engine)
 	return Common::Error(Common::kNoGameDataFoundError);
 }
 
-void AdvancedMetaEngine::composeFileHashMap(FileMap &allFiles, const Common::FSList &fslist, int depth, const Common::String &parentName) const {
+void AdvancedMetaEngineStatic::composeFileHashMap(FileMap &allFiles, const Common::FSList &fslist, int depth, const Common::String &parentName) const {
 	if (depth <= 0)
 		return;
 
@@ -407,7 +407,7 @@ void AdvancedMetaEngine::composeFileHashMap(FileMap &allFiles, const Common::FSL
 	}
 }
 
-bool AdvancedMetaEngine::getFileProperties(const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const {
+bool AdvancedMetaEngineStatic::getFileProperties(const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const {
 	// FIXME/TODO: We don't handle the case that a file is listed as a regular
 	// file and as one with resource fork.
 
@@ -439,7 +439,7 @@ bool AdvancedMetaEngine::getFileProperties(const FileMap &allFiles, const ADGame
 	return true;
 }
 
-bool AdvancedMetaEngineConnect::getFilePropertiesExtern(uint md5Bytes, const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const {
+bool AdvancedMetaEngine::getFilePropertiesExtern(uint md5Bytes, const FileMap &allFiles, const ADGameDescription &game, const Common::String fname, FileProperties &fileProps) const {
 	// FIXME/TODO: We don't handle the case that a file is listed as a regular
 	// file and as one with resource fork.
 
@@ -471,7 +471,7 @@ bool AdvancedMetaEngineConnect::getFilePropertiesExtern(uint md5Bytes, const Fil
 	return true;
 }
 
-ADDetectedGames AdvancedMetaEngine::detectGame(const Common::FSNode &parent, const FileMap &allFiles, Common::Language language, Common::Platform platform, const Common::String &extra) const {
+ADDetectedGames AdvancedMetaEngineStatic::detectGame(const Common::FSNode &parent, const FileMap &allFiles, Common::Language language, Common::Platform platform, const Common::String &extra) const {
 	FilePropertiesMap filesProps;
 	ADDetectedGames matched;
 
@@ -596,7 +596,7 @@ ADDetectedGames AdvancedMetaEngine::detectGame(const Common::FSNode &parent, con
 	return matched;
 }
 
-ADDetectedGame AdvancedMetaEngine::detectGameFilebased(const FileMap &allFiles, const ADFileBasedFallback *fileBasedFallback) const {
+ADDetectedGame AdvancedMetaEngineStatic::detectGameFilebased(const FileMap &allFiles, const ADFileBasedFallback *fileBasedFallback) const {
 	const ADFileBasedFallback *ptr;
 	const char* const* filenames;
 
@@ -644,11 +644,11 @@ ADDetectedGame AdvancedMetaEngine::detectGameFilebased(const FileMap &allFiles,
 	return result;
 }
 
-PlainGameList AdvancedMetaEngine::getSupportedGames() const {
+PlainGameList AdvancedMetaEngineStatic::getSupportedGames() const {
 	return PlainGameList(_gameIds);
 }
 
-PlainGameDescriptor AdvancedMetaEngine::findGame(const char *gameId) const {
+PlainGameDescriptor AdvancedMetaEngineStatic::findGame(const char *gameId) const {
 	// First search the list of supported gameids for a match.
 	const PlainGameDescriptor *g = findPlainGameDescriptor(gameId, _gameIds);
 	if (g)
@@ -658,7 +658,7 @@ PlainGameDescriptor AdvancedMetaEngine::findGame(const char *gameId) const {
 	return PlainGameDescriptor::empty();
 }
 
-AdvancedMetaEngine::AdvancedMetaEngine(const void *descs, uint descItemSize, const PlainGameDescriptor *gameIds, const ADExtraGuiOptionsMap *extraGuiOptions)
+AdvancedMetaEngineStatic::AdvancedMetaEngineStatic(const void *descs, uint descItemSize, const PlainGameDescriptor *gameIds, const ADExtraGuiOptionsMap *extraGuiOptions)
 	: _gameDescriptors((const byte *)descs), _descItemSize(descItemSize), _gameIds(gameIds),
 	  _extraGuiOptions(extraGuiOptions) {
 
@@ -670,7 +670,7 @@ AdvancedMetaEngine::AdvancedMetaEngine(const void *descs, uint descItemSize, con
 	_matchFullPaths = false;
 }
 
-void AdvancedMetaEngine::initSubSystems(const ADGameDescription *gameDesc) const {
+void AdvancedMetaEngineStatic::initSubSystems(const ADGameDescription *gameDesc) const {
 #ifdef ENABLE_EVENTRECORDER
 	if (gameDesc) {
 		g_eventRec.processGameDescription(gameDesc);
@@ -678,12 +678,12 @@ void AdvancedMetaEngine::initSubSystems(const ADGameDescription *gameDesc) const
 #endif
 }
 
-Common::Error AdvancedMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+Common::Error AdvancedMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
 	PluginList pl = PluginMan.getPlugins(PLUGIN_TYPE_ENGINE);
 	if (pl.size() == 1) {
 		Plugin *metaEnginePlugin = PluginMan.getMetaEngineFromEngine(pl[0]);
 		if (metaEnginePlugin) {
-			return metaEnginePlugin->get<AdvancedMetaEngine>().createInstance(syst, engine);
+			return metaEnginePlugin->get<AdvancedMetaEngineStatic>().createInstance(syst, engine);
 		}
 	}
 
diff --git a/engines/advancedDetector.h b/engines/advancedDetector.h
index 8cda4b27d2..33ae44c87c 100644
--- a/engines/advancedDetector.h
+++ b/engines/advancedDetector.h
@@ -168,7 +168,7 @@ struct ADExtraGuiOptionsMap {
 /**
  * A MetaEngine implementation based around the advanced detector code.
  */
-class AdvancedMetaEngine : public MetaEngine {
+class AdvancedMetaEngineStatic : public MetaEngineStatic {
 protected:
 	/**
 	 * Pointer to an array of objects which are either ADGameDescription
@@ -246,7 +246,7 @@ protected:
 	bool _matchFullPaths;
 
 public:
-	AdvancedMetaEngine(const void *descs, uint descItemSize, const PlainGameDescriptor *gameIds, const ADExtraGuiOptionsMap *extraGuiOptions = 0);
+	AdvancedMetaEngineStatic(const void *descs, uint descItemSize, const PlainGameDescriptor *gameIds, const ADExtraGuiOptionsMap *extraGuiOptions = 0);
 
 	/**
 	 * Returns list of targets supported by the engine.
@@ -327,7 +327,7 @@ protected:
 /**
  * A MetaEngineConnect implementation of AdvancedMetaEngine.
  */
-class AdvancedMetaEngineConnect : public MetaEngineConnect {
+class AdvancedMetaEngine : public MetaEngine {
 public:
 	/**
 	 * Base createInstance for AMEC.
diff --git a/engines/dialogs.cpp b/engines/dialogs.cpp
index b47be56ca6..c17ede7993 100644
--- a/engines/dialogs.cpp
+++ b/engines/dialogs.cpp
@@ -273,7 +273,7 @@ ConfigDialog::ConfigDialog() :
 	assert(g_engine);
 
 	const Common::String &gameDomain = ConfMan.getActiveDomainName();
-	const MetaEngineConnect &metaEngineConnect = g_engine->getMetaEngineConnect();
+	const MetaEngine &metaEngineConnect = g_engine->getMetaEngineConnect();
 
 	// GUI:  Add tab widget
 	GUI::TabWidget *tab = new GUI::TabWidget(this, "GlobalConfig.TabWidget");
diff --git a/engines/engine.cpp b/engines/engine.cpp
index 1a646355fb..e0e045b1bb 100644
--- a/engines/engine.cpp
+++ b/engines/engine.cpp
@@ -731,7 +731,7 @@ Common::Error Engine::loadGameState(int slot) {
 	Common::Error result = loadGameStream(saveFile);
 	if (result.getCode() == Common::kNoError) {
 		ExtendedSavegameHeader header;
-		if (MetaEngineConnect::readSavegameHeader(saveFile, &header))
+		if (MetaEngine::readSavegameHeader(saveFile, &header))
 			setTotalPlayTime(header.playtime);
 	}
 
@@ -757,7 +757,7 @@ Common::Error Engine::saveGameState(int slot, const Common::String &desc, bool i
 
 	Common::Error result = saveGameStream(saveFile, isAutosave);
 	if (result.getCode() == Common::kNoError) {
-		MetaEngineConnect::appendExtendedSave(saveFile, getTotalPlayTime() / 1000, desc, isAutosave);
+		MetaEngine::appendExtendedSave(saveFile, getTotalPlayTime() / 1000, desc, isAutosave);
 
 		saveFile->finalize();
 	}
@@ -865,20 +865,20 @@ EnginePlugin *Engine::getMetaEnginePlugin() const {
 
 */
 
-MetaEngine &Engine::getMetaEngine() {
+MetaEngineStatic &Engine::getMetaEngine() {
 	const Plugin *plugin = EngineMan.findPlugin(ConfMan.get("engineid"));
 	assert(plugin);
-	return plugin->get<MetaEngine>();
+	return plugin->get<MetaEngineStatic>();
 }
 
-MetaEngineConnect &Engine::getMetaEngineConnect() {
+MetaEngine &Engine::getMetaEngineConnect() {
 	const Plugin *metaEnginePlugin = EngineMan.findPlugin(ConfMan.get("engineid"));
 	assert(metaEnginePlugin);
 
 	const Plugin *enginePlugin = PluginMan.getEngineFromMetaEngine(metaEnginePlugin);
 	assert(enginePlugin);
 
-	return enginePlugin->get<MetaEngineConnect>();
+	return enginePlugin->get<MetaEngine>();
 }
 
 PauseToken::PauseToken() : _engine(nullptr) {}
diff --git a/engines/engine.h b/engines/engine.h
index 7a7402e055..24d0283870 100644
--- a/engines/engine.h
+++ b/engines/engine.h
@@ -31,8 +31,8 @@
 #include "common/singleton.h"
 
 class OSystem;
+class MetaEngineStatic;
 class MetaEngine;
-class MetaEngineConnect;
 
 namespace Audio {
 class Mixer;
@@ -379,8 +379,8 @@ public:
 	 */
 	static bool shouldQuit();
 
-	static MetaEngine &getMetaEngine();
-	static MetaEngineConnect &getMetaEngineConnect();
+	static MetaEngineStatic &getMetaEngine();
+	static MetaEngine &getMetaEngineConnect();
 
 	/**
 	 * Pause the engine. This should stop any audio playback
diff --git a/engines/metaengine.cpp b/engines/metaengine.cpp
index a77a787110..2b1222ae58 100644
--- a/engines/metaengine.cpp
+++ b/engines/metaengine.cpp
@@ -37,7 +37,7 @@
 #include "graphics/managed_surface.h"
 #include "graphics/thumbnail.h"
 
-Common::String MetaEngineConnect::getSavegameFile(int saveGameIdx, const char *target) const {
+Common::String MetaEngine::getSavegameFile(int saveGameIdx, const char *target) const {
 	if (saveGameIdx == kSavegameFilePattern) {
 		// Pattern requested
 		const char *pattern = hasFeature(kSavesUseExtendedFormat) ? "%s.###" : "%s.s##";
@@ -49,7 +49,7 @@ Common::String MetaEngineConnect::getSavegameFile(int saveGameIdx, const char *t
 	}
 }
 
-Common::KeymapArray MetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray MetaEngine::initKeymaps(const char *target) const {
 	using namespace Common;
 
 	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "engine-default", _("Default game keymap"));
@@ -128,7 +128,7 @@ Common::KeymapArray MetaEngineConnect::initKeymaps(const char *target) const {
 	return Keymap::arrayOf(engineKeyMap);
 }
 
-bool MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool MetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave) ||
@@ -140,7 +140,7 @@ bool MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSavesUseExtendedFormat);
 }
 
-void MetaEngineConnect::appendExtendedSave(Common::OutSaveFile *saveFile, uint32 playtime,
+void MetaEngine::appendExtendedSave(Common::OutSaveFile *saveFile, uint32 playtime,
 		Common::String desc, bool isAutosave) {
 	ExtendedSavegameHeader header;
 
@@ -172,7 +172,7 @@ void MetaEngineConnect::appendExtendedSave(Common::OutSaveFile *saveFile, uint32
 	saveFile->finalize();
 }
 
-void MetaEngineConnect::saveScreenThumbnail(Common::OutSaveFile *saveFile) {
+void MetaEngine::saveScreenThumbnail(Common::OutSaveFile *saveFile) {
 	// Create a thumbnail surface from the screen
 	Graphics::Surface thumb;
 	::createThumbnailFromScreen(&thumb);
@@ -182,7 +182,7 @@ void MetaEngineConnect::saveScreenThumbnail(Common::OutSaveFile *saveFile) {
 	thumb.free();
 }
 
-void MetaEngineConnect::parseSavegameHeader(ExtendedSavegameHeader *header, SaveStateDescriptor *desc) {
+void MetaEngine::parseSavegameHeader(ExtendedSavegameHeader *header, SaveStateDescriptor *desc) {
 	int day = (header->date >> 24) & 0xFF;
 	int month = (header->date >> 16) & 0xFF;
 	int year = header->date & 0xFFFF;
@@ -195,14 +195,14 @@ void MetaEngineConnect::parseSavegameHeader(ExtendedSavegameHeader *header, Save
 	desc->setDescription(header->description);
 }
 
-void MetaEngineConnect::fillDummyHeader(ExtendedSavegameHeader *header) {
+void MetaEngine::fillDummyHeader(ExtendedSavegameHeader *header) {
 	// This is wrong header, perhaps it is original savegame. Thus fill out dummy values
 	header->date = (20 << 24) | (9 << 16) | 2016;
 	header->time = (9 << 8) | 56;
 	header->playtime = 0;
 }
 
-WARN_UNUSED_RESULT bool MetaEngineConnect::readSavegameHeader(Common::InSaveFile *in, ExtendedSavegameHeader *header, bool skipThumbnail) {
+WARN_UNUSED_RESULT bool MetaEngine::readSavegameHeader(Common::InSaveFile *in, ExtendedSavegameHeader *header, bool skipThumbnail) {
 	uint oldPos = in->pos();
 
 	in->seek(-4, SEEK_END);
@@ -264,7 +264,7 @@ WARN_UNUSED_RESULT bool MetaEngineConnect::readSavegameHeader(Common::InSaveFile
 // MetaEngineConnect default implementations
 //////////////////////////////////////////////
 
-SaveStateList MetaEngineConnect::listSaves(const char *target) const {
+SaveStateList MetaEngine::listSaves(const char *target) const {
 	if (!hasFeature(kSavesUseExtendedFormat))
 		return SaveStateList();
 
@@ -305,7 +305,7 @@ SaveStateList MetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateList MetaEngineConnect::listSaves(const char *target, bool saveMode) const {
+SaveStateList MetaEngine::listSaves(const char *target, bool saveMode) const {
 	SaveStateList saveList = listSaves(target);
 	int autosaveSlot = ConfMan.getInt("autosave_period") ? getAutosaveSlot() : -1;
 	if (!saveMode || autosaveSlot == -1)
@@ -334,7 +334,7 @@ SaveStateList MetaEngineConnect::listSaves(const char *target, bool saveMode) co
 	return saveList;
 }
 
-void MetaEngine::registerDefaultSettings(const Common::String &) const {
+void MetaEngineStatic::registerDefaultSettings(const Common::String &) const {
 	// Note that as we don't pass the target to getExtraGuiOptions
 	//  we get all the options, even those not relevant for the current
 	//  game. This is necessary because some engines unconditionally
@@ -345,7 +345,7 @@ void MetaEngine::registerDefaultSettings(const Common::String &) const {
 	}
 }
 
-GUI::OptionsContainerWidget *MetaEngine::buildEngineOptionsWidgetStatic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
+GUI::OptionsContainerWidget *MetaEngineStatic::buildEngineOptionsWidgetStatic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
 	const ExtraGuiOptions engineOptions = getExtraGuiOptions(target);
 	if (engineOptions.empty()) {
 		return nullptr;
@@ -354,7 +354,7 @@ GUI::OptionsContainerWidget *MetaEngine::buildEngineOptionsWidgetStatic(GUI::Gui
 	return new GUI::ExtraGuiOptionsWidget(boss, name, target, engineOptions);
 }
 
-GUI::OptionsContainerWidget *MetaEngineConnect::buildEngineOptionsWidgetDynamic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
+GUI::OptionsContainerWidget *MetaEngine::buildEngineOptionsWidgetDynamic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
 	const ExtraGuiOptions engineOptions = getExtraGuiOptions(target);
 	if (engineOptions.empty()) {
 		return nullptr;
@@ -363,14 +363,14 @@ GUI::OptionsContainerWidget *MetaEngineConnect::buildEngineOptionsWidgetDynamic(
 	return new GUI::ExtraGuiOptionsWidget(boss, name, target, engineOptions);
 }
 
-void MetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void MetaEngine::removeSaveState(const char *target, int slot) const {
 	if (!hasFeature(kSavesUseExtendedFormat))
 		return;
 
 	g_system->getSavefileManager()->removeSavefile(getSavegameFile(slot, target));
 }
 
-SaveStateDescriptor MetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor MetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	if (!hasFeature(kSavesUseExtendedFormat))
 		return SaveStateDescriptor();
 
diff --git a/engines/metaengine.h b/engines/metaengine.h
index cb9ade66f2..db71cadf5a 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -102,9 +102,9 @@ struct ExtendedSavegameHeader {
  * and other useful functionality. To instantiate actual Engine objects,
  * See the class MetaEngineConnect below.
  */
-class MetaEngine : public PluginObject {
+class MetaEngineStatic : public PluginObject {
 public:
-	virtual ~MetaEngine() {}
+	virtual ~MetaEngineStatic() {}
 
 	/** Get the engine ID */
 	virtual const char *getEngineId() const = 0;
@@ -178,14 +178,14 @@ public:
  * Since engine plugins can be used a external runtime libraries, these can live and build inside
  * the engine, while a MetaEngine will always build into the executable to be able to detect code.
  */
-class MetaEngineConnect : public PluginObject {
+class MetaEngine : public PluginObject {
 private:
 	/**
 	 * Converts the current screen contents to a thumbnail, and saves it
 	 */
 	static void saveScreenThumbnail(Common::OutSaveFile *saveFile);
 public:
-	virtual ~MetaEngineConnect() {}
+	virtual ~MetaEngine() {}
 
 	/**
 	 * Name of the engine plugin.
diff --git a/gui/about.cpp b/gui/about.cpp
index 1e4dbcd44e..f63b972ee4 100644
--- a/gui/about.cpp
+++ b/gui/about.cpp
@@ -127,7 +127,7 @@ AboutDialog::AboutDialog()
 		addLine(str);
 
 		str = "C2";
-		str += (*iter)->get<MetaEngine>().getOriginalCopyright();
+		str += (*iter)->get<MetaEngineStatic>().getOriginalCopyright();
 		addLine(str);
 
 		//addLine("");
diff --git a/gui/editgamedialog.cpp b/gui/editgamedialog.cpp
index 8ff7a8d321..1cc80bf000 100644
--- a/gui/editgamedialog.cpp
+++ b/gui/editgamedialog.cpp
@@ -185,7 +185,7 @@ EditGameDialog::EditGameDialog(const String &domain)
 	if (metaEnginePlugin) {
 		int tabId = tab->addTab(_("Engine"), "GameOptions_Engine");
 
-		const MetaEngine &metaEngine = metaEnginePlugin->get<MetaEngine>();
+		const MetaEngineStatic &metaEngine = metaEnginePlugin->get<MetaEngineStatic>();
 		metaEngine.registerDefaultSettings(_domain);
 		_engineOptions = metaEngine.buildEngineOptionsWidgetStatic(tab, "GameOptions_Engine.Container", _domain);
 
@@ -232,7 +232,7 @@ EditGameDialog::EditGameDialog(const String &domain)
 	//
 	Common::KeymapArray keymaps;
 	if (enginePlugin) {
-		keymaps = enginePlugin->get<MetaEngineConnect>().initKeymaps(domain.c_str());
+		keymaps = enginePlugin->get<MetaEngine>().initKeymaps(domain.c_str());
 	}
 
 	if (!keymaps.empty()) {
@@ -340,7 +340,7 @@ EditGameDialog::EditGameDialog(const String &domain)
 	// 9) The Achievements tab
 	//
 	if (enginePlugin) {
-		const MetaEngineConnect &metaEngineConnect = enginePlugin->get<MetaEngineConnect>();
+		const MetaEngine &metaEngineConnect = enginePlugin->get<MetaEngine>();
 		Common::AchievementsInfo achievementsInfo = metaEngineConnect.getAchievementsInfo(domain);
 		if (achievementsInfo.descriptions.size() > 0) {
 			tab->addTab(_("Achievements"), "GameOptions_Achievements");
diff --git a/gui/launcher.cpp b/gui/launcher.cpp
index 062f7a681b..2681567ab0 100644
--- a/gui/launcher.cpp
+++ b/gui/launcher.cpp
@@ -479,9 +479,9 @@ void LauncherDialog::loadGame(int item) {
 	}
 
 	if (enginePlugin) {
-		const MetaEngineConnect &metaEngineConnect = enginePlugin->get<MetaEngineConnect>();
-		if (metaEngineConnect.hasFeature(MetaEngineConnect::kSupportsListSaves) &&
-			metaEngineConnect.hasFeature(MetaEngineConnect::kSupportsLoadingDuringStartup)) {
+		const MetaEngine &metaEngineConnect = enginePlugin->get<MetaEngine>();
+		if (metaEngineConnect.hasFeature(MetaEngine::kSupportsListSaves) &&
+			metaEngineConnect.hasFeature(MetaEngine::kSupportsLoadingDuringStartup)) {
 			int slot = _loadDialog->runModalWithPluginAndTarget(enginePlugin, target);
 			if (slot >= 0) {
 				ConfMan.setActiveDomain(_domains[item]);
diff --git a/gui/saveload-dialog.cpp b/gui/saveload-dialog.cpp
index 81f162c28d..54a8e2539b 100644
--- a/gui/saveload-dialog.cpp
+++ b/gui/saveload-dialog.cpp
@@ -103,7 +103,7 @@ void SaveLoadCloudSyncProgressDialog::handleTickle() {
 #endif
 
 #ifndef DISABLE_SAVELOADCHOOSER_GRID
-SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngineConnect &metaEngine) {
+SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngine &metaEngine) {
 	const Common::String &userConfig = ConfMan.get("gui_saveload_chooser", Common::ConfigManager::kApplicationDomain);
 
 	// Check (and update if necessary) the theme config here. This catches
@@ -114,8 +114,8 @@ SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngineConnect &metaEngi
 	g_gui.checkScreenChange();
 
 	if (g_gui.getWidth() >= 640 && g_gui.getHeight() >= 400
-		&& metaEngine.hasFeature(MetaEngineConnect::kSavesSupportMetaInfo)
-		&& metaEngine.hasFeature(MetaEngineConnect::kSavesSupportThumbnail)
+		&& metaEngine.hasFeature(MetaEngine::kSavesSupportMetaInfo)
+		&& metaEngine.hasFeature(MetaEngine::kSavesSupportThumbnail)
 		&& userConfig.equalsIgnoreCase("grid")) {
 		// In case we are 640x400 or higher, this dialog is not in save mode,
 		// the user requested the grid dialog and the engines supports it we
@@ -182,14 +182,14 @@ void SaveLoadChooserDialog::close() {
 	Dialog::close();
 }
 
-int SaveLoadChooserDialog::run(const Common::String &target, const MetaEngineConnect *metaEngine) {
+int SaveLoadChooserDialog::run(const Common::String &target, const MetaEngine *metaEngine) {
 	_metaEngine = metaEngine;
 	_target = target;
-	_delSupport = _metaEngine->hasFeature(MetaEngineConnect::kSupportsDeleteSave);
-	_metaInfoSupport = _metaEngine->hasFeature(MetaEngineConnect::kSavesSupportMetaInfo);
-	_thumbnailSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngineConnect::kSavesSupportThumbnail);
-	_saveDateSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngineConnect::kSavesSupportCreationDate);
-	_playTimeSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngineConnect::kSavesSupportPlayTime);
+	_delSupport = _metaEngine->hasFeature(MetaEngine::kSupportsDeleteSave);
+	_metaInfoSupport = _metaEngine->hasFeature(MetaEngine::kSavesSupportMetaInfo);
+	_thumbnailSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngine::kSavesSupportThumbnail);
+	_saveDateSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngine::kSavesSupportCreationDate);
+	_playTimeSupport = _metaInfoSupport && _metaEngine->hasFeature(MetaEngine::kSavesSupportPlayTime);
 
 	return runIntern();
 }
@@ -248,7 +248,7 @@ void SaveLoadChooserDialog::handleTickle() {
 		Common::Array<Common::String> files = CloudMan.getSyncingFiles();
 		if (!files.empty()) {
 			{
-				SaveLoadCloudSyncProgressDialog dialog(_metaEngine ? _metaEngine->hasFeature(MetaEngineConnect::kSimpleSavesNames) : false);
+				SaveLoadCloudSyncProgressDialog dialog(_metaEngine ? _metaEngine->hasFeature(MetaEngine::kSimpleSavesNames) : false);
 				CloudMan.setSyncTarget(&dialog);
 				int result = dialog.runModal();
 				if (result == kCancelSyncCmd) {
@@ -302,7 +302,7 @@ void SaveLoadChooserDialog::listSaves() {
 
 #if defined(USE_CLOUD) && defined(USE_LIBCURL)
 	//if there is Cloud support, add currently synced files as "locked" saves in the list
-	if (_metaEngine->hasFeature(MetaEngineConnect::kSimpleSavesNames)) {
+	if (_metaEngine->hasFeature(MetaEngine::kSimpleSavesNames)) {
 		Common::String pattern = _target + ".###";
 		Common::Array<Common::String> files = CloudMan.getSyncingFiles(); //returns empty array if not syncing
 		for (uint32 i = 0; i < files.size(); ++i) {
diff --git a/gui/saveload-dialog.h b/gui/saveload-dialog.h
index 8ff5851ca7..f0d986fbb3 100644
--- a/gui/saveload-dialog.h
+++ b/gui/saveload-dialog.h
@@ -65,7 +65,7 @@ enum SaveLoadChooserType {
 	kSaveLoadDialogGrid = 1
 };
 
-SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngineConnect &metaEngine);
+SaveLoadChooserType getRequestedSaveLoadDialog(const MetaEngine &metaEngine);
 #endif // !DISABLE_SAVELOADCHOOSER_GRID
 
 class SaveLoadChooserDialog : protected Dialog {
@@ -91,7 +91,7 @@ public:
 	virtual SaveLoadChooserType getType() const = 0;
 #endif // !DISABLE_SAVELOADCHOOSER_GRID
 
-	int run(const Common::String &target, const MetaEngineConnect *metaEngine);
+	int run(const Common::String &target, const MetaEngine *metaEngine);
 	virtual const Common::U32String &getResultString() const = 0;
 
 protected:
@@ -111,7 +111,7 @@ protected:
 	virtual void listSaves();
 
 	const bool					_saveMode;
-	const MetaEngineConnect		*_metaEngine;
+	const MetaEngine		    *_metaEngine;
 	bool						_delSupport;
 	bool						_metaInfoSupport;
 	bool						_thumbnailSupport;
diff --git a/gui/saveload.cpp b/gui/saveload.cpp
index db026eb68d..084bbc0f48 100644
--- a/gui/saveload.cpp
+++ b/gui/saveload.cpp
@@ -39,7 +39,7 @@ SaveLoadChooser::~SaveLoadChooser() {
 	_impl = nullptr;
 }
 
-void SaveLoadChooser::selectChooser(const MetaEngineConnect &engine) {
+void SaveLoadChooser::selectChooser(const MetaEngine &engine) {
 #ifndef DISABLE_SAVELOADCHOOSER_GRID
 	const SaveLoadChooserType requestedType = getRequestedSaveLoadDialog(engine);
 	if (!_impl || _impl->getType() != requestedType) {
@@ -94,7 +94,7 @@ int SaveLoadChooser::runModalWithCurrentTarget() {
 int SaveLoadChooser::runModalWithPluginAndTarget(const Plugin *plugin, const String &target) {
 	assert(plugin->getType() == PLUGIN_TYPE_ENGINE);
 
-	selectChooser(plugin->get<MetaEngineConnect>());
+	selectChooser(plugin->get<MetaEngine>());
 	if (!_impl)
 		return -1;
 
@@ -109,10 +109,10 @@ int SaveLoadChooser::runModalWithPluginAndTarget(const Plugin *plugin, const Str
 
 	int ret;
 	do {
-		ret = _impl->run(target, &plugin->get<MetaEngineConnect>());
+		ret = _impl->run(target, &plugin->get<MetaEngine>());
 #ifndef DISABLE_SAVELOADCHOOSER_GRID
 		if (ret == kSwitchSaveLoadDialog) {
-			selectChooser(plugin->get<MetaEngineConnect>());
+			selectChooser(plugin->get<MetaEngine>());
 		}
 #endif // !DISABLE_SAVELOADCHOOSER_GRID
 	} while (ret < -1);
diff --git a/gui/saveload.h b/gui/saveload.h
index 5591c04dc4..3a976863d5 100644
--- a/gui/saveload.h
+++ b/gui/saveload.h
@@ -40,7 +40,7 @@ protected:
 	const U32String _buttonLabel;
 	const bool _saveMode;
 
-	void selectChooser(const MetaEngineConnect &engine);
+	void selectChooser(const MetaEngine &engine);
 public:
 	SaveLoadChooser(const U32String &title, const U32String &buttonLabel, bool saveMode);
 	~SaveLoadChooser();


Commit: d26bbe521c95781361c42fe545fcbaad80ac126b
    https://github.com/scummvm/scummvm/commit/d26bbe521c95781361c42fe545fcbaad80ac126b
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: ALL: Finish renaming ME & AME classes

- ME -> MetaEngineStatic (static parts)
- MEC -> MetaEngine (dynamic parts)

Changed paths:
    engines/access/detection.cpp
    engines/access/metaengine.cpp
    engines/adl/detection.cpp
    engines/adl/metaengine.cpp
    engines/agi/detection.cpp
    engines/agi/metaengine.cpp
    engines/agos/detection.cpp
    engines/agos/metaengine.cpp
    engines/avalanche/detection.cpp
    engines/avalanche/metaengine.cpp
    engines/bbvs/detection.cpp
    engines/bbvs/metaengine.cpp
    engines/bladerunner/detection.cpp
    engines/bladerunner/metaengine.cpp
    engines/cge/detection.cpp
    engines/cge/metaengine.cpp
    engines/cge2/detection.cpp
    engines/cge2/metaengine.cpp
    engines/chewy/detection.cpp
    engines/chewy/metaengine.cpp
    engines/cine/detection.cpp
    engines/cine/metaengine.cpp
    engines/cine/saveload.cpp
    engines/composer/detection.cpp
    engines/composer/metaengine.cpp
    engines/cruise/detection.cpp
    engines/cruise/metaengine.cpp
    engines/cryo/detection.cpp
    engines/cryo/metaengine.cpp
    engines/cryomni3d/detection.cpp
    engines/cryomni3d/metaengine.cpp
    engines/director/detection.cpp
    engines/director/metaengine.cpp
    engines/dm/detection.cpp
    engines/dm/metaengine.cpp
    engines/draci/detection.cpp
    engines/draci/metaengine.cpp
    engines/dragons/detection.cpp
    engines/dragons/metaengine.cpp
    engines/drascula/detection.cpp
    engines/drascula/metaengine.cpp
    engines/dreamweb/detection.cpp
    engines/dreamweb/metaengine.cpp
    engines/fullpipe/detection.cpp
    engines/fullpipe/metaengine.cpp
    engines/glk/detection.cpp
    engines/glk/detection.h
    engines/glk/metaengine.cpp
    engines/gnap/detection.cpp
    engines/gnap/metaengine.cpp
    engines/gob/detection/detection.cpp
    engines/gob/metaengine.cpp
    engines/griffon/detection.cpp
    engines/griffon/metaengine.cpp
    engines/groovie/detection.cpp
    engines/groovie/metaengine.cpp
    engines/hdb/detection.cpp
    engines/hdb/metaengine.cpp
    engines/hopkins/detection.cpp
    engines/hopkins/metaengine.cpp
    engines/hugo/detection.cpp
    engines/hugo/metaengine.cpp
    engines/illusions/detection.cpp
    engines/illusions/metaengine.cpp
    engines/kingdom/detection.cpp
    engines/kingdom/metaengine.cpp
    engines/kyra/detection.cpp
    engines/kyra/kyra_v1.h
    engines/kyra/metaengine.cpp
    engines/lab/detection.cpp
    engines/lab/metaengine.cpp
    engines/lastexpress/detection.cpp
    engines/lastexpress/metaengine.cpp
    engines/lilliput/detection.cpp
    engines/lilliput/metaengine.cpp
    engines/lure/detection.cpp
    engines/lure/metaengine.cpp
    engines/macventure/detection.cpp
    engines/macventure/metaengine.cpp
    engines/made/detection.cpp
    engines/made/metaengine.cpp
    engines/mads/detection.cpp
    engines/mads/metaengine.cpp
    engines/mohawk/detection.cpp
    engines/mohawk/metaengine.cpp
    engines/mortevielle/detection.cpp
    engines/mortevielle/metaengine.cpp
    engines/mutationofjb/detection.cpp
    engines/mutationofjb/metaengine.cpp
    engines/neverhood/detection.cpp
    engines/neverhood/metaengine.cpp
    engines/parallaction/detection.cpp
    engines/parallaction/metaengine.cpp
    engines/pegasus/detection.cpp
    engines/pegasus/metaengine.cpp
    engines/petka/detection.cpp
    engines/petka/metaengine.cpp
    engines/pink/detection.cpp
    engines/pink/metaengine.cpp
    engines/plumbers/detection.cpp
    engines/plumbers/metaengine.cpp
    engines/prince/detection.cpp
    engines/prince/metaengine.cpp
    engines/queen/detection.cpp
    engines/queen/metaengine.cpp
    engines/saga/detection.cpp
    engines/saga/metaengine.cpp
    engines/sci/detection.cpp
    engines/sci/metaengine.cpp
    engines/scumm/detection.cpp
    engines/scumm/metaengine.cpp
    engines/scumm/metaengine.h
    engines/sherlock/detection.cpp
    engines/sherlock/metaengine.cpp
    engines/sky/detection.cpp
    engines/sky/metaengine.cpp
    engines/sludge/detection.cpp
    engines/sludge/metaengine.cpp
    engines/startrek/detection.cpp
    engines/startrek/metaengine.cpp
    engines/supernova/detection.cpp
    engines/supernova/metaengine.cpp
    engines/sword1/detection.cpp
    engines/sword1/metaengine.cpp
    engines/sword2/detection.cpp
    engines/sword2/metaengine.cpp
    engines/sword25/detection.cpp
    engines/sword25/metaengine.cpp
    engines/teenagent/detection.cpp
    engines/teenagent/metaengine.cpp
    engines/testbed/detection.cpp
    engines/testbed/metaengine.cpp
    engines/tinsel/detection.cpp
    engines/tinsel/metaengine.cpp
    engines/titanic/detection.cpp
    engines/titanic/metaengine.cpp
    engines/toltecs/detection.cpp
    engines/toltecs/metaengine.cpp
    engines/tony/detection.cpp
    engines/tony/metaengine.cpp
    engines/toon/detection.cpp
    engines/toon/metaengine.cpp
    engines/touche/detection.cpp
    engines/touche/metaengine.cpp
    engines/tsage/detection.cpp
    engines/tsage/metaengine.cpp
    engines/tucker/detection.cpp
    engines/tucker/metaengine.cpp
    engines/ultima/detection.cpp
    engines/ultima/detection.h
    engines/ultima/metaengine.cpp
    engines/ultima/metaengine.h
    engines/ultima/nuvie/files/nuvie_io_file.cpp
    engines/ultima/ultima8/filesys/savegame.cpp
    engines/voyeur/detection.cpp
    engines/voyeur/metaengine.cpp
    engines/wage/detection.cpp
    engines/wage/metaengine.cpp
    engines/wintermute/detection.cpp
    engines/wintermute/ext/wme_galaxy.cpp
    engines/wintermute/ext/wme_steam.cpp
    engines/wintermute/metaengine.cpp
    engines/xeen/detection.cpp
    engines/xeen/metaengine.cpp
    engines/zvision/detection.cpp
    engines/zvision/metaengine.cpp


diff --git a/engines/access/detection.cpp b/engines/access/detection.cpp
index 173b3ea8c7..af443fbb45 100644
--- a/engines/access/detection.cpp
+++ b/engines/access/detection.cpp
@@ -32,9 +32,9 @@ static const PlainGameDescriptor AccessGames[] = {
 
 #include "access/detection_tables.h"
 
-class AccessMetaEngine : public AdvancedMetaEngine {
+class AccessMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	AccessMetaEngine() : AdvancedMetaEngine(Access::gameDescriptions, sizeof(Access::AccessGameDescription), AccessGames) {
+	AccessMetaEngineStatic() : AdvancedMetaEngineStatic(Access::gameDescriptions, sizeof(Access::AccessGameDescription), AccessGames) {
 		_maxScanDepth = 3;
 	}
 
@@ -52,4 +52,4 @@ public:
 };
 
 
-REGISTER_PLUGIN_STATIC(ACCESS_DETECTION, PLUGIN_TYPE_METAENGINE, AccessMetaEngine);
+REGISTER_PLUGIN_STATIC(ACCESS_DETECTION, PLUGIN_TYPE_METAENGINE, AccessMetaEngineStatic);
diff --git a/engines/access/metaengine.cpp b/engines/access/metaengine.cpp
index 3ed66d49f1..662c7e6617 100644
--- a/engines/access/metaengine.cpp
+++ b/engines/access/metaengine.cpp
@@ -68,7 +68,7 @@ Common::Platform AccessEngine::getPlatform() const {
 
 } // End of namespace Access
 
-class AccessMetaEngineConnect : public AdvancedMetaEngineConnect {
+class AccessMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "access";
@@ -84,7 +84,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool AccessMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool AccessMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -101,7 +101,7 @@ bool Access::AccessEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool AccessMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool AccessMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Access::AccessGameDescription *gd = (const Access::AccessGameDescription *)desc;
 	if (gd) {
 		switch (gd->gameID) {
@@ -118,7 +118,7 @@ bool AccessMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, con
 	return gd != 0;
 }
 
-SaveStateList AccessMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList AccessMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -149,16 +149,16 @@ SaveStateList AccessMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int AccessMetaEngineConnect::getMaximumSaveSlot() const {
+int AccessMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVES;
 }
 
-void AccessMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void AccessMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor AccessMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor AccessMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
 
@@ -185,7 +185,7 @@ SaveStateDescriptor AccessMetaEngineConnect::querySaveMetaInfos(const char *targ
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(ACCESS)
-	REGISTER_PLUGIN_DYNAMIC(ACCESS, PLUGIN_TYPE_ENGINE, AccessMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(ACCESS, PLUGIN_TYPE_ENGINE, AccessMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(ACCESS, PLUGIN_TYPE_ENGINE, AccessMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(ACCESS, PLUGIN_TYPE_ENGINE, AccessMetaEngine);
 #endif
diff --git a/engines/adl/detection.cpp b/engines/adl/detection.cpp
index 11603e231b..7c71801acb 100644
--- a/engines/adl/detection.cpp
+++ b/engines/adl/detection.cpp
@@ -337,9 +337,9 @@ static const AdlGameDescription gameDiskDescriptions[] = {
 	{ AD_TABLE_END_MARKER, GAME_TYPE_NONE, GAME_VER_NONE }
 };
 
-class AdlMetaEngine : public AdvancedMetaEngine {
+class AdlMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	AdlMetaEngine() : AdvancedMetaEngine(gameFileDescriptions, sizeof(AdlGameDescription), adlGames, optionsList) { }
+	AdlMetaEngineStatic() : AdvancedMetaEngineStatic(gameFileDescriptions, sizeof(AdlGameDescription), adlGames, optionsList) { }
 
 	const char *getName() const override {
 		return "ADL";
@@ -358,7 +358,7 @@ public:
 	bool addFileProps(const FileMap &allFiles, Common::String fname, FilePropertiesMap &filePropsMap) const;
 };
 
-bool AdlMetaEngine::addFileProps(const FileMap &allFiles, Common::String fname, FilePropertiesMap &filePropsMap) const {
+bool AdlMetaEngineStatic::addFileProps(const FileMap &allFiles, Common::String fname, FilePropertiesMap &filePropsMap) const {
 	if (filePropsMap.contains(fname))
 		return true;
 
@@ -377,9 +377,9 @@ bool AdlMetaEngine::addFileProps(const FileMap &allFiles, Common::String fname,
 }
 
 // Based on AdvancedMetaEngine::detectGame
-ADDetectedGames AdlMetaEngine::detectGame(const Common::FSNode &parent, const FileMap &allFiles, Common::Language language, Common::Platform platform, const Common::String &extra) const {
+ADDetectedGames AdlMetaEngineStatic::detectGame(const Common::FSNode &parent, const FileMap &allFiles, Common::Language language, Common::Platform platform, const Common::String &extra) const {
 	// We run the file-based detector first, if it finds a match we do not search for disk images
-	ADDetectedGames matched = AdvancedMetaEngine::detectGame(parent, allFiles, language, platform, extra);
+	ADDetectedGames matched = AdvancedMetaEngineStatic::detectGame(parent, allFiles, language, platform, extra);
 
 	if (!matched.empty())
 		return matched;
@@ -474,4 +474,4 @@ ADDetectedGames AdlMetaEngine::detectGame(const Common::FSNode &parent, const Fi
 
 } // End of namespace Adl
 
-REGISTER_PLUGIN_STATIC(ADL_DETECTION, PLUGIN_TYPE_METAENGINE, Adl::AdlMetaEngine);
+REGISTER_PLUGIN_STATIC(ADL_DETECTION, PLUGIN_TYPE_METAENGINE, Adl::AdlMetaEngineStatic);
diff --git a/engines/adl/metaengine.cpp b/engines/adl/metaengine.cpp
index a479c5ef1f..daa38dfcf6 100644
--- a/engines/adl/metaengine.cpp
+++ b/engines/adl/metaengine.cpp
@@ -67,7 +67,7 @@ Common::Platform getPlatform(const AdlGameDescription &adlDesc) {
 	return adlDesc.desc.platform;
 }
 
-class AdlMetaEngineConnect : public AdvancedMetaEngineConnect {
+class AdlMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "adl";
@@ -82,7 +82,7 @@ public:
     bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
 };
 
-bool AdlMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool AdlMetaEngine::hasFeature(MetaEngineFeature f) const {
 	switch(f) {
 	case kSupportsListSaves:
 	case kSupportsLoadingDuringStartup:
@@ -98,7 +98,7 @@ bool AdlMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 	}
 }
 
-SaveStateDescriptor AdlMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor AdlMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.s%02d", target, slot);
 	Common::InSaveFile *inFile = g_system->getSavefileManager()->openForLoading(fileName);
 
@@ -155,7 +155,7 @@ SaveStateDescriptor AdlMetaEngineConnect::querySaveMetaInfos(const char *target,
 	return sd;
 }
 
-SaveStateList AdlMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList AdlMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray files = saveFileMan->listSavefiles(Common::String(target) + ".s##");
 
@@ -196,7 +196,7 @@ SaveStateList AdlMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void AdlMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void AdlMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.s%02d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
@@ -209,7 +209,7 @@ Engine *HiRes4Engine_create(OSystem *syst, const AdlGameDescription *gd);
 Engine *HiRes5Engine_create(OSystem *syst, const AdlGameDescription *gd);
 Engine *HiRes6Engine_create(OSystem *syst, const AdlGameDescription *gd);
 
-bool AdlMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+bool AdlMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
 	if (!gd)
 		return false;
 
@@ -247,8 +247,8 @@ bool AdlMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 } // End of namespace Adl
 
 #if PLUGIN_ENABLED_DYNAMIC(ADL)
-	REGISTER_PLUGIN_DYNAMIC(ADL, PLUGIN_TYPE_ENGINE, Adl::AdlMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(ADL, PLUGIN_TYPE_ENGINE, Adl::AdlMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(ADL, PLUGIN_TYPE_ENGINE, Adl::AdlMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(ADL, PLUGIN_TYPE_ENGINE, Adl::AdlMetaEngine);
 #endif
 
diff --git a/engines/agi/detection.cpp b/engines/agi/detection.cpp
index e3a87feb1e..c72953afaf 100644
--- a/engines/agi/detection.cpp
+++ b/engines/agi/detection.cpp
@@ -131,12 +131,12 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 
 using namespace Agi;
 
-class AgiMetaEngine : public AdvancedMetaEngine {
+class AgiMetaEngineStatic : public AdvancedMetaEngineStatic {
 	mutable Common::String _gameid;
 	mutable Common::String _extra;
 
 public:
-	AgiMetaEngine() : AdvancedMetaEngine(Agi::gameDescriptions, sizeof(Agi::AGIGameDescription), agiGames, optionsList) {
+	AgiMetaEngineStatic() : AdvancedMetaEngineStatic(Agi::gameDescriptions, sizeof(Agi::AGIGameDescription), agiGames, optionsList) {
 		_guiOptions = GUIO1(GUIO_NOSPEECH);
 	}
 
@@ -155,7 +155,7 @@ public:
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
 };
 
-ADDetectedGame AgiMetaEngine::fallbackDetect(const FileMap &allFilesXXX, const Common::FSList &fslist) const {
+ADDetectedGame AgiMetaEngineStatic::fallbackDetect(const FileMap &allFilesXXX, const Common::FSList &fslist) const {
 	typedef Common::HashMap<Common::String, int32> IntMap;
 	IntMap allFiles;
 	bool matchedUsingFilenames = false;
@@ -323,4 +323,4 @@ ADDetectedGame AgiMetaEngine::fallbackDetect(const FileMap &allFilesXXX, const C
 	return ADDetectedGame();
 }
 
-REGISTER_PLUGIN_STATIC(AGI_DETECTION, PLUGIN_TYPE_METAENGINE, AgiMetaEngine);
+REGISTER_PLUGIN_STATIC(AGI_DETECTION, PLUGIN_TYPE_METAENGINE, AgiMetaEngineStatic);
diff --git a/engines/agi/metaengine.cpp b/engines/agi/metaengine.cpp
index f2507a8f37..3811371c8b 100644
--- a/engines/agi/metaengine.cpp
+++ b/engines/agi/metaengine.cpp
@@ -106,7 +106,7 @@ bool AgiBase::hasFeature(EngineFeature f) const {
 
 using namespace Agi;
 
-class AgiMetaEngineConnect : public AdvancedMetaEngineConnect {
+class AgiMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "agi";
@@ -122,7 +122,7 @@ public:
 	bool hasFeature(MetaEngineFeature f) const override;
 };
 
-bool AgiMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool AgiMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 	    (f == kSupportsLoadingDuringStartup) ||
@@ -134,7 +134,7 @@ bool AgiMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSimpleSavesNames);
 }
 
-bool AgiMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool AgiMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Agi::AGIGameDescription *gd = (const Agi::AGIGameDescription *)desc;
 	bool res = true;
 
@@ -169,7 +169,7 @@ bool AgiMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return res;
 }
 
-SaveStateList AgiMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList AgiMetaEngine::listSaves(const char *target) const {
 	const uint32 AGIflag = MKTAG('A', 'G', 'I', ':');
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
@@ -219,14 +219,14 @@ SaveStateList AgiMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void AgiMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void AgiMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-int AgiMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+int AgiMetaEngine::getMaximumSaveSlot() const { return 999; }
 
-SaveStateDescriptor AgiMetaEngineConnect::querySaveMetaInfos(const char *target, int slotNr) const {
+SaveStateDescriptor AgiMetaEngine::querySaveMetaInfos(const char *target, int slotNr) const {
 	const uint32 AGIflag = MKTAG('A', 'G', 'I', ':');
 	Common::String fileName = Common::String::format("%s.%03d", target, slotNr);
 
@@ -317,9 +317,9 @@ SaveStateDescriptor AgiMetaEngineConnect::querySaveMetaInfos(const char *target,
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(AGI)
-	REGISTER_PLUGIN_DYNAMIC(AGI, PLUGIN_TYPE_ENGINE, AgiMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(AGI, PLUGIN_TYPE_ENGINE, AgiMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(AGI, PLUGIN_TYPE_ENGINE, AgiMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(AGI, PLUGIN_TYPE_ENGINE, AgiMetaEngine);
 #endif
 
 namespace Agi {
diff --git a/engines/agos/detection.cpp b/engines/agos/detection.cpp
index 6626c980e7..9fea140ac3 100644
--- a/engines/agos/detection.cpp
+++ b/engines/agos/detection.cpp
@@ -65,9 +65,9 @@ static const char *const directoryGlobs[] = {
 
 using namespace AGOS;
 
-class AgosMetaEngine : public AdvancedMetaEngine {
+class AgosMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	AgosMetaEngine() : AdvancedMetaEngine(AGOS::gameDescriptions, sizeof(AGOS::AGOSGameDescription), agosGames) {
+	AgosMetaEngineStatic() : AdvancedMetaEngineStatic(AGOS::gameDescriptions, sizeof(AGOS::AGOSGameDescription), agosGames) {
 		_guiOptions = GUIO1(GUIO_NOLAUNCHLOAD);
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
@@ -90,4 +90,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(AGOS_DETECTION, PLUGIN_TYPE_METAENGINE, AgosMetaEngine);
+REGISTER_PLUGIN_STATIC(AGOS_DETECTION, PLUGIN_TYPE_METAENGINE, AgosMetaEngineStatic);
diff --git a/engines/agos/metaengine.cpp b/engines/agos/metaengine.cpp
index 7bac156118..98655c22aa 100644
--- a/engines/agos/metaengine.cpp
+++ b/engines/agos/metaengine.cpp
@@ -33,7 +33,7 @@
 #include "agos/detection.h"
 #include "agos/obsolete.h"
 
-class AgosMetaEngineConnect : public AdvancedMetaEngineConnect {
+class AgosMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "agos";
@@ -43,7 +43,7 @@ public:
 
 	Common::Error createInstance(OSystem *syst, Engine **engine) const override {
 		Engines::upgradeTargetIfNecessary(obsoleteGameIDsTable);
-		return AdvancedMetaEngineConnect::createInstance(syst, engine);
+		return AdvancedMetaEngine::createInstance(syst, engine);
 	}
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 
@@ -51,7 +51,7 @@ public:
 	int getMaximumSaveSlot() const override;
 };
 
-bool AgosMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool AgosMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSimpleSavesNames);
@@ -62,7 +62,7 @@ bool AGOS::AGOSEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsReturnToLauncher);
 }
 
-bool AgosMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool AgosMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const AGOS::AGOSGameDescription *gd = (const AGOS::AGOSGameDescription *)desc;
 	bool res = true;
 
@@ -107,7 +107,7 @@ bool AgosMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return res;
 }
 
-SaveStateList AgosMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList AgosMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -136,12 +136,12 @@ SaveStateList AgosMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int AgosMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+int AgosMetaEngine::getMaximumSaveSlot() const { return 999; }
 
 #if PLUGIN_ENABLED_DYNAMIC(AGOS)
-	REGISTER_PLUGIN_DYNAMIC(AGOS, PLUGIN_TYPE_ENGINE, AgosMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(AGOS, PLUGIN_TYPE_ENGINE, AgosMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(AGOS, PLUGIN_TYPE_ENGINE, AgosMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(AGOS, PLUGIN_TYPE_ENGINE, AgosMetaEngine);
 #endif
 
 namespace AGOS {
diff --git a/engines/avalanche/detection.cpp b/engines/avalanche/detection.cpp
index d6baf0f64e..4c9552a0d3 100644
--- a/engines/avalanche/detection.cpp
+++ b/engines/avalanche/detection.cpp
@@ -56,9 +56,9 @@ static const ADGameDescription gameDescriptions[] = {
 	AD_TABLE_END_MARKER
 };
 
-class AvalancheMetaEngine : public AdvancedMetaEngine {
+class AvalancheMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	AvalancheMetaEngine() : AdvancedMetaEngine(gameDescriptions, sizeof(AvalancheGameDescription), avalancheGames) {
+	AvalancheMetaEngineStatic() : AdvancedMetaEngineStatic(gameDescriptions, sizeof(AvalancheGameDescription), avalancheGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -76,4 +76,4 @@ public:
 
 } // End of namespace Avalanche
 
-REGISTER_PLUGIN_STATIC(AVALANCHE_DETECTION, PLUGIN_TYPE_METAENGINE, Avalanche::AvalancheMetaEngine);
+REGISTER_PLUGIN_STATIC(AVALANCHE_DETECTION, PLUGIN_TYPE_METAENGINE, Avalanche::AvalancheMetaEngineStatic);
diff --git a/engines/avalanche/metaengine.cpp b/engines/avalanche/metaengine.cpp
index f004c89964..51ff2dea27 100644
--- a/engines/avalanche/metaengine.cpp
+++ b/engines/avalanche/metaengine.cpp
@@ -54,7 +54,7 @@ Common::Platform AvalancheEngine::getPlatform() const {
 
 namespace Avalanche {
 
-class AvalancheMetaEngineConnect : public AdvancedMetaEngineConnect {
+class AvalancheMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "avalanche";
@@ -69,13 +69,13 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool AvalancheMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+bool AvalancheMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
 	if (gd)
 		*engine = new AvalancheEngine(syst, (const AvalancheGameDescription *)gd);
 	return gd != 0;
 }
 
-bool AvalancheMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool AvalancheMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave) ||
@@ -85,7 +85,7 @@ bool AvalancheMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSimpleSavesNames);
 }
 
-SaveStateList AvalancheMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList AvalancheMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -139,12 +139,12 @@ SaveStateList AvalancheMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void AvalancheMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void AvalancheMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-SaveStateDescriptor AvalancheMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor AvalancheMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
 
@@ -192,7 +192,7 @@ SaveStateDescriptor AvalancheMetaEngineConnect::querySaveMetaInfos(const char *t
 } // End of namespace Avalanche
 
 #if PLUGIN_ENABLED_DYNAMIC(AVALANCHE)
-	REGISTER_PLUGIN_DYNAMIC(AVALANCHE, PLUGIN_TYPE_ENGINE, Avalanche::AvalancheMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(AVALANCHE, PLUGIN_TYPE_ENGINE, Avalanche::AvalancheMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(AVALANCHE, PLUGIN_TYPE_ENGINE, Avalanche::AvalancheMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(AVALANCHE, PLUGIN_TYPE_ENGINE, Avalanche::AvalancheMetaEngine);
 #endif
diff --git a/engines/bbvs/detection.cpp b/engines/bbvs/detection.cpp
index 4b50e7ce7d..33d28c6bfc 100644
--- a/engines/bbvs/detection.cpp
+++ b/engines/bbvs/detection.cpp
@@ -83,9 +83,9 @@ static const char * const directoryGlobs[] = {
 	0
 };
 
-class BbvsMetaEngine : public AdvancedMetaEngine {
+class BbvsMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	BbvsMetaEngine() : AdvancedMetaEngine(Bbvs::gameDescriptions, sizeof(ADGameDescription), bbvsGames) {
+	BbvsMetaEngineStatic() : AdvancedMetaEngineStatic(Bbvs::gameDescriptions, sizeof(ADGameDescription), bbvsGames) {
 		_maxScanDepth = 3;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -103,4 +103,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(BBVS_DETECTION, PLUGIN_TYPE_METAENGINE, BbvsMetaEngine);
+REGISTER_PLUGIN_STATIC(BBVS_DETECTION, PLUGIN_TYPE_METAENGINE, BbvsMetaEngineStatic);
diff --git a/engines/bbvs/metaengine.cpp b/engines/bbvs/metaengine.cpp
index c888af3fe5..ca070f4cac 100644
--- a/engines/bbvs/metaengine.cpp
+++ b/engines/bbvs/metaengine.cpp
@@ -37,7 +37,7 @@ bool BbvsEngine::isLoogieDemo() const {
 
 } // End of namespace Bbvs
 
-class BbvsMetaEngineConnect : public AdvancedMetaEngineConnect {
+class BbvsMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "bbvs";
@@ -52,7 +52,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool BbvsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool BbvsMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 	    (f == kSupportsDeleteSave) ||
@@ -63,16 +63,16 @@ bool BbvsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSimpleSavesNames);
 }
 
-void BbvsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void BbvsMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-int BbvsMetaEngineConnect::getMaximumSaveSlot() const {
+int BbvsMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-SaveStateList BbvsMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList BbvsMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Bbvs::BbvsEngine::SaveHeader header;
 	Common::String pattern = target;
@@ -98,7 +98,7 @@ SaveStateList BbvsMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor BbvsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor BbvsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Bbvs::BbvsEngine::getSavegameFilename(target, slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
 	if (in) {
@@ -121,7 +121,7 @@ SaveStateDescriptor BbvsMetaEngineConnect::querySaveMetaInfos(const char *target
 	return SaveStateDescriptor();
 }
 
-bool BbvsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool BbvsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Bbvs::BbvsEngine(syst, desc);
 	}
@@ -129,7 +129,7 @@ bool BbvsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(BBVS)
-	REGISTER_PLUGIN_DYNAMIC(BBVS, PLUGIN_TYPE_ENGINE, BbvsMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(BBVS, PLUGIN_TYPE_ENGINE, BbvsMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(BBVS, PLUGIN_TYPE_ENGINE, BbvsMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(BBVS, PLUGIN_TYPE_ENGINE, BbvsMetaEngine);
 #endif
diff --git a/engines/bladerunner/detection.cpp b/engines/bladerunner/detection.cpp
index ecef2d5b34..5c0bec1af2 100644
--- a/engines/bladerunner/detection.cpp
+++ b/engines/bladerunner/detection.cpp
@@ -92,32 +92,32 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 
 } // End of namespace BladeRunner
 
-class BladeRunnerMetaEngine : public AdvancedMetaEngine {
+class BladeRunnerMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	BladeRunnerMetaEngine();
+	BladeRunnerMetaEngineStatic();
 
 	const char *getEngineId() const override;
 	const char *getName() const override;
 	const char *getOriginalCopyright() const override;
 };
 
-BladeRunnerMetaEngine::BladeRunnerMetaEngine()
-	: AdvancedMetaEngine(
+BladeRunnerMetaEngineStatic::BladeRunnerMetaEngineStatic()
+	: AdvancedMetaEngineStatic(
 		BladeRunner::gameDescriptions,
 		sizeof(BladeRunner::gameDescriptions[0]),
 		BladeRunner::bladeRunnerGames,
 		BladeRunner::optionsList) {}
 
-const char *BladeRunnerMetaEngine::getEngineId() const {
+const char *BladeRunnerMetaEngineStatic::getEngineId() const {
 	return "bladerunner";
 }
 
-const char *BladeRunnerMetaEngine::getName() const {
+const char *BladeRunnerMetaEngineStatic::getName() const {
 	return "Blade Runner";
 }
 
-const char *BladeRunnerMetaEngine::getOriginalCopyright() const {
+const char *BladeRunnerMetaEngineStatic::getOriginalCopyright() const {
 	return "Blade Runner (C) 1997 Westwood Studios";
 }
 
-REGISTER_PLUGIN_STATIC(BLADERUNNER_DETECTION, PLUGIN_TYPE_METAENGINE, BladeRunnerMetaEngine);
+REGISTER_PLUGIN_STATIC(BLADERUNNER_DETECTION, PLUGIN_TYPE_METAENGINE, BladeRunnerMetaEngineStatic);
diff --git a/engines/bladerunner/metaengine.cpp b/engines/bladerunner/metaengine.cpp
index 46d7da01e1..00be0f73c2 100644
--- a/engines/bladerunner/metaengine.cpp
+++ b/engines/bladerunner/metaengine.cpp
@@ -32,7 +32,7 @@
 
 #include "engines/advancedDetector.h"
 
-class BladeRunnerMetaEngineConnect : public AdvancedMetaEngineConnect {
+class BladeRunnerMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override;
 
@@ -45,17 +45,17 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-const char *BladeRunnerMetaEngineConnect::getName() const {
+const char *BladeRunnerMetaEngine::getName() const {
 	return "bladerunner";
 }
 
-bool BladeRunnerMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool BladeRunnerMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	*engine = new BladeRunner::BladeRunnerEngine(syst, desc);
 
 	return true;
 }
 
-bool BladeRunnerMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool BladeRunnerMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		f == kSupportsListSaves ||
 		f == kSupportsLoadingDuringStartup ||
@@ -67,24 +67,24 @@ bool BladeRunnerMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		f == kSimpleSavesNames;
 }
 
-SaveStateList BladeRunnerMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList BladeRunnerMetaEngine::listSaves(const char *target) const {
 	return BladeRunner::SaveFileManager::list(target);
 }
 
-int BladeRunnerMetaEngineConnect::getMaximumSaveSlot() const {
+int BladeRunnerMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-void BladeRunnerMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void BladeRunnerMetaEngine::removeSaveState(const char *target, int slot) const {
 	BladeRunner::SaveFileManager::remove(target, slot);
 }
 
-SaveStateDescriptor BladeRunnerMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor BladeRunnerMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	return BladeRunner::SaveFileManager::queryMetaInfos(target, slot);
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(BLADERUNNER)
-	REGISTER_PLUGIN_DYNAMIC(BLADERUNNER, PLUGIN_TYPE_ENGINE, BladeRunnerMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(BLADERUNNER, PLUGIN_TYPE_ENGINE, BladeRunnerMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(BLADERUNNER, PLUGIN_TYPE_ENGINE, BladeRunnerMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(BLADERUNNER, PLUGIN_TYPE_ENGINE, BladeRunnerMetaEngine);
 #endif
diff --git a/engines/cge/detection.cpp b/engines/cge/detection.cpp
index 92288b2e59..1d8d433863 100644
--- a/engines/cge/detection.cpp
+++ b/engines/cge/detection.cpp
@@ -120,9 +120,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class CGEMetaEngine : public AdvancedMetaEngine {
+class CGEMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	CGEMetaEngine() : AdvancedMetaEngine(CGE::gameDescriptions, sizeof(ADGameDescription), CGEGames, optionsList) {
+	CGEMetaEngineStatic() : AdvancedMetaEngineStatic(CGE::gameDescriptions, sizeof(ADGameDescription), CGEGames, optionsList) {
 	}
 
 	const char *getEngineId() const override {
@@ -155,19 +155,19 @@ static const ADFileBasedFallback fileBasedFallback[] = {
 	{ 0, { 0 } }
 };
 
-ADDetectedGame CGEMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
+ADDetectedGame CGEMetaEngineStatic::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	ADDetectedGame game = detectGameFilebased(allFiles, CGE::fileBasedFallback);
 
 	if (!game.desc)
 		return ADDetectedGame();
 
-	SearchMan.addDirectory("CGEMetaEngine::fallbackDetect", fslist.begin()->getParent());
+	SearchMan.addDirectory("CGEMetaEngineStatic::fallbackDetect", fslist.begin()->getParent());
 	ResourceManager *resman;
 	resman = new ResourceManager();
 	bool sayFileFound = resman->exist("CGE.SAY");
 	delete resman;
 
-	SearchMan.remove("CGEMetaEngine::fallbackDetect");
+	SearchMan.remove("CGEMetaEngineStatic::fallbackDetect");
 
 	if (!sayFileFound)
 		return ADDetectedGame();
@@ -177,4 +177,4 @@ ADDetectedGame CGEMetaEngine::fallbackDetect(const FileMap &allFiles, const Comm
 
 } // End of namespace CGE
 
-REGISTER_PLUGIN_STATIC(CGE_DETECTION, PLUGIN_TYPE_METAENGINE, CGE::CGEMetaEngine);
+REGISTER_PLUGIN_STATIC(CGE_DETECTION, PLUGIN_TYPE_METAENGINE, CGE::CGEMetaEngineStatic);
diff --git a/engines/cge/metaengine.cpp b/engines/cge/metaengine.cpp
index b080e1b1ff..ae9a613c28 100644
--- a/engines/cge/metaengine.cpp
+++ b/engines/cge/metaengine.cpp
@@ -31,7 +31,7 @@
 
 namespace CGE {
 
-class CGEMetaEngineConnect : public AdvancedMetaEngineConnect {
+class CGEMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "cge";
@@ -47,7 +47,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool CGEMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool CGEMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -59,16 +59,16 @@ bool CGEMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSimpleSavesNames);
 }
 
-void CGEMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void CGEMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-int CGEMetaEngineConnect::getMaximumSaveSlot() const {
+int CGEMetaEngine::getMaximumSaveSlot() const {
 	return 99;
 }
 
-SaveStateList CGEMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList CGEMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -111,7 +111,7 @@ SaveStateList CGEMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor CGEMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor CGEMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
 
@@ -153,7 +153,7 @@ SaveStateDescriptor CGEMetaEngineConnect::querySaveMetaInfos(const char *target,
 	return SaveStateDescriptor();
 }
 
-bool CGEMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool CGEMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new CGE::CGEEngine(syst, desc);
 	}
@@ -163,7 +163,7 @@ bool CGEMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 } // End of namespace CGE
 
 #if PLUGIN_ENABLED_DYNAMIC(CGE)
-REGISTER_PLUGIN_DYNAMIC(CGE, PLUGIN_TYPE_ENGINE, CGE::CGEMetaEngineConnect);
+REGISTER_PLUGIN_DYNAMIC(CGE, PLUGIN_TYPE_ENGINE, CGE::CGEMetaEngine);
 #else
-REGISTER_PLUGIN_STATIC(CGE, PLUGIN_TYPE_ENGINE, CGE::CGEMetaEngineConnect);
+REGISTER_PLUGIN_STATIC(CGE, PLUGIN_TYPE_ENGINE, CGE::CGEMetaEngine);
 #endif
diff --git a/engines/cge2/detection.cpp b/engines/cge2/detection.cpp
index 9807efad9b..ddf6ee8bfd 100644
--- a/engines/cge2/detection.cpp
+++ b/engines/cge2/detection.cpp
@@ -116,9 +116,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 		AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class CGE2MetaEngine : public AdvancedMetaEngine {
+class CGE2MetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	CGE2MetaEngine() : AdvancedMetaEngine(gameDescriptions, sizeof(ADGameDescription), CGE2Games, optionsList) {
+	CGE2MetaEngineStatic() : AdvancedMetaEngineStatic(gameDescriptions, sizeof(ADGameDescription), CGE2Games, optionsList) {
 	}
 
 	const char *getEngineId() const override {
@@ -153,19 +153,19 @@ static const ADFileBasedFallback fileBasedFallback[] = {
 
 // This fallback detection looks identical to the one used for CGE. In fact, the difference resides
 // in the ResourceManager which handles a different archive format. The rest of the detection is identical.
-ADDetectedGame CGE2MetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
+ADDetectedGame CGE2MetaEngineStatic::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	ADDetectedGame game = detectGameFilebased(allFiles, CGE2::fileBasedFallback);
 
 	if (!game.desc)
 		return ADDetectedGame();
 
-	SearchMan.addDirectory("CGE2MetaEngine::fallbackDetect", fslist.begin()->getParent());
+	SearchMan.addDirectory("CGE2MetaEngineStatic::fallbackDetect", fslist.begin()->getParent());
 	ResourceManager *resman;
 	resman = new ResourceManager();
 	bool sayFileFound = resman->exist("CGE.SAY");
 	delete resman;
 
-	SearchMan.remove("CGE2MetaEngine::fallbackDetect");
+	SearchMan.remove("CGE2MetaEngineStatic::fallbackDetect");
 
 	if (!sayFileFound)
 		return ADDetectedGame();
@@ -175,4 +175,4 @@ ADDetectedGame CGE2MetaEngine::fallbackDetect(const FileMap &allFiles, const Com
 
 } // End of namespace CGE2
 
-REGISTER_PLUGIN_STATIC(CGE2_DETECTION, PLUGIN_TYPE_METAENGINE, CGE2::CGE2MetaEngine);
+REGISTER_PLUGIN_STATIC(CGE2_DETECTION, PLUGIN_TYPE_METAENGINE, CGE2::CGE2MetaEngineStatic);
diff --git a/engines/cge2/metaengine.cpp b/engines/cge2/metaengine.cpp
index 31b2f63444..bd3cdf68d7 100644
--- a/engines/cge2/metaengine.cpp
+++ b/engines/cge2/metaengine.cpp
@@ -33,7 +33,7 @@
 
 namespace CGE2 {
 
-class CGE2MetaEngineConnect : public AdvancedMetaEngineConnect {
+class CGE2MetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "cge2";
@@ -47,14 +47,14 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool CGE2MetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool CGE2MetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc)
 		*engine = new CGE2::CGE2Engine(syst, desc);
 
 	return desc != 0;
 }
 
-bool CGE2MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool CGE2MetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsDeleteSave) ||
 		(f == kSavesSupportMetaInfo) ||
@@ -66,11 +66,11 @@ bool CGE2MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSimpleSavesNames);
 }
 
-int CGE2MetaEngineConnect::getMaximumSaveSlot() const {
+int CGE2MetaEngine::getMaximumSaveSlot() const {
 	return 99;
 }
 
-SaveStateList CGE2MetaEngineConnect::listSaves(const char *target) const {
+SaveStateList CGE2MetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -113,7 +113,7 @@ SaveStateList CGE2MetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor CGE2MetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor CGE2MetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
 
@@ -155,7 +155,7 @@ SaveStateDescriptor CGE2MetaEngineConnect::querySaveMetaInfos(const char *target
 	return SaveStateDescriptor();
 }
 
-void CGE2MetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void CGE2MetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
@@ -163,7 +163,7 @@ void CGE2MetaEngineConnect::removeSaveState(const char *target, int slot) const
 } // End of namespace CGE2
 
 #if PLUGIN_ENABLED_DYNAMIC(CGE2)
-	REGISTER_PLUGIN_DYNAMIC(CGE2, PLUGIN_TYPE_ENGINE, CGE2::CGE2MetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(CGE2, PLUGIN_TYPE_ENGINE, CGE2::CGE2MetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(CGE2, PLUGIN_TYPE_ENGINE, CGE2::CGE2MetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(CGE2, PLUGIN_TYPE_ENGINE, CGE2::CGE2MetaEngine);
 #endif
diff --git a/engines/chewy/detection.cpp b/engines/chewy/detection.cpp
index 17ed3f2b25..c816fae9ec 100644
--- a/engines/chewy/detection.cpp
+++ b/engines/chewy/detection.cpp
@@ -90,9 +90,9 @@ static const ChewyGameDescription gameDescriptions[] = {
 
 } // End of namespace Chewy
 
-class ChewyMetaEngine : public AdvancedMetaEngine {
+class ChewyMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	ChewyMetaEngine() : AdvancedMetaEngine(Chewy::gameDescriptions, sizeof(Chewy::ChewyGameDescription), chewyGames) {
+	ChewyMetaEngineStatic() : AdvancedMetaEngineStatic(Chewy::gameDescriptions, sizeof(Chewy::ChewyGameDescription), chewyGames) {
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -110,4 +110,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(CHEWY_DETECTION, PLUGIN_TYPE_METAENGINE, ChewyMetaEngine);
+REGISTER_PLUGIN_STATIC(CHEWY_DETECTION, PLUGIN_TYPE_METAENGINE, ChewyMetaEngineStatic);
diff --git a/engines/chewy/metaengine.cpp b/engines/chewy/metaengine.cpp
index bf14b79ebb..1be80fe05a 100644
--- a/engines/chewy/metaengine.cpp
+++ b/engines/chewy/metaengine.cpp
@@ -41,7 +41,7 @@ Common::Language ChewyEngine::getLanguage() const {
 
 } // End of namespace Chewy
 
-class ChewyMetaEngineConnect : public AdvancedMetaEngineConnect {
+class ChewyMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "chewy";
@@ -56,7 +56,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool ChewyMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool ChewyMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -74,7 +74,7 @@ bool Chewy::ChewyEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool ChewyMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool ChewyMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Chewy::ChewyGameDescription *gd = (const Chewy::ChewyGameDescription *)desc;
 	if (gd) {
 		*engine = new Chewy::ChewyEngine(syst, gd);
@@ -82,25 +82,25 @@ bool ChewyMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, cons
 	return gd != 0;
 }
 
-SaveStateList ChewyMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList ChewyMetaEngine::listSaves(const char *target) const {
 	SaveStateList saveList;
 
 	return saveList;
 }
 
-int ChewyMetaEngineConnect::getMaximumSaveSlot() const {
+int ChewyMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-void ChewyMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void ChewyMetaEngine::removeSaveState(const char *target, int slot) const {
 }
 
-SaveStateDescriptor ChewyMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor ChewyMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	return SaveStateDescriptor();
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(CHEWY)
-	REGISTER_PLUGIN_DYNAMIC(CHEWY, PLUGIN_TYPE_ENGINE, ChewyMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(CHEWY, PLUGIN_TYPE_ENGINE, ChewyMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(CHEWY, PLUGIN_TYPE_ENGINE, ChewyMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(CHEWY, PLUGIN_TYPE_ENGINE, ChewyMetaEngine);
 #endif
diff --git a/engines/cine/detection.cpp b/engines/cine/detection.cpp
index 7b183b6868..752d8c683b 100644
--- a/engines/cine/detection.cpp
+++ b/engines/cine/detection.cpp
@@ -59,9 +59,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class CineMetaEngine : public AdvancedMetaEngine {
+class CineMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	CineMetaEngine() : AdvancedMetaEngine(Cine::gameDescriptions, sizeof(Cine::CINEGameDescription), cineGames, optionsList) {
+	CineMetaEngineStatic() : AdvancedMetaEngineStatic(Cine::gameDescriptions, sizeof(Cine::CINEGameDescription), cineGames, optionsList) {
 		_guiOptions = GUIO3(GUIO_NOSPEECH, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_TRANSPARENT_DIALOG_BOXES);
 	}
 
@@ -78,4 +78,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(CINE_DETECTION, PLUGIN_TYPE_METAENGINE, CineMetaEngine);
+REGISTER_PLUGIN_STATIC(CINE_DETECTION, PLUGIN_TYPE_METAENGINE, CineMetaEngineStatic);
diff --git a/engines/cine/metaengine.cpp b/engines/cine/metaengine.cpp
index 12c2d0a7bc..60cd0fb1b7 100644
--- a/engines/cine/metaengine.cpp
+++ b/engines/cine/metaengine.cpp
@@ -48,14 +48,14 @@ Common::Platform CineEngine::getPlatform() const { return _gameDescription->desc
 
 } // End of namespace Cine
 
-class CineMetaEngineConnect : public AdvancedMetaEngineConnect {
+class CineMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "cine";
 	}
 
     Common::Error createInstance(OSystem *syst, Engine **engine) const override {
-		return AdvancedMetaEngineConnect::createInstance(syst, engine);
+		return AdvancedMetaEngine::createInstance(syst, engine);
 	}
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 
@@ -67,7 +67,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool CineMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool CineMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -86,7 +86,7 @@ bool Cine::CineEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool CineMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool CineMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Cine::CINEGameDescription *gd = (const Cine::CINEGameDescription *)desc;
 	if (gd) {
 		*engine = new Cine::CineEngine(syst, gd);
@@ -94,7 +94,7 @@ bool CineMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return gd != 0;
 }
 
-SaveStateList CineMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList CineMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	SaveStateList saveList;
 
@@ -170,13 +170,13 @@ SaveStateList CineMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int CineMetaEngineConnect::getMaximumSaveSlot() const { return MAX_SAVEGAMES - 1; }
+int CineMetaEngine::getMaximumSaveSlot() const { return MAX_SAVEGAMES - 1; }
 
-Common::String CineMetaEngineConnect::getSavegameFile(int saveGameIdx, const char *target) const {
+Common::String CineMetaEngine::getSavegameFile(int saveGameIdx, const char *target) const {
 	return Common::String::format("%s.%d", target == nullptr ? getEngineId() : target, saveGameIdx);
 }
 
-SaveStateDescriptor CineMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor CineMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	if (slot < 0 || slot > getMaximumSaveSlot()) {
 		// HACK: Try to make SaveLoadChooserGrid::open() not use save slot
 		// numbers over the maximum save slot number for "New save".
@@ -239,7 +239,7 @@ SaveStateDescriptor CineMetaEngineConnect::querySaveMetaInfos(const char *target
 	return SaveStateDescriptor();
 }
 
-void CineMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void CineMetaEngine::removeSaveState(const char *target, int slot) const {
 	if (slot < 0 || slot >= MAX_SAVEGAMES) {
 		return;
 	}
@@ -285,9 +285,9 @@ void CineMetaEngineConnect::removeSaveState(const char *target, int slot) const
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(CINE)
-	REGISTER_PLUGIN_DYNAMIC(CINE, PLUGIN_TYPE_ENGINE, CineMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(CINE, PLUGIN_TYPE_ENGINE, CineMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(CINE, PLUGIN_TYPE_ENGINE, CineMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(CINE, PLUGIN_TYPE_ENGINE, CineMetaEngine);
 #endif
 
 namespace Cine {
diff --git a/engines/cine/saveload.cpp b/engines/cine/saveload.cpp
index f5cd98cb7a..6b03f4fcd3 100644
--- a/engines/cine/saveload.cpp
+++ b/engines/cine/saveload.cpp
@@ -879,7 +879,7 @@ bool CineEngine::makeLoad(const Common::String &saveName) {
 		}
 
 		ExtendedSavegameHeader header;
-		if (MetaEngineConnect::readSavegameHeader(saveFile.get(), &header)) {
+		if (MetaEngine::readSavegameHeader(saveFile.get(), &header)) {
 			setTotalPlayTime(header.playtime * 1000); // Seconds to milliseconds
 		}
 	}
@@ -1030,7 +1030,7 @@ void CineEngine::makeSave(const Common::String &saveFileName, uint32 playtime,
 		renderer->popSavedBackBuffer(BEFORE_OPENING_MENU);
 	}
 
-	MetaEngineConnect::appendExtendedSave(fHandle.get(), playtime, desc, isAutosave);
+	MetaEngine::appendExtendedSave(fHandle.get(), playtime, desc, isAutosave);
 
 	renderer->restoreSavedBackBuffer(BEFORE_TAKING_THUMBNAIL);
 
diff --git a/engines/composer/detection.cpp b/engines/composer/detection.cpp
index 57cc9bcbbd..087d2a29bf 100644
--- a/engines/composer/detection.cpp
+++ b/engines/composer/detection.cpp
@@ -52,9 +52,9 @@ static const char *directoryGlobs[] = {
 	0
 };
 
-class ComposerMetaEngine : public AdvancedMetaEngine {
+class ComposerMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	ComposerMetaEngine() : AdvancedMetaEngine(Composer::gameDescriptions, sizeof(Composer::ComposerGameDescription), composerGames) {
+	ComposerMetaEngineStatic() : AdvancedMetaEngineStatic(Composer::gameDescriptions, sizeof(Composer::ComposerGameDescription), composerGames) {
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -72,4 +72,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(COMPOSER_DETECTION, PLUGIN_TYPE_METAENGINE, ComposerMetaEngine);
+REGISTER_PLUGIN_STATIC(COMPOSER_DETECTION, PLUGIN_TYPE_METAENGINE, ComposerMetaEngineStatic);
diff --git a/engines/composer/metaengine.cpp b/engines/composer/metaengine.cpp
index bb70d1bdc4..8c7511dc69 100644
--- a/engines/composer/metaengine.cpp
+++ b/engines/composer/metaengine.cpp
@@ -65,7 +65,7 @@ bool ComposerEngine::loadDetectedConfigFile(Common::INIFile &configFile) const {
 
 } // End of namespace Composer
 
-class ComposerMetaEngineConnect : public AdvancedMetaEngineConnect {
+class ComposerMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "composer";
@@ -78,7 +78,7 @@ public:
 	SaveStateList listSaves(const char* target) const override;
 };
 
-bool ComposerMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool ComposerMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Composer::ComposerGameDescription *gd = (const Composer::ComposerGameDescription *)desc;
 	if (gd) {
 		*engine = new Composer::ComposerEngine(syst, gd);
@@ -86,7 +86,7 @@ bool ComposerMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, c
 	return gd != 0;
 }
 
-bool ComposerMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool ComposerMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return ((f == kSupportsListSaves) || (f == kSupportsLoadingDuringStartup));
 }
 
@@ -99,10 +99,10 @@ Common::String getSaveName(Common::InSaveFile *in) {
 	ser.syncString(name);
 	return name;
 }
-int ComposerMetaEngineConnect::getMaximumSaveSlot() const {
+int ComposerMetaEngine::getMaximumSaveSlot() const {
 	return 99;
 }
-SaveStateList ComposerMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList ComposerMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -136,7 +136,7 @@ bool Composer::ComposerEngine::hasFeature(EngineFeature f) const {
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(COMPOSER)
-	REGISTER_PLUGIN_DYNAMIC(COMPOSER, PLUGIN_TYPE_ENGINE, ComposerMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(COMPOSER, PLUGIN_TYPE_ENGINE, ComposerMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(COMPOSER, PLUGIN_TYPE_ENGINE, ComposerMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(COMPOSER, PLUGIN_TYPE_ENGINE, ComposerMetaEngine);
 #endif
diff --git a/engines/cruise/detection.cpp b/engines/cruise/detection.cpp
index b47cdb59ee..dddd524fee 100644
--- a/engines/cruise/detection.cpp
+++ b/engines/cruise/detection.cpp
@@ -170,9 +170,9 @@ static const CRUISEGameDescription gameDescriptions[] = {
 
 }
 
-class CruiseMetaEngine : public AdvancedMetaEngine {
+class CruiseMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	CruiseMetaEngine() : AdvancedMetaEngine(Cruise::gameDescriptions, sizeof(Cruise::CRUISEGameDescription), cruiseGames) {
+	CruiseMetaEngineStatic() : AdvancedMetaEngineStatic(Cruise::gameDescriptions, sizeof(Cruise::CRUISEGameDescription), cruiseGames) {
 		_guiOptions = GUIO2(GUIO_NOSPEECH, GUIO_NOMIDI);
 	}
 
@@ -189,4 +189,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(CRUISE_DETECTION, PLUGIN_TYPE_METAENGINE, CruiseMetaEngine);
+REGISTER_PLUGIN_STATIC(CRUISE_DETECTION, PLUGIN_TYPE_METAENGINE, CruiseMetaEngineStatic);
diff --git a/engines/cruise/metaengine.cpp b/engines/cruise/metaengine.cpp
index 83abf985fe..5224d3bad1 100644
--- a/engines/cruise/metaengine.cpp
+++ b/engines/cruise/metaengine.cpp
@@ -44,7 +44,7 @@ Common::Platform CruiseEngine::getPlatform() const {
 
 } // End of namespace Cruise
 
-class CruiseMetaEngineConnect : public AdvancedMetaEngineConnect {
+class CruiseMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "cruise";
@@ -59,7 +59,7 @@ public:
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool CruiseMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool CruiseMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave) ||
@@ -68,7 +68,7 @@ bool CruiseMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSupportsLoadingDuringStartup);
 }
 
-SaveStateList CruiseMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList CruiseMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern("cruise.s##");
@@ -96,11 +96,11 @@ SaveStateList CruiseMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void CruiseMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void CruiseMetaEngine::removeSaveState(const char *target, int slot) const {
 	g_system->getSavefileManager()->removeSavefile(Cruise::CruiseEngine::getSavegameFile(slot));
 }
 
-SaveStateDescriptor CruiseMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor CruiseMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(
 		Cruise::CruiseEngine::getSavegameFile(slot));
 
@@ -123,7 +123,7 @@ SaveStateDescriptor CruiseMetaEngineConnect::querySaveMetaInfos(const char *targ
 	return SaveStateDescriptor();
 }
 
-bool CruiseMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool CruiseMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Cruise::CRUISEGameDescription *gd = (const Cruise::CRUISEGameDescription *)desc;
 	if (gd) {
 		*engine = new Cruise::CruiseEngine(syst, gd);
@@ -132,7 +132,7 @@ bool CruiseMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, con
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(CRUISE)
-	REGISTER_PLUGIN_DYNAMIC(CRUISE, PLUGIN_TYPE_ENGINE, CruiseMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(CRUISE, PLUGIN_TYPE_ENGINE, CruiseMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(CRUISE, PLUGIN_TYPE_ENGINE, CruiseMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(CRUISE, PLUGIN_TYPE_ENGINE, CruiseMetaEngine);
 #endif
diff --git a/engines/cryo/detection.cpp b/engines/cryo/detection.cpp
index 37b1d60a08..cfff60604b 100644
--- a/engines/cryo/detection.cpp
+++ b/engines/cryo/detection.cpp
@@ -119,9 +119,9 @@ static const ADGameDescription gameDescriptions[] = {
 
 } // End of namespace Cryo
 
-class CryoMetaEngine : public AdvancedMetaEngine {
+class CryoMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	CryoMetaEngine() : AdvancedMetaEngine(Cryo::gameDescriptions, sizeof(ADGameDescription), cryoGames) {
+	CryoMetaEngineStatic() : AdvancedMetaEngineStatic(Cryo::gameDescriptions, sizeof(ADGameDescription), cryoGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -137,4 +137,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(CRYO_DETECTION, PLUGIN_TYPE_METAENGINE, CryoMetaEngine);
+REGISTER_PLUGIN_STATIC(CRYO_DETECTION, PLUGIN_TYPE_METAENGINE, CryoMetaEngineStatic);
diff --git a/engines/cryo/metaengine.cpp b/engines/cryo/metaengine.cpp
index 428b41d1c3..47a7bd1a2d 100644
--- a/engines/cryo/metaengine.cpp
+++ b/engines/cryo/metaengine.cpp
@@ -35,7 +35,7 @@ Common::Platform CryoEngine::getPlatform() const { return _gameDescription->plat
 
 } // End of namespace Cryo
 
-class CryoMetaEngineConnect : public AdvancedMetaEngineConnect {
+class CryoMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "cryo";
@@ -45,11 +45,11 @@ public:
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool CryoMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool CryoMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return false;
 }
 
-bool CryoMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool CryoMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Cryo::CryoEngine(syst, desc);
 	}
@@ -57,8 +57,8 @@ bool CryoMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(CRYO)
-	REGISTER_PLUGIN_DYNAMIC(CRYO, PLUGIN_TYPE_ENGINE, CryoMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(CRYO, PLUGIN_TYPE_ENGINE, CryoMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(CRYO, PLUGIN_TYPE_ENGINE, CryoMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(CRYO, PLUGIN_TYPE_ENGINE, CryoMetaEngine);
 #endif
 
diff --git a/engines/cryomni3d/detection.cpp b/engines/cryomni3d/detection.cpp
index 054af4dbae..c8a50c159e 100644
--- a/engines/cryomni3d/detection.cpp
+++ b/engines/cryomni3d/detection.cpp
@@ -46,9 +46,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class CryOmni3DMetaEngine : public AdvancedMetaEngine {
+class CryOmni3DMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	CryOmni3DMetaEngine() : AdvancedMetaEngine(CryOmni3D::gameDescriptions,
+	CryOmni3DMetaEngineStatic() : AdvancedMetaEngineStatic(CryOmni3D::gameDescriptions,
 				sizeof(CryOmni3DGameDescription), cryomni3DGames, optionsList) {
 		_directoryGlobs = directoryGlobs;
 		_maxScanDepth = 5;
@@ -74,4 +74,4 @@ public:
 
 } // End of Namespace CryOmni3D
 
-REGISTER_PLUGIN_STATIC(CRYOMNI3D_DETECTION, PLUGIN_TYPE_METAENGINE, CryOmni3D::CryOmni3DMetaEngine);
+REGISTER_PLUGIN_STATIC(CRYOMNI3D_DETECTION, PLUGIN_TYPE_METAENGINE, CryOmni3D::CryOmni3DMetaEngineStatic);
diff --git a/engines/cryomni3d/metaengine.cpp b/engines/cryomni3d/metaengine.cpp
index edf688c661..42f830aecb 100644
--- a/engines/cryomni3d/metaengine.cpp
+++ b/engines/cryomni3d/metaengine.cpp
@@ -67,7 +67,7 @@ bool CryOmni3DEngine::hasFeature(EngineFeature f) const {
 }
 
 
-class CryOmni3DMetaEngineConnect : public AdvancedMetaEngineConnect {
+class CryOmni3DMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "cryomni3d";
@@ -81,7 +81,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool CryOmni3DMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool CryOmni3DMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves)
 		|| (f == kSupportsLoadingDuringStartup)
@@ -89,7 +89,7 @@ bool CryOmni3DMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		|| (f == kSimpleSavesNames);
 }
 
-SaveStateList CryOmni3DMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList CryOmni3DMetaEngine::listSaves(const char *target) const {
 	// Replicate constant here to shorten lines
 	static const uint kSaveDescriptionLen = CryOmni3DEngine::kSaveDescriptionLen;
 	SaveStateList saveList;
@@ -123,13 +123,13 @@ SaveStateList CryOmni3DMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void CryOmni3DMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void CryOmni3DMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%04d", target, slot + 1);
 
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-bool CryOmni3DMetaEngineConnect::createInstance(OSystem *syst, Engine **engine,
+bool CryOmni3DMetaEngine::createInstance(OSystem *syst, Engine **engine,
 		const ADGameDescription *desc) const {
 	const CryOmni3DGameDescription *gd = (const CryOmni3DGameDescription *)desc;
 
@@ -154,7 +154,7 @@ bool CryOmni3DMetaEngineConnect::createInstance(OSystem *syst, Engine **engine,
 } // End of namespace CryOmni3D
 
 #if PLUGIN_ENABLED_DYNAMIC(CRYOMNI3D)
-	REGISTER_PLUGIN_DYNAMIC(CRYOMNI3D, PLUGIN_TYPE_ENGINE, CryOmni3D::CryOmni3DMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(CRYOMNI3D, PLUGIN_TYPE_ENGINE, CryOmni3D::CryOmni3DMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(CRYOMNI3D, PLUGIN_TYPE_ENGINE, CryOmni3D::CryOmni3DMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(CRYOMNI3D, PLUGIN_TYPE_ENGINE, CryOmni3D::CryOmni3DMetaEngine);
 #endif
diff --git a/engines/director/detection.cpp b/engines/director/detection.cpp
index 6f4bce2f79..81de4e99db 100644
--- a/engines/director/detection.cpp
+++ b/engines/director/detection.cpp
@@ -174,9 +174,9 @@ static const char *directoryGlobs[] = {
 	0
 };
 
-class DirectorMetaEngine : public AdvancedMetaEngine {
+class DirectorMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	DirectorMetaEngine() : AdvancedMetaEngine(Director::gameDescriptions, sizeof(Director::DirectorGameDescription), directorGames) {
+	DirectorMetaEngineStatic() : AdvancedMetaEngineStatic(Director::gameDescriptions, sizeof(Director::DirectorGameDescription), directorGames) {
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -213,7 +213,7 @@ static Director::DirectorGameDescription s_fallbackDesc = {
 static char s_fallbackFileNameBuffer[51];
 static char s_fallbackExtraBuf[256];
 
-ADDetectedGame DirectorMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
+ADDetectedGame DirectorMetaEngineStatic::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	// TODO: Handle Mac fallback
 
 	// reset fallback description
@@ -321,4 +321,4 @@ ADDetectedGame DirectorMetaEngine::fallbackDetect(const FileMap &allFiles, const
 	return ADDetectedGame();
 }
 
-REGISTER_PLUGIN_STATIC(DIRECTOR_DETECTION, PLUGIN_TYPE_METAENGINE, DirectorMetaEngine);
+REGISTER_PLUGIN_STATIC(DIRECTOR_DETECTION, PLUGIN_TYPE_METAENGINE, DirectorMetaEngineStatic);
diff --git a/engines/director/metaengine.cpp b/engines/director/metaengine.cpp
index 15f4313e56..9f545fcec9 100644
--- a/engines/director/metaengine.cpp
+++ b/engines/director/metaengine.cpp
@@ -86,7 +86,7 @@ bool DirectorEngine::hasFeature(EngineFeature f) const {
 
 } // End of Namespace Director
 
-class DirectorMetaEngineConnect : public AdvancedMetaEngineConnect {
+class DirectorMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "director";
@@ -95,7 +95,7 @@ public:
     bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool DirectorMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool DirectorMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Director::DirectorGameDescription *gd = (const Director::DirectorGameDescription *)desc;
 
 	if (gd)
@@ -105,7 +105,7 @@ bool DirectorMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, c
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(DIRECTOR)
-	REGISTER_PLUGIN_DYNAMIC(DIRECTOR, PLUGIN_TYPE_ENGINE, DirectorMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(DIRECTOR, PLUGIN_TYPE_ENGINE, DirectorMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(DIRECTOR, PLUGIN_TYPE_ENGINE, DirectorMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(DIRECTOR, PLUGIN_TYPE_ENGINE, DirectorMetaEngine);
 #endif
diff --git a/engines/dm/detection.cpp b/engines/dm/detection.cpp
index 0a36556b1f..d6087b3f18 100644
--- a/engines/dm/detection.cpp
+++ b/engines/dm/detection.cpp
@@ -92,9 +92,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class DMMetaEngine : public AdvancedMetaEngine {
+class DMMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	DMMetaEngine() : AdvancedMetaEngine(DM::gameDescriptions, sizeof(DMADGameDescription), DMGames, optionsList) {
+	DMMetaEngineStatic() : AdvancedMetaEngineStatic(DM::gameDescriptions, sizeof(DMADGameDescription), DMGames, optionsList) {
 	}
 
 	const char *getEngineId() const override {
@@ -114,4 +114,4 @@ public:
 
 } // End of namespace DM
 
-REGISTER_PLUGIN_STATIC(DM_DETECTION, PLUGIN_TYPE_METAENGINE, DM::DMMetaEngine);
+REGISTER_PLUGIN_STATIC(DM_DETECTION, PLUGIN_TYPE_METAENGINE, DM::DMMetaEngineStatic);
diff --git a/engines/dm/metaengine.cpp b/engines/dm/metaengine.cpp
index 853034313c..25f585c2d3 100644
--- a/engines/dm/metaengine.cpp
+++ b/engines/dm/metaengine.cpp
@@ -36,7 +36,7 @@
 
 namespace DM {
 
-class DMMetaEngineConnect : public AdvancedMetaEngineConnect {
+class DMMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "dm";
@@ -116,7 +116,7 @@ public:
 } // End of namespace DM
 
 #if PLUGIN_ENABLED_DYNAMIC(DM)
-	REGISTER_PLUGIN_DYNAMIC(DM, PLUGIN_TYPE_ENGINE, DM::DMMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(DM, PLUGIN_TYPE_ENGINE, DM::DMMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(DM, PLUGIN_TYPE_ENGINE, DM::DMMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(DM, PLUGIN_TYPE_ENGINE, DM::DMMetaEngine);
 #endif
diff --git a/engines/draci/detection.cpp b/engines/draci/detection.cpp
index d34cbf3ba2..4aad4a70d9 100644
--- a/engines/draci/detection.cpp
+++ b/engines/draci/detection.cpp
@@ -78,9 +78,9 @@ const ADGameDescription gameDescriptions[] = {
 
 } // End of namespace Draci
 
-class DraciMetaEngine : public AdvancedMetaEngine {
+class DraciMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	DraciMetaEngine() : AdvancedMetaEngine(Draci::gameDescriptions, sizeof(ADGameDescription), draciGames) {
+	DraciMetaEngineStatic() : AdvancedMetaEngineStatic(Draci::gameDescriptions, sizeof(ADGameDescription), draciGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -96,4 +96,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(DRACI_DETECTION, PLUGIN_TYPE_METAENGINE, DraciMetaEngine);
+REGISTER_PLUGIN_STATIC(DRACI_DETECTION, PLUGIN_TYPE_METAENGINE, DraciMetaEngineStatic);
diff --git a/engines/draci/metaengine.cpp b/engines/draci/metaengine.cpp
index 1a2bfdfb80..f211037d58 100644
--- a/engines/draci/metaengine.cpp
+++ b/engines/draci/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "engines/advancedDetector.h"
 #include "engines/metaengine.h"
 
-class DraciMetaEngineConnect : public AdvancedMetaEngineConnect {
+class DraciMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "draci";
@@ -42,7 +42,7 @@ public:
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool DraciMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool DraciMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave) ||
@@ -53,7 +53,7 @@ bool DraciMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSupportsLoadingDuringStartup);
 }
 
-SaveStateList DraciMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList DraciMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern("draci.s##");
@@ -82,11 +82,11 @@ SaveStateList DraciMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void DraciMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void DraciMetaEngine::removeSaveState(const char *target, int slot) const {
 	g_system->getSavefileManager()->removeSavefile(Draci::DraciEngine::getSavegameFile(slot));
 }
 
-SaveStateDescriptor DraciMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor DraciMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(
 		Draci::DraciEngine::getSavegameFile(slot));
 
@@ -120,7 +120,7 @@ SaveStateDescriptor DraciMetaEngineConnect::querySaveMetaInfos(const char *targe
 	return SaveStateDescriptor();
 }
 
-bool DraciMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool DraciMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Draci::DraciEngine(syst, desc);
 	}
@@ -128,7 +128,7 @@ bool DraciMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, cons
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(DRACI)
-	REGISTER_PLUGIN_DYNAMIC(DRACI, PLUGIN_TYPE_ENGINE, DraciMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(DRACI, PLUGIN_TYPE_ENGINE, DraciMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(DRACI, PLUGIN_TYPE_ENGINE, DraciMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(DRACI, PLUGIN_TYPE_ENGINE, DraciMetaEngine);
 #endif
diff --git a/engines/dragons/detection.cpp b/engines/dragons/detection.cpp
index 7356a4b0d8..d8eafd0d0a 100644
--- a/engines/dragons/detection.cpp
+++ b/engines/dragons/detection.cpp
@@ -123,9 +123,9 @@ static const char * const directoryGlobs[] = {
 	0
 };
 
-class DragonsMetaEngine : public AdvancedMetaEngine {
+class DragonsMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	DragonsMetaEngine() : AdvancedMetaEngine(Dragons::gameDescriptions, sizeof(Dragons::DragonsGameDescription), dragonsGames) {
+	DragonsMetaEngineStatic() : AdvancedMetaEngineStatic(Dragons::gameDescriptions, sizeof(Dragons::DragonsGameDescription), dragonsGames) {
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -143,4 +143,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(DRAGONS_DETECTION, PLUGIN_TYPE_METAENGINE, DragonsMetaEngine);
+REGISTER_PLUGIN_STATIC(DRAGONS_DETECTION, PLUGIN_TYPE_METAENGINE, DragonsMetaEngineStatic);
diff --git a/engines/dragons/metaengine.cpp b/engines/dragons/metaengine.cpp
index d8d3ef7066..f372c7996d 100644
--- a/engines/dragons/metaengine.cpp
+++ b/engines/dragons/metaengine.cpp
@@ -31,7 +31,7 @@
 #include "base/plugins.h"
 #include "graphics/thumbnail.h"
 
-class DragonsMetaEngineConnect : public AdvancedMetaEngineConnect {
+class DragonsMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const {
 		return "dragons";
@@ -46,7 +46,7 @@ public:
 	Common::KeymapArray initKeymaps(const char *target) const override;
 };
 
-bool DragonsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool DragonsMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 			(f == kSupportsListSaves) ||
 			(f == kSupportsDeleteSave) ||
@@ -56,16 +56,16 @@ bool DragonsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 			(f == kSavesSupportCreationDate);
 }
 
-void DragonsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void DragonsMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-int DragonsMetaEngineConnect::getMaximumSaveSlot() const {
+int DragonsMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-SaveStateList DragonsMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList DragonsMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Dragons::SaveHeader header;
 	Common::String pattern = target;
@@ -90,7 +90,7 @@ SaveStateList DragonsMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor DragonsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor DragonsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Dragons::DragonsEngine::getSavegameFilename(target, slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
 	if (in) {
@@ -113,7 +113,7 @@ SaveStateDescriptor DragonsMetaEngineConnect::querySaveMetaInfos(const char *tar
 	return SaveStateDescriptor();
 }
 
-bool DragonsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool DragonsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Dragons::DragonsGameDescription *gd = (const Dragons::DragonsGameDescription *)desc;
 	if (gd) {
 		switch (gd->gameId) {
@@ -132,7 +132,7 @@ bool DragonsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, co
 	return desc != 0;
 }
 
-Common::KeymapArray DragonsMetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray DragonsMetaEngine::initKeymaps(const char *target) const {
 	using namespace Common;
 
 	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "dragons", "Blazing Dragons");
@@ -236,7 +236,7 @@ Common::KeymapArray DragonsMetaEngineConnect::initKeymaps(const char *target) co
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(DRAGONS)
-	REGISTER_PLUGIN_DYNAMIC(DRAGONS, PLUGIN_TYPE_ENGINE, DragonsMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(DRAGONS, PLUGIN_TYPE_ENGINE, DragonsMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(DRAGONS, PLUGIN_TYPE_ENGINE, DragonsMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(DRAGONS, PLUGIN_TYPE_ENGINE, DragonsMetaEngine);
 #endif
diff --git a/engines/drascula/detection.cpp b/engines/drascula/detection.cpp
index 98a4f7c5e1..1eb8468d7d 100644
--- a/engines/drascula/detection.cpp
+++ b/engines/drascula/detection.cpp
@@ -302,9 +302,9 @@ static const ExtraGuiOption drasculaExtraGuiOption = {
 	false
 };
 
-class DrasculaMetaEngine : public AdvancedMetaEngine {
+class DrasculaMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	DrasculaMetaEngine() : AdvancedMetaEngine(Drascula::gameDescriptions, sizeof(Drascula::DrasculaGameDescription), drasculaGames) {
+	DrasculaMetaEngineStatic() : AdvancedMetaEngineStatic(Drascula::gameDescriptions, sizeof(Drascula::DrasculaGameDescription), drasculaGames) {
 		_guiOptions = GUIO1(GUIO_NOMIDI);
 	}
 
@@ -323,7 +323,7 @@ public:
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
 };
 
-const ExtraGuiOptions DrasculaMetaEngine::getExtraGuiOptions(const Common::String &target) const {
+const ExtraGuiOptions DrasculaMetaEngineStatic::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	options.push_back(drasculaExtraGuiOption);
 	return options;
@@ -331,4 +331,4 @@ const ExtraGuiOptions DrasculaMetaEngine::getExtraGuiOptions(const Common::Strin
 
 } // End of namespace Drascula
 
-REGISTER_PLUGIN_STATIC(DRASCULA_DETECTION, PLUGIN_TYPE_METAENGINE, Drascula::DrasculaMetaEngine);
+REGISTER_PLUGIN_STATIC(DRASCULA_DETECTION, PLUGIN_TYPE_METAENGINE, Drascula::DrasculaMetaEngineStatic);
diff --git a/engines/drascula/metaengine.cpp b/engines/drascula/metaengine.cpp
index ec732a512b..1495ae7176 100644
--- a/engines/drascula/metaengine.cpp
+++ b/engines/drascula/metaengine.cpp
@@ -58,7 +58,7 @@ namespace Drascula {
 
 SaveStateDescriptor loadMetaData(Common::ReadStream *s, int slot, bool setPlayTime);
 
-class DrasculaMetaEngineConnect : public AdvancedMetaEngineConnect {
+class DrasculaMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "drascula";
@@ -73,7 +73,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool DrasculaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool DrasculaMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -85,7 +85,7 @@ bool DrasculaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSimpleSavesNames);
 }
 
-SaveStateList DrasculaMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList DrasculaMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -119,7 +119,7 @@ SaveStateList DrasculaMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor DrasculaMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor DrasculaMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
@@ -150,14 +150,14 @@ SaveStateDescriptor DrasculaMetaEngineConnect::querySaveMetaInfos(const char *ta
 	return desc;
 }
 
-int DrasculaMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+int DrasculaMetaEngine::getMaximumSaveSlot() const { return 999; }
 
-void DrasculaMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void DrasculaMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-bool DrasculaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool DrasculaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Drascula::DrasculaGameDescription *gd = (const Drascula::DrasculaGameDescription *)desc;
 	if (gd) {
 		*engine = new Drascula::DrasculaEngine(syst, gd);
@@ -168,7 +168,7 @@ bool DrasculaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, c
 } // End of namespace Drascula
 
 #if PLUGIN_ENABLED_DYNAMIC(DRASCULA)
-	REGISTER_PLUGIN_DYNAMIC(DRASCULA, PLUGIN_TYPE_ENGINE, Drascula::DrasculaMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(DRASCULA, PLUGIN_TYPE_ENGINE, Drascula::DrasculaMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(DRASCULA, PLUGIN_TYPE_ENGINE, Drascula::DrasculaMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(DRASCULA, PLUGIN_TYPE_ENGINE, Drascula::DrasculaMetaEngine);
 #endif
diff --git a/engines/dreamweb/detection.cpp b/engines/dreamweb/detection.cpp
index 19e9a502a1..4da74dc059 100644
--- a/engines/dreamweb/detection.cpp
+++ b/engines/dreamweb/detection.cpp
@@ -61,10 +61,10 @@ static const ADExtraGuiOptionsMap gameGuiOptions[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class DreamWebMetaEngine : public AdvancedMetaEngine {
+class DreamWebMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	DreamWebMetaEngine():
-	AdvancedMetaEngine(DreamWeb::gameDescriptions,
+	DreamWebMetaEngineStatic():
+	AdvancedMetaEngineStatic(DreamWeb::gameDescriptions,
 	sizeof(DreamWeb::DreamWebGameDescription), dreamWebGames,
 	gameGuiOptions) {
 		_guiOptions = GUIO1(GUIO_NOMIDI);
@@ -83,4 +83,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(DREAMWEB_DETECTION, PLUGIN_TYPE_METAENGINE, DreamWebMetaEngine);
+REGISTER_PLUGIN_STATIC(DREAMWEB_DETECTION, PLUGIN_TYPE_METAENGINE, DreamWebMetaEngineStatic);
diff --git a/engines/dreamweb/metaengine.cpp b/engines/dreamweb/metaengine.cpp
index 1d7a1c213f..576d34378f 100644
--- a/engines/dreamweb/metaengine.cpp
+++ b/engines/dreamweb/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "dreamweb/dreamweb.h"
 #include "dreamweb/detection.h"
 
-class DreamWebMetaEngineConnect : public AdvancedMetaEngineConnect {
+class DreamWebMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "dreamweb";
@@ -45,7 +45,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool DreamWebMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool DreamWebMetaEngine::hasFeature(MetaEngineFeature f) const {
 	switch(f) {
 	case kSupportsListSaves:
 	case kSupportsLoadingDuringStartup:
@@ -71,7 +71,7 @@ bool DreamWeb::DreamWebEngine::hasFeature(EngineFeature f) const {
 	}
 }
 
-bool DreamWebMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool DreamWebMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const DreamWeb::DreamWebGameDescription *gd = (const DreamWeb::DreamWebGameDescription *)desc;
 	if (gd) {
 		*engine = new DreamWeb::DreamWebEngine(syst, gd);
@@ -79,7 +79,7 @@ bool DreamWebMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, c
 	return gd != 0;
 }
 
-SaveStateList DreamWebMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList DreamWebMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray files = saveFileMan->listSavefiles("DREAMWEB.D##");
 
@@ -104,14 +104,14 @@ SaveStateList DreamWebMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int DreamWebMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+int DreamWebMetaEngine::getMaximumSaveSlot() const { return 99; }
 
-void DreamWebMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void DreamWebMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("DREAMWEB.D%02d", slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-SaveStateDescriptor DreamWebMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor DreamWebMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("DREAMWEB.D%02d", slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
 
@@ -178,9 +178,9 @@ SaveStateDescriptor DreamWebMetaEngineConnect::querySaveMetaInfos(const char *ta
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(DREAMWEB)
-	REGISTER_PLUGIN_DYNAMIC(DREAMWEB, PLUGIN_TYPE_ENGINE, DreamWebMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(DREAMWEB, PLUGIN_TYPE_ENGINE, DreamWebMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(DREAMWEB, PLUGIN_TYPE_ENGINE, DreamWebMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(DREAMWEB, PLUGIN_TYPE_ENGINE, DreamWebMetaEngine);
 #endif
 
 namespace DreamWeb {
diff --git a/engines/fullpipe/detection.cpp b/engines/fullpipe/detection.cpp
index a73cc08cae..6473ca227c 100644
--- a/engines/fullpipe/detection.cpp
+++ b/engines/fullpipe/detection.cpp
@@ -106,9 +106,9 @@ static const ADGameDescription gameDescriptions[] = {
 
 } // End of namespace Fullpipe
 
-class FullpipeMetaEngine : public AdvancedMetaEngine {
+class FullpipeMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	FullpipeMetaEngine() : AdvancedMetaEngine(Fullpipe::gameDescriptions, sizeof(ADGameDescription), fullpipeGames) {
+	FullpipeMetaEngineStatic() : AdvancedMetaEngineStatic(Fullpipe::gameDescriptions, sizeof(ADGameDescription), fullpipeGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -124,4 +124,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(FULLPIPE_DETECTION, PLUGIN_TYPE_METAENGINE, FullpipeMetaEngine);
+REGISTER_PLUGIN_STATIC(FULLPIPE_DETECTION, PLUGIN_TYPE_METAENGINE, FullpipeMetaEngineStatic);
diff --git a/engines/fullpipe/metaengine.cpp b/engines/fullpipe/metaengine.cpp
index b230912a70..0b2970bed2 100644
--- a/engines/fullpipe/metaengine.cpp
+++ b/engines/fullpipe/metaengine.cpp
@@ -46,7 +46,7 @@ Common::Language FullpipeEngine::getLanguage() const {
 
 } // End of namspace Fullpipe
 
-class FullpipeMetaEngineConnect : public AdvancedMetaEngineConnect {
+class FullpipeMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "fullpipe";
@@ -62,7 +62,7 @@ public:
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool FullpipeMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool FullpipeMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave) ||
@@ -81,7 +81,7 @@ bool Fullpipe::FullpipeEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-SaveStateList FullpipeMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList FullpipeMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern("fullpipe.s##");
@@ -117,11 +117,11 @@ SaveStateList FullpipeMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void FullpipeMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void FullpipeMetaEngine::removeSaveState(const char *target, int slot) const {
 	g_system->getSavefileManager()->removeSavefile(Fullpipe::getSavegameFile(slot));
 }
 
-SaveStateDescriptor FullpipeMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor FullpipeMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(
 		Fullpipe::getSavegameFile(slot)));
 
@@ -145,7 +145,7 @@ SaveStateDescriptor FullpipeMetaEngineConnect::querySaveMetaInfos(const char *ta
 	return SaveStateDescriptor();
 }
 
-bool FullpipeMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool FullpipeMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Fullpipe::FullpipeEngine(syst, desc);
 	}
@@ -153,7 +153,7 @@ bool FullpipeMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, c
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(FULLPIPE)
-	REGISTER_PLUGIN_DYNAMIC(FULLPIPE, PLUGIN_TYPE_ENGINE, FullpipeMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(FULLPIPE, PLUGIN_TYPE_ENGINE, FullpipeMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(FULLPIPE, PLUGIN_TYPE_ENGINE, FullpipeMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(FULLPIPE, PLUGIN_TYPE_ENGINE, FullpipeMetaEngine);
 #endif
diff --git a/engines/glk/detection.cpp b/engines/glk/detection.cpp
index eb081845ba..25d2d8e2c4 100644
--- a/engines/glk/detection.cpp
+++ b/engines/glk/detection.cpp
@@ -114,7 +114,7 @@ GlkDetectedGame::GlkDetectedGame(const char *id, const char *desc, const Common:
 
 } // End of namespace Glk
 
-PlainGameList GlkMetaEngine::getSupportedGames() const {
+PlainGameList GlkMetaEngineStatic::getSupportedGames() const {
 	PlainGameList list;
 	Glk::Adrift::AdriftMetaEngine::getSupportedGames(list);
 	Glk::AdvSys::AdvSysMetaEngine::getSupportedGames(list);
@@ -142,7 +142,7 @@ PlainGameList GlkMetaEngine::getSupportedGames() const {
 	Glk::GameDescriptor gd##SUBENGINE = Glk::SUBENGINE::SUBENGINE##MetaEngine::findGame(gameId); \
 	if (gd##SUBENGINE._description) return gd##SUBENGINE
 
-PlainGameDescriptor GlkMetaEngine::findGame(const char *gameId) const {
+PlainGameDescriptor GlkMetaEngineStatic::findGame(const char *gameId) const {
 	FIND_GAME(Adrift);
 	FIND_GAME(AdvSys);
 	FIND_GAME(Alan2);
@@ -167,7 +167,7 @@ PlainGameDescriptor GlkMetaEngine::findGame(const char *gameId) const {
 
 #undef FIND_GAME
 
-DetectedGames GlkMetaEngine::detectGames(const Common::FSList &fslist) const {
+DetectedGames GlkMetaEngineStatic::detectGames(const Common::FSList &fslist) const {
 	// This is as good a place as any to detect multiple sub-engines using the same Ids
 	detectClashes();
 
@@ -194,7 +194,7 @@ DetectedGames GlkMetaEngine::detectGames(const Common::FSList &fslist) const {
 	return detectedGames;
 }
 
-void GlkMetaEngine::detectClashes() const {
+void GlkMetaEngineStatic::detectClashes() const {
 	Common::StringMap map;
 	Glk::Adrift::AdriftMetaEngine::detectClashes(map);
 	Glk::AdvSys::AdvSysMetaEngine::detectClashes(map);
@@ -216,7 +216,7 @@ void GlkMetaEngine::detectClashes() const {
 #endif
 }
 
-const ExtraGuiOptions GlkMetaEngine::getExtraGuiOptions(const Common::String &) const {
+const ExtraGuiOptions GlkMetaEngineStatic::getExtraGuiOptions(const Common::String &) const {
 	ExtraGuiOptions  options;
 #if defined(USE_TTS)
 	static const ExtraGuiOption ttsSpeakOptions = {
@@ -237,4 +237,4 @@ const ExtraGuiOptions GlkMetaEngine::getExtraGuiOptions(const Common::String &)
 	return options;
 }
 
-REGISTER_PLUGIN_STATIC(GLK_DETECTION, PLUGIN_TYPE_METAENGINE, GlkMetaEngine);
+REGISTER_PLUGIN_STATIC(GLK_DETECTION, PLUGIN_TYPE_METAENGINE, GlkMetaEngineStatic);
diff --git a/engines/glk/detection.h b/engines/glk/detection.h
index e1e97e4001..30cd50db8d 100644
--- a/engines/glk/detection.h
+++ b/engines/glk/detection.h
@@ -29,9 +29,9 @@
 /**
  * ScummVM Meta Engine interface
  */
-class GlkMetaEngine : public MetaEngine {
+class GlkMetaEngineStatic : public MetaEngineStatic {
 public:
-	GlkMetaEngine() : MetaEngine() {}
+	GlkMetaEngineStatic() : MetaEngineStatic() {}
 
 	const char *getName() const override {
 		return "Glk";
diff --git a/engines/glk/metaengine.cpp b/engines/glk/metaengine.cpp
index b30b55a0a8..d73ad00c1b 100644
--- a/engines/glk/metaengine.cpp
+++ b/engines/glk/metaengine.cpp
@@ -73,7 +73,7 @@
 
 #define MAX_SAVES 99
 
-class GlkMetaEngineConnect : public MetaEngineConnect {
+class GlkMetaEngine : public MetaEngine {
 private:
 	Common::String findFileByGameId(const Common::String &gameId) const;
 public:
@@ -90,7 +90,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool GlkMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool GlkMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 	    (f == kSupportsLoadingDuringStartup) ||
@@ -138,14 +138,14 @@ template<class META, class ENG>bool create(OSystem *syst,
 	}
 }
 
-Common::String GlkMetaEngineConnect::findFileByGameId(const Common::String &gameId) const {
+Common::String GlkMetaEngine::findFileByGameId(const Common::String &gameId) const {
 	// Get the list of files in the folder and return detection against them
 	Common::FSNode folder = Common::FSNode(ConfMan.get("path"));
 	Common::FSList fslist;
 	folder.getChildren(fslist, Common::FSNode::kListFilesOnly);
 
 	// Get the matching MetaEngine for this Engine.
-	const MetaEngine &metaEngine = g_engine->getMetaEngine();
+	const MetaEngineStatic &metaEngine = g_engine->getMetaEngine();
 
 	// Iterate over the files
 	for (Common::FSList::iterator i = fslist.begin(); i != fslist.end(); ++i) {
@@ -163,7 +163,7 @@ Common::String GlkMetaEngineConnect::findFileByGameId(const Common::String &game
 	return Common::String();
 }
 
-Common::Error GlkMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+Common::Error GlkMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
 #ifndef RELEASE_BUILD
 	Glk::GameDescriptor td = Glk::GameDescriptor::empty();
 #endif
@@ -231,7 +231,7 @@ Common::Error GlkMetaEngineConnect::createInstance(OSystem *syst, Engine **engin
 	return *engine ? Common::kNoError : Common::kUserCanceled;
 }
 
-SaveStateList GlkMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList GlkMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -262,16 +262,16 @@ SaveStateList GlkMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int GlkMetaEngineConnect::getMaximumSaveSlot() const {
+int GlkMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVES;
 }
 
-void GlkMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void GlkMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor GlkMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor GlkMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename);
 	SaveStateDescriptor ssd;
@@ -290,7 +290,7 @@ SaveStateDescriptor GlkMetaEngineConnect::querySaveMetaInfos(const char *target,
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(GLK)
-	REGISTER_PLUGIN_DYNAMIC(GLK, PLUGIN_TYPE_ENGINE, GlkMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(GLK, PLUGIN_TYPE_ENGINE, GlkMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(GLK, PLUGIN_TYPE_ENGINE, GlkMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(GLK, PLUGIN_TYPE_ENGINE, GlkMetaEngine);
 #endif
diff --git a/engines/gnap/detection.cpp b/engines/gnap/detection.cpp
index deeed2a0db..6f5a163ac5 100644
--- a/engines/gnap/detection.cpp
+++ b/engines/gnap/detection.cpp
@@ -83,9 +83,9 @@ static const ADGameDescription gameDescriptions[] = {
 
 } // End of namespace Gnap
 
-class GnapMetaEngine : public AdvancedMetaEngine {
+class GnapMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	GnapMetaEngine() : AdvancedMetaEngine(Gnap::gameDescriptions, sizeof(ADGameDescription), gnapGames) {
+	GnapMetaEngineStatic() : AdvancedMetaEngineStatic(Gnap::gameDescriptions, sizeof(ADGameDescription), gnapGames) {
 		_maxScanDepth = 3;
 	}
 
@@ -102,4 +102,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(GNAP_DETECTION, PLUGIN_TYPE_METAENGINE, GnapMetaEngine);
+REGISTER_PLUGIN_STATIC(GNAP_DETECTION, PLUGIN_TYPE_METAENGINE, GnapMetaEngineStatic);
diff --git a/engines/gnap/metaengine.cpp b/engines/gnap/metaengine.cpp
index 7d981081d7..f12eda0652 100644
--- a/engines/gnap/metaengine.cpp
+++ b/engines/gnap/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "base/plugins.h"
 #include "graphics/thumbnail.h"
 
-class GnapMetaEngineConnect : public AdvancedMetaEngineConnect {
+class GnapMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "gnap";
@@ -44,7 +44,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool GnapMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool GnapMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -62,14 +62,14 @@ bool Gnap::GnapEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-void GnapMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void GnapMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-int GnapMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+int GnapMetaEngine::getMaximumSaveSlot() const { return 99; }
 
-SaveStateList GnapMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList GnapMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -99,7 +99,7 @@ SaveStateList GnapMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor GnapMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor GnapMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
 	if (file) {
@@ -144,7 +144,7 @@ SaveStateDescriptor GnapMetaEngineConnect::querySaveMetaInfos(const char *target
 	return SaveStateDescriptor();
 }
 
-bool GnapMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool GnapMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Gnap::GnapEngine(syst, desc);
 	}
@@ -152,7 +152,7 @@ bool GnapMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(GNAP)
-	REGISTER_PLUGIN_DYNAMIC(GNAP, PLUGIN_TYPE_ENGINE, GnapMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(GNAP, PLUGIN_TYPE_ENGINE, GnapMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(GNAP, PLUGIN_TYPE_ENGINE, GnapMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(GNAP, PLUGIN_TYPE_ENGINE, GnapMetaEngine);
 #endif
diff --git a/engines/gob/detection/detection.cpp b/engines/gob/detection/detection.cpp
index d408dbd093..f9fd1c61a4 100644
--- a/engines/gob/detection/detection.cpp
+++ b/engines/gob/detection/detection.cpp
@@ -27,9 +27,9 @@
 #include "gob/detection/detection.h"
 #include "gob/detection/tables.h"
 
-class GobMetaEngine : public AdvancedMetaEngine {
+class GobMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	GobMetaEngine();
+	GobMetaEngineStatic();
 
 	const char *getEngineId() const override {
 		return "gob";
@@ -47,13 +47,13 @@ private:
 	static const Gob::GOBGameDescription *detectOnceUponATime(const Common::FSList &fslist);
 };
 
-GobMetaEngine::GobMetaEngine() :
-	AdvancedMetaEngine(Gob::gameDescriptions, sizeof(Gob::GOBGameDescription), gobGames) {
+GobMetaEngineStatic::GobMetaEngineStatic() :
+	AdvancedMetaEngineStatic(Gob::gameDescriptions, sizeof(Gob::GOBGameDescription), gobGames) {
 
 	_guiOptions = GUIO1(GUIO_NOLAUNCHLOAD);
 }
 
-ADDetectedGame GobMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
+ADDetectedGame GobMetaEngineStatic::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	ADDetectedGame detectedGame = detectGameFilebased(allFiles, Gob::fileBased);
 	if (!detectedGame.desc) {
 		return ADDetectedGame();
@@ -71,7 +71,7 @@ ADDetectedGame GobMetaEngine::fallbackDetect(const FileMap &allFiles, const Comm
 	return detectedGame;
 }
 
-const Gob::GOBGameDescription *GobMetaEngine::detectOnceUponATime(const Common::FSList &fslist) {
+const Gob::GOBGameDescription *GobMetaEngineStatic::detectOnceUponATime(const Common::FSList &fslist) {
 	// Add the game path to the search manager
 	SearchMan.clear();
 	SearchMan.addDirectory(fslist.begin()->getParent().getPath(), fslist.begin()->getParent());
@@ -140,7 +140,7 @@ const Gob::GOBGameDescription *GobMetaEngine::detectOnceUponATime(const Common::
 	SearchMan.clear();
 
 	if ((gameType == Gob::kOnceUponATimeInvalid) || (platform == Gob::kOnceUponATimePlatformInvalid)) {
-		warning("GobMetaEngine::detectOnceUponATime(): Detection failed (%d, %d)",
+		warning("GobMetaEngineStatic::detectOnceUponATime(): Detection failed (%d, %d)",
 		        (int)gameType, (int)platform);
 		return 0;
 	}
@@ -148,12 +148,12 @@ const Gob::GOBGameDescription *GobMetaEngine::detectOnceUponATime(const Common::
 	return &Gob::fallbackOnceUpon[gameType][platform];
 }
 
-const char *GobMetaEngine::getName() const {
+const char *GobMetaEngineStatic::getName() const {
 	return "Gob";
 }
 
-const char *GobMetaEngine::getOriginalCopyright() const {
+const char *GobMetaEngineStatic::getOriginalCopyright() const {
 	return "Goblins Games (C) Coktel Vision";
 }
 
-REGISTER_PLUGIN_STATIC(GOB_DETECTION, PLUGIN_TYPE_METAENGINE, GobMetaEngine);
+REGISTER_PLUGIN_STATIC(GOB_DETECTION, PLUGIN_TYPE_METAENGINE, GobMetaEngineStatic);
diff --git a/engines/gob/metaengine.cpp b/engines/gob/metaengine.cpp
index 4ec0a04cf8..a4f24a091d 100644
--- a/engines/gob/metaengine.cpp
+++ b/engines/gob/metaengine.cpp
@@ -27,7 +27,7 @@
 // For struct GOBGameDescription.
 #include "gob/detection/detection.h"
 
-class GobMetaEngineConnect : public AdvancedMetaEngineConnect {
+class GobMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "gob";
@@ -39,7 +39,7 @@ public:
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool GobMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool GobMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return false;
 }
 
@@ -48,11 +48,11 @@ bool Gob::GobEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsReturnToLauncher);
 }
 
-Common::Error GobMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
-	return AdvancedMetaEngineConnect::createInstance(syst, engine);
+Common::Error GobMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
+	return AdvancedMetaEngine::createInstance(syst, engine);
 }
 
-bool GobMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool GobMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Gob::GOBGameDescription *gd = (const Gob::GOBGameDescription *)desc;
 	if (gd) {
 		*engine = new Gob::GobEngine(syst);
@@ -63,9 +63,9 @@ bool GobMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 
 
 #if PLUGIN_ENABLED_DYNAMIC(GOB)
-	REGISTER_PLUGIN_DYNAMIC(GOB, PLUGIN_TYPE_ENGINE, GobMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(GOB, PLUGIN_TYPE_ENGINE, GobMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(GOB, PLUGIN_TYPE_ENGINE, GobMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(GOB, PLUGIN_TYPE_ENGINE, GobMetaEngine);
 #endif
 
 namespace Gob {
diff --git a/engines/griffon/detection.cpp b/engines/griffon/detection.cpp
index a41c397a10..74d6bc2718 100644
--- a/engines/griffon/detection.cpp
+++ b/engines/griffon/detection.cpp
@@ -46,9 +46,9 @@ static const ADGameDescription gameDescriptions[] = {
 
 }
 
-class GriffonMetaEngine: public AdvancedMetaEngine {
+class GriffonMetaEngineStatic: public AdvancedMetaEngineStatic {
 public:
-	GriffonMetaEngine() : AdvancedMetaEngine(Griffon::gameDescriptions, sizeof(ADGameDescription), griffonGames) {
+	GriffonMetaEngineStatic() : AdvancedMetaEngineStatic(Griffon::gameDescriptions, sizeof(ADGameDescription), griffonGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -64,4 +64,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(GRIFFON_DETECTION, PLUGIN_TYPE_METAENGINE, GriffonMetaEngine);
+REGISTER_PLUGIN_STATIC(GRIFFON_DETECTION, PLUGIN_TYPE_METAENGINE, GriffonMetaEngineStatic);
diff --git a/engines/griffon/metaengine.cpp b/engines/griffon/metaengine.cpp
index 53caf64a88..86db14f6dd 100644
--- a/engines/griffon/metaengine.cpp
+++ b/engines/griffon/metaengine.cpp
@@ -31,7 +31,7 @@
 
 #include "griffon/griffon.h"
 
-class GriffonMetaEngineConnect: public AdvancedMetaEngineConnect {
+class GriffonMetaEngine: public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "griffon";
@@ -52,7 +52,7 @@ public:
 
 };
 
-Common::String GriffonMetaEngineConnect::getSavegameFile(int saveGameIdx, const char *target) const {
+Common::String GriffonMetaEngine::getSavegameFile(int saveGameIdx, const char *target) const {
 	if (saveGameIdx == kSavegameFilePattern) {
 		// Pattern requested
 		return Common::String::format("%s.s##", target == nullptr ? getEngineId() : target);
@@ -69,14 +69,14 @@ bool Griffon::GriffonEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool GriffonMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool GriffonMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc)
 		*engine = new Griffon::GriffonEngine(syst);
 
 	return desc != nullptr;
 }
 
-Common::KeymapArray GriffonMetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray GriffonMetaEngine::initKeymaps(const char *target) const {
 	using namespace Common;
 
 	Keymap *engineKeyMap = new Keymap(Keymap::kKeymapTypeGame, "griffon", "The Griffon Legend");
@@ -143,7 +143,7 @@ Common::KeymapArray GriffonMetaEngineConnect::initKeymaps(const char *target) co
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(GRIFFON)
-	REGISTER_PLUGIN_DYNAMIC(GRIFFON, PLUGIN_TYPE_ENGINE, GriffonMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(GRIFFON, PLUGIN_TYPE_ENGINE, GriffonMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(GRIFFON, PLUGIN_TYPE_ENGINE, GriffonMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(GRIFFON, PLUGIN_TYPE_ENGINE, GriffonMetaEngine);
 #endif
diff --git a/engines/groovie/detection.cpp b/engines/groovie/detection.cpp
index e0e4479860..53e365153c 100644
--- a/engines/groovie/detection.cpp
+++ b/engines/groovie/detection.cpp
@@ -327,9 +327,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class GroovieMetaEngine : public AdvancedMetaEngine {
+class GroovieMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	GroovieMetaEngine() : AdvancedMetaEngine(gameDescriptions, sizeof(GroovieGameDescription), groovieGames, optionsList) {
+	GroovieMetaEngineStatic() : AdvancedMetaEngineStatic(gameDescriptions, sizeof(GroovieGameDescription), groovieGames, optionsList) {
 		// Use kADFlagUseExtraAsHint in order to distinguish the 11th hour from
 		// its "Making of" as well as the Clandestiny Trailer; they all share
 		// the same MD5.
@@ -361,4 +361,4 @@ public:
 
 } // End of namespace Groovie
 
-REGISTER_PLUGIN_STATIC(GROOVIE_DETECTION, PLUGIN_TYPE_METAENGINE, Groovie::GroovieMetaEngine);
+REGISTER_PLUGIN_STATIC(GROOVIE_DETECTION, PLUGIN_TYPE_METAENGINE, Groovie::GroovieMetaEngineStatic);
diff --git a/engines/groovie/metaengine.cpp b/engines/groovie/metaengine.cpp
index 316237f6a7..1361d04a66 100644
--- a/engines/groovie/metaengine.cpp
+++ b/engines/groovie/metaengine.cpp
@@ -31,7 +31,7 @@
 
 namespace Groovie {
 
-class GroovieMetaEngineConnect : public AdvancedMetaEngineConnect {
+class GroovieMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "groovie";
@@ -46,14 +46,14 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool GroovieMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+bool GroovieMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
 	if (gd) {
 		*engine = new GroovieEngine(syst, (const GroovieGameDescription *)gd);
 	}
 	return gd != 0;
 }
 
-bool GroovieMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool GroovieMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -61,15 +61,15 @@ bool GroovieMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSavesSupportMetaInfo);
 }
 
-SaveStateList GroovieMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList GroovieMetaEngine::listSaves(const char *target) const {
 	return SaveLoad::listValidSaves(target);
 }
 
-int GroovieMetaEngineConnect::getMaximumSaveSlot() const {
+int GroovieMetaEngine::getMaximumSaveSlot() const {
 	return SaveLoad::getMaximumSlot();
 }
 
-void GroovieMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void GroovieMetaEngine::removeSaveState(const char *target, int slot) const {
 	if (!SaveLoad::isSlotValid(slot)) {
 		// Invalid slot, do nothing
 		return;
@@ -79,7 +79,7 @@ void GroovieMetaEngineConnect::removeSaveState(const char *target, int slot) con
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor GroovieMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor GroovieMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	SaveStateDescriptor desc;
 
 	Common::InSaveFile *savefile = SaveLoad::openForLoading(target, slot, &desc);
@@ -91,7 +91,7 @@ SaveStateDescriptor GroovieMetaEngineConnect::querySaveMetaInfos(const char *tar
 } // End of namespace Groovie
 
 #if PLUGIN_ENABLED_DYNAMIC(GROOVIE)
-	REGISTER_PLUGIN_DYNAMIC(GROOVIE, PLUGIN_TYPE_ENGINE, Groovie::GroovieMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(GROOVIE, PLUGIN_TYPE_ENGINE, Groovie::GroovieMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(GROOVIE, PLUGIN_TYPE_ENGINE, Groovie::GroovieMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(GROOVIE, PLUGIN_TYPE_ENGINE, Groovie::GroovieMetaEngine);
 #endif
diff --git a/engines/hdb/detection.cpp b/engines/hdb/detection.cpp
index e199a90fa9..01d21039f2 100644
--- a/engines/hdb/detection.cpp
+++ b/engines/hdb/detection.cpp
@@ -131,9 +131,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 		AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class HDBMetaEngine : public AdvancedMetaEngine {
+class HDBMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	HDBMetaEngine() : AdvancedMetaEngine(HDB::gameDescriptions, sizeof(ADGameDescription), hdbGames, optionsList) {
+	HDBMetaEngineStatic() : AdvancedMetaEngineStatic(HDB::gameDescriptions, sizeof(ADGameDescription), hdbGames, optionsList) {
 	}
 
 	const char *getEngineId() const override {
@@ -149,4 +149,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(HDB_DETECTION, PLUGIN_TYPE_METAENGINE, HDBMetaEngine);
+REGISTER_PLUGIN_STATIC(HDB_DETECTION, PLUGIN_TYPE_METAENGINE, HDBMetaEngineStatic);
diff --git a/engines/hdb/metaengine.cpp b/engines/hdb/metaengine.cpp
index 6627db9c84..3ca7d83dde 100644
--- a/engines/hdb/metaengine.cpp
+++ b/engines/hdb/metaengine.cpp
@@ -63,7 +63,7 @@ bool HDBGame::isHandango() const {
 
 } // End of namespace HDB
 
-class HDBMetaEngineConnect : public AdvancedMetaEngineConnect {
+class HDBMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "hdb";
@@ -79,7 +79,7 @@ public:
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool HDBMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool HDBMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsLoadingDuringStartup) ||
 		(f == kSupportsListSaves) ||
@@ -95,14 +95,14 @@ bool HDB::HDBGame::hasFeature(Engine::EngineFeature f) const {
 		   (f == kSupportsSavingDuringRuntime);
 }
 
-void HDBMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void HDBMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-int HDBMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+int HDBMetaEngine::getMaximumSaveSlot() const { return 99; }
 
-SaveStateList HDBMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList HDBMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -150,7 +150,7 @@ SaveStateList HDBMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor HDBMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor HDBMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::ScopedPtr<Common::InSaveFile> in(g_system->getSavefileManager()->openForLoading(Common::String::format("%s.%03d", target, slot)));
 
 	if (in) {
@@ -176,7 +176,7 @@ SaveStateDescriptor HDBMetaEngineConnect::querySaveMetaInfos(const char *target,
 	return SaveStateDescriptor();
 }
 
-Common::KeymapArray HDBMetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray HDBMetaEngine::initKeymaps(const char *target) const {
 	using namespace Common;
 	using namespace HDB;
 
@@ -260,7 +260,7 @@ Common::KeymapArray HDBMetaEngineConnect::initKeymaps(const char *target) const
 	return Keymap::arrayOf(engineKeyMap);
 }
 
-bool HDBMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool HDBMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new HDB::HDBGame(syst, desc);
 	}
@@ -269,7 +269,7 @@ bool HDBMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(HDB)
-	REGISTER_PLUGIN_DYNAMIC(HDB, PLUGIN_TYPE_ENGINE, HDBMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(HDB, PLUGIN_TYPE_ENGINE, HDBMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(HDB, PLUGIN_TYPE_ENGINE, HDBMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(HDB, PLUGIN_TYPE_ENGINE, HDBMetaEngine);
 #endif
diff --git a/engines/hopkins/detection.cpp b/engines/hopkins/detection.cpp
index 97fcb86eb9..d0f29f16c3 100644
--- a/engines/hopkins/detection.cpp
+++ b/engines/hopkins/detection.cpp
@@ -63,9 +63,9 @@ const static char *directoryGlobs[] = {
 	0
 };
 
-class HopkinsMetaEngine : public AdvancedMetaEngine {
+class HopkinsMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	HopkinsMetaEngine() : AdvancedMetaEngine(Hopkins::gameDescriptions, sizeof(Hopkins::HopkinsGameDescription), hopkinsGames, optionsList) {
+	HopkinsMetaEngineStatic() : AdvancedMetaEngineStatic(Hopkins::gameDescriptions, sizeof(Hopkins::HopkinsGameDescription), hopkinsGames, optionsList) {
 		_maxScanDepth = 3;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -84,4 +84,4 @@ public:
 };
 
 
-REGISTER_PLUGIN_STATIC(HOPKINS_DETECTION, PLUGIN_TYPE_METAENGINE, HopkinsMetaEngine);
+REGISTER_PLUGIN_STATIC(HOPKINS_DETECTION, PLUGIN_TYPE_METAENGINE, HopkinsMetaEngineStatic);
diff --git a/engines/hopkins/metaengine.cpp b/engines/hopkins/metaengine.cpp
index bc07ba1599..fdd0d09f58 100644
--- a/engines/hopkins/metaengine.cpp
+++ b/engines/hopkins/metaengine.cpp
@@ -59,7 +59,7 @@ const Common::String &HopkinsEngine::getTargetName() const {
 
 } // End of namespace Hopkins
 
-class HopkinsMetaEngineConnect : public AdvancedMetaEngineConnect {
+class HopkinsMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "hopkins";
@@ -74,7 +74,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool HopkinsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool HopkinsMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -91,7 +91,7 @@ bool Hopkins::HopkinsEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool HopkinsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool HopkinsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Hopkins::HopkinsGameDescription *gd = (const Hopkins::HopkinsGameDescription *)desc;
 	if (gd) {
 		*engine = new Hopkins::HopkinsEngine(syst, gd);
@@ -99,7 +99,7 @@ bool HopkinsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, co
 	return gd != 0;
 }
 
-SaveStateList HopkinsMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList HopkinsMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -132,16 +132,16 @@ SaveStateList HopkinsMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int HopkinsMetaEngineConnect::getMaximumSaveSlot() const {
+int HopkinsMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVES;
 }
 
-void HopkinsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void HopkinsMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor HopkinsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor HopkinsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
 
@@ -168,7 +168,7 @@ SaveStateDescriptor HopkinsMetaEngineConnect::querySaveMetaInfos(const char *tar
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(HOPKINS)
-	REGISTER_PLUGIN_DYNAMIC(HOPKINS, PLUGIN_TYPE_ENGINE, HopkinsMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(HOPKINS, PLUGIN_TYPE_ENGINE, HopkinsMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(HOPKINS, PLUGIN_TYPE_ENGINE, HopkinsMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(HOPKINS, PLUGIN_TYPE_ENGINE, HopkinsMetaEngine);
 #endif
diff --git a/engines/hugo/detection.cpp b/engines/hugo/detection.cpp
index 2559582a25..e35a75e1e5 100644
--- a/engines/hugo/detection.cpp
+++ b/engines/hugo/detection.cpp
@@ -113,9 +113,9 @@ static const HugoGameDescription gameDescriptions[] = {
 	{AD_TABLE_END_MARKER, kGameTypeNone}
 };
 
-class HugoMetaEngine : public AdvancedMetaEngine {
+class HugoMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	HugoMetaEngine() : AdvancedMetaEngine(gameDescriptions, sizeof(HugoGameDescription), hugoGames) {
+	HugoMetaEngineStatic() : AdvancedMetaEngineStatic(gameDescriptions, sizeof(HugoGameDescription), hugoGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -133,4 +133,4 @@ public:
 
 } // End of namespace Hugo
 
-REGISTER_PLUGIN_STATIC(HUGO_DETECTION, PLUGIN_TYPE_METAENGINE, Hugo::HugoMetaEngine);
+REGISTER_PLUGIN_STATIC(HUGO_DETECTION, PLUGIN_TYPE_METAENGINE, Hugo::HugoMetaEngineStatic);
diff --git a/engines/hugo/metaengine.cpp b/engines/hugo/metaengine.cpp
index 8deb53be2c..0169549d44 100644
--- a/engines/hugo/metaengine.cpp
+++ b/engines/hugo/metaengine.cpp
@@ -40,7 +40,7 @@ const char *HugoEngine::getGameId() const {
 	return _gameDescription->desc.gameId;
 }
 
-class HugoMetaEngineConnect : public AdvancedMetaEngineConnect {
+class HugoMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "hugo";
@@ -56,7 +56,7 @@ public:
 
 };
 
-bool HugoMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+bool HugoMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
 	if (gd) {
 		*engine = new HugoEngine(syst, (const HugoGameDescription *)gd);
 		((HugoEngine *)*engine)->initGame((const HugoGameDescription *)gd);
@@ -64,7 +64,7 @@ bool HugoMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return gd != 0;
 }
 
-bool HugoMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool HugoMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 	    (f == kSupportsLoadingDuringStartup) ||
@@ -74,9 +74,9 @@ bool HugoMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 	    (f == kSavesSupportCreationDate);
 }
 
-int HugoMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+int HugoMetaEngine::getMaximumSaveSlot() const { return 99; }
 
-SaveStateList HugoMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList HugoMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -124,7 +124,7 @@ SaveStateList HugoMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor HugoMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor HugoMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
 	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
 
@@ -177,7 +177,7 @@ SaveStateDescriptor HugoMetaEngineConnect::querySaveMetaInfos(const char *target
 	return SaveStateDescriptor();
 }
 
-void HugoMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void HugoMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
@@ -185,9 +185,9 @@ void HugoMetaEngineConnect::removeSaveState(const char *target, int slot) const
 } // End of namespace Hugo
 
 #if PLUGIN_ENABLED_DYNAMIC(HUGO)
-	REGISTER_PLUGIN_DYNAMIC(HUGO, PLUGIN_TYPE_ENGINE, Hugo::HugoMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(HUGO, PLUGIN_TYPE_ENGINE, Hugo::HugoMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(HUGO, PLUGIN_TYPE_ENGINE, Hugo::HugoMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(HUGO, PLUGIN_TYPE_ENGINE, Hugo::HugoMetaEngine);
 #endif
 
 namespace Hugo {
diff --git a/engines/illusions/detection.cpp b/engines/illusions/detection.cpp
index 207dbee649..6d9f1adba4 100644
--- a/engines/illusions/detection.cpp
+++ b/engines/illusions/detection.cpp
@@ -110,9 +110,9 @@ static const char * const directoryGlobs[] = {
 	0
 };
 
-class IllusionsMetaEngine : public AdvancedMetaEngine {
+class IllusionsMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	IllusionsMetaEngine() : AdvancedMetaEngine(Illusions::gameDescriptions, sizeof(Illusions::IllusionsGameDescription), illusionsGames) {
+	IllusionsMetaEngineStatic() : AdvancedMetaEngineStatic(Illusions::gameDescriptions, sizeof(Illusions::IllusionsGameDescription), illusionsGames) {
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -130,4 +130,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(ILLUSIONS_DETECTION, PLUGIN_TYPE_METAENGINE, IllusionsMetaEngine);
+REGISTER_PLUGIN_STATIC(ILLUSIONS_DETECTION, PLUGIN_TYPE_METAENGINE, IllusionsMetaEngineStatic);
diff --git a/engines/illusions/metaengine.cpp b/engines/illusions/metaengine.cpp
index b01997b873..ae54d008ed 100644
--- a/engines/illusions/metaengine.cpp
+++ b/engines/illusions/metaengine.cpp
@@ -45,7 +45,7 @@ Common::Language IllusionsEngine::getGameLanguage() const {
 
 } // End of namespace Illusions
 
-class IllusionsMetaEngineConnect : public AdvancedMetaEngineConnect {
+class IllusionsMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "illusions";
@@ -60,7 +60,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool IllusionsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool IllusionsMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave) ||
@@ -70,16 +70,16 @@ bool IllusionsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSavesSupportCreationDate);
 }
 
-void IllusionsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void IllusionsMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-int IllusionsMetaEngineConnect::getMaximumSaveSlot() const {
+int IllusionsMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-SaveStateList IllusionsMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList IllusionsMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Illusions::IllusionsEngine::SaveHeader header;
 	Common::String pattern = target;
@@ -104,7 +104,7 @@ SaveStateList IllusionsMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor IllusionsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor IllusionsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Illusions::IllusionsEngine::getSavegameFilename(target, slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
 	if (in) {
@@ -127,7 +127,7 @@ SaveStateDescriptor IllusionsMetaEngineConnect::querySaveMetaInfos(const char *t
 	return SaveStateDescriptor();
 }
 
-bool IllusionsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool IllusionsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Illusions::IllusionsGameDescription *gd = (const Illusions::IllusionsGameDescription *)desc;
 	if (gd) {
 		switch (gd->gameId) {
@@ -146,7 +146,7 @@ bool IllusionsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine,
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(ILLUSIONS)
-	REGISTER_PLUGIN_DYNAMIC(ILLUSIONS, PLUGIN_TYPE_ENGINE, IllusionsMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(ILLUSIONS, PLUGIN_TYPE_ENGINE, IllusionsMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(ILLUSIONS, PLUGIN_TYPE_ENGINE, IllusionsMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(ILLUSIONS, PLUGIN_TYPE_ENGINE, IllusionsMetaEngine);
 #endif
diff --git a/engines/kingdom/detection.cpp b/engines/kingdom/detection.cpp
index 4cf93a596e..b5c5b5f4c4 100644
--- a/engines/kingdom/detection.cpp
+++ b/engines/kingdom/detection.cpp
@@ -72,9 +72,9 @@ static const ADGameDescription gameDescriptions[] = {
 
 } // End of namespace Kingdom
 
-class KingdomMetaEngine : public AdvancedMetaEngine {
+class KingdomMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	KingdomMetaEngine() : AdvancedMetaEngine(Kingdom::gameDescriptions, sizeof(ADGameDescription), kingdomGames) {
+	KingdomMetaEngineStatic() : AdvancedMetaEngineStatic(Kingdom::gameDescriptions, sizeof(ADGameDescription), kingdomGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -90,4 +90,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(KINGDOM_DETECTION, PLUGIN_TYPE_METAENGINE, KingdomMetaEngine);
+REGISTER_PLUGIN_STATIC(KINGDOM_DETECTION, PLUGIN_TYPE_METAENGINE, KingdomMetaEngineStatic);
diff --git a/engines/kingdom/metaengine.cpp b/engines/kingdom/metaengine.cpp
index 78c13dec6e..4b130f387a 100644
--- a/engines/kingdom/metaengine.cpp
+++ b/engines/kingdom/metaengine.cpp
@@ -38,7 +38,7 @@ Common::Platform KingdomGame::getPlatform() const { return _gameDescription->pla
 } // End of namespace Kingdom
 
 
-class KingdomMetaEngineConnect : public AdvancedMetaEngineConnect {
+class KingdomMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "kingdom";
@@ -53,7 +53,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool KingdomMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool KingdomMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 	    (f == kSupportsLoadingDuringStartup) ||
@@ -63,18 +63,18 @@ bool KingdomMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 	    (f == kSavesSupportCreationDate);
 }
 
-bool KingdomMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool KingdomMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc)
 		*engine = new Kingdom::KingdomGame(syst, desc);
 
 	return desc != nullptr;
 }
 
-int KingdomMetaEngineConnect::getMaximumSaveSlot() const {
+int KingdomMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVES;
 }
 
-SaveStateList KingdomMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList KingdomMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -110,12 +110,12 @@ SaveStateList KingdomMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void KingdomMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void KingdomMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor KingdomMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor KingdomMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
 
@@ -137,7 +137,7 @@ SaveStateDescriptor KingdomMetaEngineConnect::querySaveMetaInfos(const char *tar
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(KINGDOM)
-	REGISTER_PLUGIN_DYNAMIC(KINGDOM, PLUGIN_TYPE_ENGINE, KingdomMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(KINGDOM, PLUGIN_TYPE_ENGINE, KingdomMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(KINGDOM, PLUGIN_TYPE_ENGINE, KingdomMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(KINGDOM, PLUGIN_TYPE_ENGINE, KingdomMetaEngine);
 #endif
diff --git a/engines/kyra/detection.cpp b/engines/kyra/detection.cpp
index 63443bb446..6538578bcf 100644
--- a/engines/kyra/detection.cpp
+++ b/engines/kyra/detection.cpp
@@ -144,9 +144,9 @@ const ADExtraGuiOptionsMap gameGuiOptions[] = {
 
 } // End of anonymous namespace
 
-class KyraMetaEngine : public AdvancedMetaEngine {
+class KyraMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	KyraMetaEngine() : AdvancedMetaEngine(adGameDescs, sizeof(KYRAGameDescription), gameList, gameGuiOptions) {
+	KyraMetaEngineStatic() : AdvancedMetaEngineStatic(adGameDescs, sizeof(KYRAGameDescription), gameList, gameGuiOptions) {
 		_md5Bytes = 1024 * 1024;
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
@@ -172,4 +172,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(KYRA_DETECTION, PLUGIN_TYPE_METAENGINE, KyraMetaEngine);
+REGISTER_PLUGIN_STATIC(KYRA_DETECTION, PLUGIN_TYPE_METAENGINE, KyraMetaEngineStatic);
diff --git a/engines/kyra/kyra_v1.h b/engines/kyra/kyra_v1.h
index 315708033c..229b1a65b0 100644
--- a/engines/kyra/kyra_v1.h
+++ b/engines/kyra/kyra_v1.h
@@ -48,7 +48,7 @@ namespace Graphics {
 struct Surface;
 }
 
-class KyraMetaEngineConnect;
+class KyraMetaEngine;
 
 /**
  * This is the namespace of the Kyra engine.
@@ -147,7 +147,7 @@ struct Button;
 
 class KyraEngine_v1 : public Engine {
 friend class Debugger;
-friend class ::KyraMetaEngineConnect;
+friend class ::KyraMetaEngine;
 friend class GUI;
 friend class GUI_v1;
 friend class GUI_EoB;
diff --git a/engines/kyra/metaengine.cpp b/engines/kyra/metaengine.cpp
index 3d6c680693..4813f79623 100644
--- a/engines/kyra/metaengine.cpp
+++ b/engines/kyra/metaengine.cpp
@@ -38,7 +38,7 @@
 
 #include "kyra/detection.h"
 
-class KyraMetaEngineConnect : public AdvancedMetaEngineConnect {
+class KyraMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "kyra";
@@ -56,7 +56,7 @@ public:
 	Common::KeymapArray initKeymaps(const char *target) const override;
 };
 
-bool KyraMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool KyraMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 	    (f == kSupportsLoadingDuringStartup) ||
@@ -74,7 +74,7 @@ bool Kyra::KyraEngine_v1::hasFeature(EngineFeature f) const {
 	    (f == kSupportsSubtitleOptions);
 }
 
-bool KyraMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool KyraMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const KYRAGameDescription *gd = (const KYRAGameDescription *)desc;
 	bool res = true;
 
@@ -134,7 +134,7 @@ bool KyraMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return res;
 }
 
-SaveStateList KyraMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList KyraMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Kyra::KyraEngine_v1::SaveHeader header;
 	Common::String pattern = target;
@@ -169,11 +169,11 @@ SaveStateList KyraMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int KyraMetaEngineConnect::getMaximumSaveSlot() const {
+int KyraMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-void KyraMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void KyraMetaEngine::removeSaveState(const char *target, int slot) const {
 	// In Kyra games slot 0 can't be deleted, it's for restarting the game(s).
 	// An exception makes Lands of Lore here, it does not have any way to restart the
 	// game except via its main menu.
@@ -184,7 +184,7 @@ void KyraMetaEngineConnect::removeSaveState(const char *target, int slot) const
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor KyraMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor KyraMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Kyra::KyraEngine_v1::getSavegameFilename(target, slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename);
 	const bool nonKyraGame = ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("lol") || ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob") || ConfMan.getDomain(target)->getVal("gameid").equalsIgnoreCase("eob2");
@@ -223,7 +223,7 @@ SaveStateDescriptor KyraMetaEngineConnect::querySaveMetaInfos(const char *target
 	return desc;
 }
 
-Common::KeymapArray KyraMetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray KyraMetaEngine::initKeymaps(const char *target) const {
 	Common::String gameId = ConfMan.get("gameid", target);
 
 #ifdef ENABLE_LOL
@@ -238,11 +238,11 @@ Common::KeymapArray KyraMetaEngineConnect::initKeymaps(const char *target) const
 	}
 #endif
 
-	return AdvancedMetaEngineConnect::initKeymaps(target);
+	return AdvancedMetaEngine::initKeymaps(target);
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(KYRA)
-	REGISTER_PLUGIN_DYNAMIC(KYRA, PLUGIN_TYPE_ENGINE, KyraMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(KYRA, PLUGIN_TYPE_ENGINE, KyraMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(KYRA, PLUGIN_TYPE_ENGINE, KyraMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(KYRA, PLUGIN_TYPE_ENGINE, KyraMetaEngine);
 #endif
diff --git a/engines/lab/detection.cpp b/engines/lab/detection.cpp
index 6985a46695..b89e2739f9 100644
--- a/engines/lab/detection.cpp
+++ b/engines/lab/detection.cpp
@@ -101,9 +101,9 @@ static const char *const directoryGlobs[] = {
 
 
 
-class LabMetaEngine : public AdvancedMetaEngine {
+class LabMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	LabMetaEngine() : AdvancedMetaEngine(labDescriptions, sizeof(ADGameDescription), lab_setting) {
+	LabMetaEngineStatic() : AdvancedMetaEngineStatic(labDescriptions, sizeof(ADGameDescription), lab_setting) {
 		_maxScanDepth = 4;
 		_directoryGlobs = directoryGlobs;
 		_flags = kADFlagUseExtraAsHint;
@@ -122,4 +122,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(LAB_DETECTION, PLUGIN_TYPE_METAENGINE, LabMetaEngine);
+REGISTER_PLUGIN_STATIC(LAB_DETECTION, PLUGIN_TYPE_METAENGINE, LabMetaEngineStatic);
diff --git a/engines/lab/metaengine.cpp b/engines/lab/metaengine.cpp
index b1b81356fc..bf69e15149 100644
--- a/engines/lab/metaengine.cpp
+++ b/engines/lab/metaengine.cpp
@@ -43,7 +43,7 @@ uint32 LabEngine::getFeatures() const {
 
 } // End of namespace Lab
 
-class LabMetaEngineConnect : public AdvancedMetaEngineConnect {
+class LabMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "lab";
@@ -62,7 +62,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool LabMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool LabMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -81,7 +81,7 @@ bool Lab::LabEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-SaveStateList LabMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList LabMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Lab::SaveGameHeader header;
 	Common::String pattern = target;
@@ -111,16 +111,16 @@ SaveStateList LabMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int LabMetaEngineConnect::getMaximumSaveSlot() const {
+int LabMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-void LabMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void LabMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	saveFileMan->removeSavefile(Common::String::format("%s.%03u", target, slot));
 }
 
-SaveStateDescriptor LabMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor LabMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03u", target, slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
 
@@ -145,7 +145,7 @@ SaveStateDescriptor LabMetaEngineConnect::querySaveMetaInfos(const char *target,
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(LAB)
-	REGISTER_PLUGIN_DYNAMIC(LAB, PLUGIN_TYPE_ENGINE, LabMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(LAB, PLUGIN_TYPE_ENGINE, LabMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(LAB, PLUGIN_TYPE_ENGINE, LabMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(LAB, PLUGIN_TYPE_ENGINE, LabMetaEngine);
 #endif
diff --git a/engines/lastexpress/detection.cpp b/engines/lastexpress/detection.cpp
index 0dcc5ccc57..fc070cef93 100644
--- a/engines/lastexpress/detection.cpp
+++ b/engines/lastexpress/detection.cpp
@@ -223,9 +223,9 @@ static const ADGameDescription gameDescriptions[] = {
 };
 
 
-class LastExpressMetaEngine : public AdvancedMetaEngine {
+class LastExpressMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	LastExpressMetaEngine() : AdvancedMetaEngine(gameDescriptions, sizeof(ADGameDescription), lastExpressGames) {
+	LastExpressMetaEngineStatic() : AdvancedMetaEngineStatic(gameDescriptions, sizeof(ADGameDescription), lastExpressGames) {
 		_guiOptions = GUIO2(GUIO_NOSUBTITLES, GUIO_NOSFX);
 	}
 
@@ -244,4 +244,4 @@ public:
 
 } // End of namespace LastExpress
 
-REGISTER_PLUGIN_STATIC(LASTEXPRESS_DETECTION, PLUGIN_TYPE_METAENGINE, LastExpress::LastExpressMetaEngine);
+REGISTER_PLUGIN_STATIC(LASTEXPRESS_DETECTION, PLUGIN_TYPE_METAENGINE, LastExpress::LastExpressMetaEngineStatic);
diff --git a/engines/lastexpress/metaengine.cpp b/engines/lastexpress/metaengine.cpp
index b9ebb244fb..54bef00bcc 100644
--- a/engines/lastexpress/metaengine.cpp
+++ b/engines/lastexpress/metaengine.cpp
@@ -25,7 +25,7 @@
 
 namespace LastExpress {
 
-class LastExpressMetaEngineConnect : public AdvancedMetaEngineConnect {
+class LastExpressMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "lastexpress";
@@ -35,7 +35,7 @@ protected:
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const override;
 };
 
-bool LastExpressMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+bool LastExpressMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
 	if (gd) {
 		*engine = new LastExpressEngine(syst, (const ADGameDescription *)gd);
 	}
@@ -49,7 +49,7 @@ bool LastExpressEngine::isDemo() const {
 } // End of namespace LastExpress
 
 #if PLUGIN_ENABLED_DYNAMIC(LASTEXPRESS)
-	REGISTER_PLUGIN_DYNAMIC(LASTEXPRESS, PLUGIN_TYPE_ENGINE, LastExpress::LastExpressMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(LASTEXPRESS, PLUGIN_TYPE_ENGINE, LastExpress::LastExpressMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(LASTEXPRESS, PLUGIN_TYPE_ENGINE, LastExpress::LastExpressMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(LASTEXPRESS, PLUGIN_TYPE_ENGINE, LastExpress::LastExpressMetaEngine);
 #endif
diff --git a/engines/lilliput/detection.cpp b/engines/lilliput/detection.cpp
index 356fceef35..4013d5f319 100644
--- a/engines/lilliput/detection.cpp
+++ b/engines/lilliput/detection.cpp
@@ -104,9 +104,9 @@ static const LilliputGameDescription gameDescriptions[] = {
 	{AD_TABLE_END_MARKER, kGameTypeNone}
 };
 
-class LilliputMetaEngine : public AdvancedMetaEngine {
+class LilliputMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	LilliputMetaEngine() : AdvancedMetaEngine(gameDescriptions, sizeof(LilliputGameDescription), lilliputGames) {
+	LilliputMetaEngineStatic() : AdvancedMetaEngineStatic(gameDescriptions, sizeof(LilliputGameDescription), lilliputGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -124,4 +124,4 @@ public:
 
 } // End of namespace Lilliput
 
-REGISTER_PLUGIN_STATIC(LILLIPUT_DETECTION, PLUGIN_TYPE_METAENGINE, Lilliput::LilliputMetaEngine);
+REGISTER_PLUGIN_STATIC(LILLIPUT_DETECTION, PLUGIN_TYPE_METAENGINE, Lilliput::LilliputMetaEngineStatic);
diff --git a/engines/lilliput/metaengine.cpp b/engines/lilliput/metaengine.cpp
index e6df2bacfb..3a837940e2 100644
--- a/engines/lilliput/metaengine.cpp
+++ b/engines/lilliput/metaengine.cpp
@@ -44,7 +44,7 @@ const char *LilliputEngine::getGameId() const {
 
 namespace Lilliput {
 
-class LilliputMetaEngineConnect : public AdvancedMetaEngineConnect {
+class LilliputMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "lilliput";
@@ -59,7 +59,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool LilliputMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
+bool LilliputMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *gd) const {
 	if (gd) {
 		*engine = new LilliputEngine(syst, (const LilliputGameDescription *)gd);
 		((LilliputEngine *)*engine)->initGame((const LilliputGameDescription *)gd);
@@ -67,7 +67,7 @@ bool LilliputMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, c
 	return gd != 0;
 }
 
-bool LilliputMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool LilliputMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -77,11 +77,11 @@ bool LilliputMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSavesSupportCreationDate);
 }
 
-int LilliputMetaEngineConnect::getMaximumSaveSlot() const {
+int LilliputMetaEngine::getMaximumSaveSlot() const {
 	return 99;
 }
 
-SaveStateList LilliputMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList LilliputMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -129,7 +129,7 @@ SaveStateList LilliputMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor LilliputMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor LilliputMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
 	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
 
@@ -186,7 +186,7 @@ SaveStateDescriptor LilliputMetaEngineConnect::querySaveMetaInfos(const char *ta
 	return SaveStateDescriptor();
 }
 
-void LilliputMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void LilliputMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s-%02d.SAV", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
@@ -194,9 +194,9 @@ void LilliputMetaEngineConnect::removeSaveState(const char *target, int slot) co
 } // End of namespace Lilliput
 
 #if PLUGIN_ENABLED_DYNAMIC(LILLIPUT)
-	REGISTER_PLUGIN_DYNAMIC(LILLIPUT, PLUGIN_TYPE_ENGINE, Lilliput::LilliputMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(LILLIPUT, PLUGIN_TYPE_ENGINE, Lilliput::LilliputMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(LILLIPUT, PLUGIN_TYPE_ENGINE, Lilliput::LilliputMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(LILLIPUT, PLUGIN_TYPE_ENGINE, Lilliput::LilliputMetaEngine);
 #endif
 
 namespace Lilliput {
diff --git a/engines/lure/detection.cpp b/engines/lure/detection.cpp
index 92619e1179..f5ba70217e 100644
--- a/engines/lure/detection.cpp
+++ b/engines/lure/detection.cpp
@@ -202,9 +202,9 @@ static const LureGameDescription gameDescriptions[] = {
 
 } // End of namespace Lure
 
-class LureMetaEngine : public AdvancedMetaEngine {
+class LureMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	LureMetaEngine() : AdvancedMetaEngine(Lure::gameDescriptions, sizeof(Lure::LureGameDescription), lureGames
+	LureMetaEngineStatic() : AdvancedMetaEngineStatic(Lure::gameDescriptions, sizeof(Lure::LureGameDescription), lureGames
 #ifdef USE_TTS
 			, optionsList
 #endif
@@ -230,4 +230,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(LURE_DETECTION, PLUGIN_TYPE_METAENGINE, LureMetaEngine);
+REGISTER_PLUGIN_STATIC(LURE_DETECTION, PLUGIN_TYPE_METAENGINE, LureMetaEngineStatic);
diff --git a/engines/lure/metaengine.cpp b/engines/lure/metaengine.cpp
index c6d7171f3b..7bac80b7c9 100644
--- a/engines/lure/metaengine.cpp
+++ b/engines/lure/metaengine.cpp
@@ -50,7 +50,7 @@ LureLanguage LureEngine::getLureLanguage() const {
 
 } // End of namespace Lure
 
-class LureMetaEngineConnect : public AdvancedMetaEngineConnect {
+class LureMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "lure";
@@ -64,7 +64,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool LureMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool LureMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -78,7 +78,7 @@ bool Lure::LureEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool LureMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool LureMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Lure::LureGameDescription *gd = (const Lure::LureGameDescription *)desc;
 	if (gd) {
 		*engine = new Lure::LureEngine(syst, gd);
@@ -86,7 +86,7 @@ bool LureMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return gd != 0;
 }
 
-SaveStateList LureMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList LureMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -114,9 +114,9 @@ SaveStateList LureMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int LureMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+int LureMetaEngine::getMaximumSaveSlot() const { return 999; }
 
-void LureMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void LureMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = target;
 	filename += Common::String::format(".%03d", slot);
 
@@ -124,7 +124,7 @@ void LureMetaEngineConnect::removeSaveState(const char *target, int slot) const
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(LURE)
-	REGISTER_PLUGIN_DYNAMIC(LURE, PLUGIN_TYPE_ENGINE, LureMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(LURE, PLUGIN_TYPE_ENGINE, LureMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(LURE, PLUGIN_TYPE_ENGINE, LureMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(LURE, PLUGIN_TYPE_ENGINE, LureMetaEngine);
 #endif
diff --git a/engines/macventure/detection.cpp b/engines/macventure/detection.cpp
index 062f269569..c25fba2bfb 100644
--- a/engines/macventure/detection.cpp
+++ b/engines/macventure/detection.cpp
@@ -50,9 +50,9 @@ namespace MacVenture {
 
 SaveStateDescriptor loadMetaData(Common::SeekableReadStream *s, int slot, bool skipThumbnail = true);
 
-class MacVentureMetaEngine : public AdvancedMetaEngine {
+class MacVentureMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	MacVentureMetaEngine() : AdvancedMetaEngine(MacVenture::gameDescriptions, sizeof(ADGameDescription), macventureGames) {
+	MacVentureMetaEngineStatic() : AdvancedMetaEngineStatic(MacVenture::gameDescriptions, sizeof(ADGameDescription), macventureGames) {
 		_guiOptions = GUIO1(GUIO_NOMIDI);
 		_md5Bytes = 5000000; // TODO: Upper limit, adjust it once all games are added
 	}
@@ -72,4 +72,4 @@ public:
 
 } // End of namespace MacVenture
 
-REGISTER_PLUGIN_STATIC(MACVENTURE_DETECTION, PLUGIN_TYPE_METAENGINE, MacVenture::MacVentureMetaEngine);
+REGISTER_PLUGIN_STATIC(MACVENTURE_DETECTION, PLUGIN_TYPE_METAENGINE, MacVenture::MacVentureMetaEngineStatic);
diff --git a/engines/macventure/metaengine.cpp b/engines/macventure/metaengine.cpp
index af5a0bde12..5edf092636 100644
--- a/engines/macventure/metaengine.cpp
+++ b/engines/macventure/metaengine.cpp
@@ -40,7 +40,7 @@ namespace MacVenture {
 
 SaveStateDescriptor loadMetaData(Common::SeekableReadStream *s, int slot, bool skipThumbnail = true);
 
-class MacVentureMetaEngineConnect : public AdvancedMetaEngineConnect {
+class MacVentureMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "macventure";
@@ -56,7 +56,7 @@ protected:
 
 };
 
-bool MacVentureMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool MacVentureMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -74,7 +74,7 @@ bool MacVentureEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-SaveStateList MacVentureMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList MacVentureMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -111,21 +111,21 @@ SaveStateList MacVentureMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int MacVentureMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+int MacVentureMetaEngine::getMaximumSaveSlot() const { return 999; }
 
-bool MacVentureMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *game) const {
+bool MacVentureMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *game) const {
 	if (game) {
 		*engine = new MacVenture::MacVentureEngine(syst, game);
 	}
 	return game != 0;
 }
 
-void MacVentureMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void MacVentureMetaEngine::removeSaveState(const char *target, int slot) const {
 	g_system->getSavefileManager()->removeSavefile(Common::String::format("%s.%03d", target, slot));
 }
 
 
-SaveStateDescriptor MacVentureMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor MacVentureMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	SaveStateDescriptor desc;
 	Common::String saveFileName;
@@ -151,7 +151,7 @@ SaveStateDescriptor MacVentureMetaEngineConnect::querySaveMetaInfos(const char *
 } // End of namespace MacVenture
 
 #if PLUGIN_ENABLED_DYNAMIC(MACVENTURE)
-	REGISTER_PLUGIN_DYNAMIC(MACVENTURE, PLUGIN_TYPE_ENGINE, MacVenture::MacVentureMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(MACVENTURE, PLUGIN_TYPE_ENGINE, MacVenture::MacVentureMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(MACVENTURE, PLUGIN_TYPE_ENGINE, MacVenture::MacVentureMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(MACVENTURE, PLUGIN_TYPE_ENGINE, MacVenture::MacVentureMetaEngine);
 #endif
diff --git a/engines/made/detection.cpp b/engines/made/detection.cpp
index 3c04d58df1..b76a80cfda 100644
--- a/engines/made/detection.cpp
+++ b/engines/made/detection.cpp
@@ -35,9 +35,9 @@ static const PlainGameDescriptor madeGames[] = {
 
 #include "made/detection_tables.h"
 
-class MadeMetaEngine : public AdvancedMetaEngine {
+class MadeMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	MadeMetaEngine() : AdvancedMetaEngine(Made::gameDescriptions, sizeof(Made::MadeGameDescription), madeGames) {
+	MadeMetaEngineStatic() : AdvancedMetaEngineStatic(Made::gameDescriptions, sizeof(Made::MadeGameDescription), madeGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -55,7 +55,7 @@ public:
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
 };
 
-ADDetectedGame MadeMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
+ADDetectedGame MadeMetaEngineStatic::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	// Set the default values for the fallback descriptor's ADGameDescription part.
 	Made::g_fallbackDesc.desc.language = Common::UNK_LANG;
 	Made::g_fallbackDesc.desc.platform = Common::kPlatformDOS;
@@ -70,4 +70,4 @@ ADDetectedGame MadeMetaEngine::fallbackDetect(const FileMap &allFiles, const Com
 	return ADDetectedGame();
 }
 
-REGISTER_PLUGIN_STATIC(MADE_DETECTION, PLUGIN_TYPE_METAENGINE, MadeMetaEngine);
+REGISTER_PLUGIN_STATIC(MADE_DETECTION, PLUGIN_TYPE_METAENGINE, MadeMetaEngineStatic);
diff --git a/engines/made/metaengine.cpp b/engines/made/metaengine.cpp
index cacc7b929e..e3d98df657 100644
--- a/engines/made/metaengine.cpp
+++ b/engines/made/metaengine.cpp
@@ -45,7 +45,7 @@ uint16 MadeEngine::getVersion() const {
 
 } // End of namespace Made
 
-class MadeMetaEngineConnect : public AdvancedMetaEngineConnect {
+class MadeMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "made";
@@ -55,7 +55,7 @@ public:
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool MadeMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool MadeMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		false;
 }
@@ -65,7 +65,7 @@ bool Made::MadeEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsReturnToLauncher);
 }
 
-bool MadeMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool MadeMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Made::MadeGameDescription *gd = (const Made::MadeGameDescription *)desc;
 	if (gd) {
 		*engine = new Made::MadeEngine(syst, gd);
@@ -74,7 +74,7 @@ bool MadeMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(MADE)
-	REGISTER_PLUGIN_DYNAMIC(MADE, PLUGIN_TYPE_ENGINE, MadeMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(MADE, PLUGIN_TYPE_ENGINE, MadeMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(MADE, PLUGIN_TYPE_ENGINE, MadeMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(MADE, PLUGIN_TYPE_ENGINE, MadeMetaEngine);
 #endif
diff --git a/engines/mads/detection.cpp b/engines/mads/detection.cpp
index f7d8111c9d..2accf7fe27 100644
--- a/engines/mads/detection.cpp
+++ b/engines/mads/detection.cpp
@@ -114,9 +114,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class MADSMetaEngine : public AdvancedMetaEngine {
+class MADSMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	MADSMetaEngine() : AdvancedMetaEngine(MADS::gameDescriptions, sizeof(MADS::MADSGameDescription), MADSGames, optionsList) {
+	MADSMetaEngineStatic() : AdvancedMetaEngineStatic(MADS::gameDescriptions, sizeof(MADS::MADSGameDescription), MADSGames, optionsList) {
 		_maxScanDepth = 3;
 	}
 
@@ -133,4 +133,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(MADS_DETECTION, PLUGIN_TYPE_METAENGINE, MADSMetaEngine);
+REGISTER_PLUGIN_STATIC(MADS_DETECTION, PLUGIN_TYPE_METAENGINE, MADSMetaEngineStatic);
diff --git a/engines/mads/metaengine.cpp b/engines/mads/metaengine.cpp
index 9ba6633666..227708c555 100644
--- a/engines/mads/metaengine.cpp
+++ b/engines/mads/metaengine.cpp
@@ -63,7 +63,7 @@ Common::Platform MADSEngine::getPlatform() const {
 
 } // End of namespace MADS
 
-class MADSMetaEngineConnect : public AdvancedMetaEngineConnect {
+class MADSMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "mads";
@@ -78,7 +78,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool MADSMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool MADSMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -95,7 +95,7 @@ bool MADS::MADSEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool MADSMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool MADSMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const MADS::MADSGameDescription *gd = (const MADS::MADSGameDescription *)desc;
 	if (gd) {
 		*engine = new MADS::MADSEngine(syst, gd);
@@ -103,7 +103,7 @@ bool MADSMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return gd != 0;
 }
 
-SaveStateList MADSMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList MADSMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -133,16 +133,16 @@ SaveStateList MADSMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int MADSMetaEngineConnect::getMaximumSaveSlot() const {
+int MADSMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVES;
 }
 
-void MADSMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void MADSMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor MADSMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor MADSMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
 
@@ -168,7 +168,7 @@ SaveStateDescriptor MADSMetaEngineConnect::querySaveMetaInfos(const char *target
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(MADS)
-	REGISTER_PLUGIN_DYNAMIC(MADS, PLUGIN_TYPE_ENGINE, MADSMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(MADS, PLUGIN_TYPE_ENGINE, MADSMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(MADS, PLUGIN_TYPE_ENGINE, MADSMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(MADS, PLUGIN_TYPE_ENGINE, MADSMetaEngine);
 #endif
diff --git a/engines/mohawk/detection.cpp b/engines/mohawk/detection.cpp
index 1d7dcbd44c..d44739b302 100644
--- a/engines/mohawk/detection.cpp
+++ b/engines/mohawk/detection.cpp
@@ -76,9 +76,9 @@ static const char *directoryGlobs[] = {
 	nullptr
 };
 
-class MohawkMetaEngine : public AdvancedMetaEngine {
+class MohawkMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	MohawkMetaEngine() : AdvancedMetaEngine(Mohawk::gameDescriptions, sizeof(Mohawk::MohawkGameDescription), mohawkGames) {
+	MohawkMetaEngineStatic() : AdvancedMetaEngineStatic(Mohawk::gameDescriptions, sizeof(Mohawk::MohawkGameDescription), mohawkGames) {
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -104,8 +104,8 @@ public:
 	void registerDefaultSettings(const Common::String &target) const override;
 };
 
-DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) const {
-	DetectedGame game = AdvancedMetaEngine::toDetectedGame(adGame);
+DetectedGame MohawkMetaEngineStatic::toDetectedGame(const ADDetectedGame &adGame) const {
+	DetectedGame game = AdvancedMetaEngineStatic::toDetectedGame(adGame);
 
 	// The AdvancedDetector model only allows specifying a single supported
 	// game language. The 25th anniversary edition Myst games are multilanguage.
@@ -132,7 +132,7 @@ DetectedGame MohawkMetaEngine::toDetectedGame(const ADDetectedGame &adGame) cons
 	return game;
 }
 
-void MohawkMetaEngine::registerDefaultSettings(const Common::String &target) const {
+void MohawkMetaEngineStatic::registerDefaultSettings(const Common::String &target) const {
 	Common::String gameId = ConfMan.get("gameid", target);
 
 	if (gameId == "myst" || gameId == "makingofmyst") {
@@ -143,7 +143,7 @@ void MohawkMetaEngine::registerDefaultSettings(const Common::String &target) con
 		return Mohawk::MohawkMetaEngine_Riven::registerDefaultSettings();
 	}
 
-	return AdvancedMetaEngine::registerDefaultSettings(target);
+	return AdvancedMetaEngineStatic::registerDefaultSettings(target);
 }
 
-REGISTER_PLUGIN_STATIC(MOHAWK_DETECTION, PLUGIN_TYPE_METAENGINE, MohawkMetaEngine);
+REGISTER_PLUGIN_STATIC(MOHAWK_DETECTION, PLUGIN_TYPE_METAENGINE, MohawkMetaEngineStatic);
diff --git a/engines/mohawk/metaengine.cpp b/engines/mohawk/metaengine.cpp
index 764e2d8c18..2ab8cdabe2 100644
--- a/engines/mohawk/metaengine.cpp
+++ b/engines/mohawk/metaengine.cpp
@@ -119,7 +119,7 @@ bool MohawkEngine_Riven::hasFeature(EngineFeature f) const {
 
 } // End of Namespace Mohawk
 
-class MohawkMetaEngineConnect : public AdvancedMetaEngineConnect {
+class MohawkMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "mohawk";
@@ -139,7 +139,7 @@ public:
 	GUI::OptionsContainerWidget *buildEngineOptionsWidgetDynamic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const override;
 };
 
-bool MohawkMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool MohawkMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves)
 		|| (f == kSupportsLoadingDuringStartup)
@@ -150,7 +150,7 @@ bool MohawkMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		|| (f == kSavesSupportPlayTime);
 }
 
-SaveStateList MohawkMetaEngineConnect::listSavesForPrefix(const char *prefix, const char *extension) const {
+SaveStateList MohawkMetaEngine::listSavesForPrefix(const char *prefix, const char *extension) const {
 	Common::String pattern = Common::String::format("%s-###.%s", prefix, extension);
 	Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
 	size_t prefixLen = strlen(prefix);
@@ -174,7 +174,7 @@ SaveStateList MohawkMetaEngineConnect::listSavesForPrefix(const char *prefix, co
 	return saveList;
 }
 
-SaveStateList MohawkMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList MohawkMetaEngine::listSaves(const char *target) const {
 	Common::String gameId = ConfMan.get("gameid", target);
 	SaveStateList saveList;
 
@@ -207,7 +207,7 @@ SaveStateList MohawkMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void MohawkMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void MohawkMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String gameId = ConfMan.get("gameid", target);
 
 	// Removing saved games is only supported in Myst/Riven currently.
@@ -223,7 +223,7 @@ void MohawkMetaEngineConnect::removeSaveState(const char *target, int slot) cons
 #endif
 }
 
-SaveStateDescriptor MohawkMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor MohawkMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String gameId = ConfMan.get("gameid", target);
 
 #ifdef ENABLE_MYST
@@ -241,7 +241,7 @@ SaveStateDescriptor MohawkMetaEngineConnect::querySaveMetaInfos(const char *targ
 	}
 }
 
-Common::KeymapArray MohawkMetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray MohawkMetaEngine::initKeymaps(const char *target) const {
 	Common::String gameId = ConfMan.get("gameid", target);
 
 #ifdef ENABLE_MYST
@@ -255,10 +255,10 @@ Common::KeymapArray MohawkMetaEngineConnect::initKeymaps(const char *target) con
 	}
 #endif
 
-	return AdvancedMetaEngineConnect::initKeymaps(target);
+	return AdvancedMetaEngine::initKeymaps(target);
 }
 
-bool MohawkMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool MohawkMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Mohawk::MohawkGameDescription *gd = (const Mohawk::MohawkGameDescription *)desc;
 
 	if (gd) {
@@ -309,7 +309,7 @@ bool MohawkMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, con
 	return (gd != nullptr);
 }
 
-GUI::OptionsContainerWidget *MohawkMetaEngineConnect::buildEngineOptionsWidgetDynamic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
+GUI::OptionsContainerWidget *MohawkMetaEngine::buildEngineOptionsWidgetDynamic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
 	Common::String gameId = ConfMan.get("gameid", target);
 
 #ifdef ENABLE_MYST
@@ -323,11 +323,11 @@ GUI::OptionsContainerWidget *MohawkMetaEngineConnect::buildEngineOptionsWidgetDy
 	}
 #endif
 
-	return MetaEngineConnect::buildEngineOptionsWidgetDynamic(boss, name, target);
+	return MetaEngine::buildEngineOptionsWidgetDynamic(boss, name, target);
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(MOHAWK)
-	REGISTER_PLUGIN_DYNAMIC(MOHAWK, PLUGIN_TYPE_ENGINE, MohawkMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(MOHAWK, PLUGIN_TYPE_ENGINE, MohawkMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(MOHAWK, PLUGIN_TYPE_ENGINE, MohawkMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(MOHAWK, PLUGIN_TYPE_ENGINE, MohawkMetaEngine);
 #endif
diff --git a/engines/mortevielle/detection.cpp b/engines/mortevielle/detection.cpp
index 99a324964f..f9a7b1164f 100644
--- a/engines/mortevielle/detection.cpp
+++ b/engines/mortevielle/detection.cpp
@@ -32,9 +32,9 @@ static const PlainGameDescriptor MortevielleGame[] = {
 
 #include "mortevielle/detection_tables.h"
 
-class MortevielleMetaEngine : public AdvancedMetaEngine {
+class MortevielleMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	MortevielleMetaEngine() : AdvancedMetaEngine(Mortevielle::MortevielleGameDescriptions, sizeof(Mortevielle::MortevielleGameDescription),
+	MortevielleMetaEngineStatic() : AdvancedMetaEngineStatic(Mortevielle::MortevielleGameDescriptions, sizeof(Mortevielle::MortevielleGameDescription),
 		MortevielleGame) {
 		_md5Bytes = 512;
 		// Use kADFlagUseExtraAsHint to distinguish between original and improved versions
@@ -56,4 +56,4 @@ public:
 };
 
 
-REGISTER_PLUGIN_STATIC(MORTEVIELLE_DETECTION, PLUGIN_TYPE_METAENGINE, MortevielleMetaEngine);
+REGISTER_PLUGIN_STATIC(MORTEVIELLE_DETECTION, PLUGIN_TYPE_METAENGINE, MortevielleMetaEngineStatic);
diff --git a/engines/mortevielle/metaengine.cpp b/engines/mortevielle/metaengine.cpp
index 6bc1e23ef2..0ce49d3dcd 100644
--- a/engines/mortevielle/metaengine.cpp
+++ b/engines/mortevielle/metaengine.cpp
@@ -39,7 +39,7 @@ bool MortevielleEngine::useOriginalData() const { return _gameDescription->dataF
 
 } // End of namespace Mortevielle
 
-class MortevielleMetaEngineConnect : public AdvancedMetaEngineConnect {
+class MortevielleMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "mortevielle";
@@ -53,14 +53,14 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool MortevielleMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool MortevielleMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Mortevielle::MortevielleEngine(syst, (const Mortevielle::MortevielleGameDescription *)desc);
 	}
 	return desc != 0;
 }
 
-bool MortevielleMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool MortevielleMetaEngine::hasFeature(MetaEngineFeature f) const {
 	switch (f) {
 	case kSupportsListSaves:
 	case kSupportsDeleteSave:
@@ -75,19 +75,19 @@ bool MortevielleMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 	}
 }
 
-int MortevielleMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+int MortevielleMetaEngine::getMaximumSaveSlot() const { return 99; }
 
-SaveStateList MortevielleMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList MortevielleMetaEngine::listSaves(const char *target) const {
 	return Mortevielle::SavegameManager::listSaves(target);
 }
 
-SaveStateDescriptor MortevielleMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor MortevielleMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Mortevielle::MortevielleEngine::generateSaveFilename(target, slot);
 	return Mortevielle::SavegameManager::querySaveMetaInfos(filename);
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(MORTEVIELLE)
-	REGISTER_PLUGIN_DYNAMIC(MORTEVIELLE, PLUGIN_TYPE_ENGINE, MortevielleMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(MORTEVIELLE, PLUGIN_TYPE_ENGINE, MortevielleMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(MORTEVIELLE, PLUGIN_TYPE_ENGINE, MortevielleMetaEngineConnect);
-#endif
\ No newline at end of file
+	REGISTER_PLUGIN_STATIC(MORTEVIELLE, PLUGIN_TYPE_ENGINE, MortevielleMetaEngine);
+#endif
diff --git a/engines/mutationofjb/detection.cpp b/engines/mutationofjb/detection.cpp
index a88db46fdf..f29ef03768 100644
--- a/engines/mutationofjb/detection.cpp
+++ b/engines/mutationofjb/detection.cpp
@@ -79,9 +79,9 @@ static const char *const mutationofjbDirectoryGlobs[] = {
 	nullptr
 };
 
-class MutationOfJBMetaEngine : public AdvancedMetaEngine {
+class MutationOfJBMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	MutationOfJBMetaEngine() : AdvancedMetaEngine(mutationofjbDescriptions, sizeof(ADGameDescription), mutationofjbGames) {
+	MutationOfJBMetaEngineStatic() : AdvancedMetaEngineStatic(mutationofjbDescriptions, sizeof(ADGameDescription), mutationofjbGames) {
 		_maxScanDepth = 2;
 		_directoryGlobs = mutationofjbDirectoryGlobs;
 	}
@@ -99,4 +99,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(MUTATIONOFJB_DETECTION, PLUGIN_TYPE_METAENGINE, MutationOfJBMetaEngine);
+REGISTER_PLUGIN_STATIC(MUTATIONOFJB_DETECTION, PLUGIN_TYPE_METAENGINE, MutationOfJBMetaEngineStatic);
diff --git a/engines/mutationofjb/metaengine.cpp b/engines/mutationofjb/metaengine.cpp
index 453bf28929..9f23d23755 100644
--- a/engines/mutationofjb/metaengine.cpp
+++ b/engines/mutationofjb/metaengine.cpp
@@ -29,7 +29,7 @@
 
 #include "engines/advancedDetector.h"
 
-class MutationOfJBMetaEngineConnect : public AdvancedMetaEngineConnect {
+class MutationOfJBMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "mutationofjb";
@@ -83,7 +83,7 @@ public:
 };
 
 #if PLUGIN_ENABLED_DYNAMIC(MUTATIONOFJB)
-	REGISTER_PLUGIN_DYNAMIC(MUTATIONOFJB, PLUGIN_TYPE_ENGINE, MutationOfJBMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(MUTATIONOFJB, PLUGIN_TYPE_ENGINE, MutationOfJBMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(MUTATIONOFJB, PLUGIN_TYPE_ENGINE, MutationOfJBMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(MUTATIONOFJB, PLUGIN_TYPE_ENGINE, MutationOfJBMetaEngine);
 #endif
diff --git a/engines/neverhood/detection.cpp b/engines/neverhood/detection.cpp
index 036b3397a2..5730c94480 100644
--- a/engines/neverhood/detection.cpp
+++ b/engines/neverhood/detection.cpp
@@ -130,9 +130,9 @@ static const ExtraGuiOption neverhoodExtraGuiOption3 = {
 };
 
 
-class NeverhoodMetaEngine : public AdvancedMetaEngine {
+class NeverhoodMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	NeverhoodMetaEngine() : AdvancedMetaEngine(Neverhood::gameDescriptions, sizeof(ADGameDescription), neverhoodGames) {
+	NeverhoodMetaEngineStatic() : AdvancedMetaEngineStatic(Neverhood::gameDescriptions, sizeof(ADGameDescription), neverhoodGames) {
 		_guiOptions = GUIO2(GUIO_NOSUBTITLES, GUIO_NOMIDI);
 	}
 
@@ -151,7 +151,7 @@ public:
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
 };
 
-const ExtraGuiOptions NeverhoodMetaEngine::getExtraGuiOptions(const Common::String &target) const {
+const ExtraGuiOptions NeverhoodMetaEngineStatic::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	options.push_back(neverhoodExtraGuiOption1);
 	options.push_back(neverhoodExtraGuiOption2);
@@ -159,4 +159,4 @@ const ExtraGuiOptions NeverhoodMetaEngine::getExtraGuiOptions(const Common::Stri
 	return options;
 }
 
-REGISTER_PLUGIN_STATIC(NEVERHOOD_DETECTION, PLUGIN_TYPE_METAENGINE, NeverhoodMetaEngine);
+REGISTER_PLUGIN_STATIC(NEVERHOOD_DETECTION, PLUGIN_TYPE_METAENGINE, NeverhoodMetaEngineStatic);
diff --git a/engines/neverhood/metaengine.cpp b/engines/neverhood/metaengine.cpp
index 3f7ed7aca3..28992aedc3 100644
--- a/engines/neverhood/metaengine.cpp
+++ b/engines/neverhood/metaengine.cpp
@@ -57,7 +57,7 @@ bool NeverhoodEngine::applyResourceFixes() const {
 
 } // End of namespace Neverhood
 
-class NeverhoodMetaEngineConnect : public AdvancedMetaEngineConnect {
+class NeverhoodMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "neverhood";
@@ -72,7 +72,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool NeverhoodMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool NeverhoodMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -91,14 +91,14 @@ bool Neverhood::NeverhoodEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool NeverhoodMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool NeverhoodMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Neverhood::NeverhoodEngine(syst, desc);
 	}
 	return desc != 0;
 }
 
-SaveStateList NeverhoodMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList NeverhoodMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Neverhood::NeverhoodEngine::SaveHeader header;
 	Common::String pattern = target;
@@ -127,17 +127,17 @@ SaveStateList NeverhoodMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int NeverhoodMetaEngineConnect::getMaximumSaveSlot() const {
+int NeverhoodMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-void NeverhoodMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void NeverhoodMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::String filename = Neverhood::NeverhoodEngine::getSavegameFilename(target, slot);
 	saveFileMan->removeSavefile(filename.c_str());
 }
 
-SaveStateDescriptor NeverhoodMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor NeverhoodMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Neverhood::NeverhoodEngine::getSavegameFilename(target, slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
 
@@ -170,7 +170,7 @@ SaveStateDescriptor NeverhoodMetaEngineConnect::querySaveMetaInfos(const char *t
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(NEVERHOOD)
-	REGISTER_PLUGIN_DYNAMIC(NEVERHOOD, PLUGIN_TYPE_ENGINE, NeverhoodMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(NEVERHOOD, PLUGIN_TYPE_ENGINE, NeverhoodMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(NEVERHOOD, PLUGIN_TYPE_ENGINE, NeverhoodMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(NEVERHOOD, PLUGIN_TYPE_ENGINE, NeverhoodMetaEngine);
 #endif
diff --git a/engines/parallaction/detection.cpp b/engines/parallaction/detection.cpp
index 6f38b981da..3ebf1f410f 100644
--- a/engines/parallaction/detection.cpp
+++ b/engines/parallaction/detection.cpp
@@ -201,9 +201,9 @@ static const PARALLACTIONGameDescription gameDescriptions[] = {
 
 }
 
-class ParallactionMetaEngine : public AdvancedMetaEngine {
+class ParallactionMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	ParallactionMetaEngine() : AdvancedMetaEngine(Parallaction::gameDescriptions, sizeof(Parallaction::PARALLACTIONGameDescription), parallactionGames) {
+	ParallactionMetaEngineStatic() : AdvancedMetaEngineStatic(Parallaction::gameDescriptions, sizeof(Parallaction::PARALLACTIONGameDescription), parallactionGames) {
 		_guiOptions = GUIO1(GUIO_NOLAUNCHLOAD);
 	}
 
@@ -220,4 +220,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(PARALLACTION_DETECTION, PLUGIN_TYPE_METAENGINE, ParallactionMetaEngine);
+REGISTER_PLUGIN_STATIC(PARALLACTION_DETECTION, PLUGIN_TYPE_METAENGINE, ParallactionMetaEngineStatic);
diff --git a/engines/parallaction/metaengine.cpp b/engines/parallaction/metaengine.cpp
index 42ec7d6520..82231a74aa 100644
--- a/engines/parallaction/metaengine.cpp
+++ b/engines/parallaction/metaengine.cpp
@@ -39,7 +39,7 @@ Common::Platform Parallaction::getPlatform() const { return _gameDescription->de
 
 } // End of namespace Parallaction
 
-class ParallactionMetaEngineConnect : public AdvancedMetaEngineConnect {
+class ParallactionMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "parallaction";
@@ -53,7 +53,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool ParallactionMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool ParallactionMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave);
@@ -64,7 +64,7 @@ bool Parallaction::Parallaction::hasFeature(EngineFeature f) const {
 		(f == kSupportsReturnToLauncher);
 }
 
-bool ParallactionMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool ParallactionMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Parallaction::PARALLACTIONGameDescription *gd = (const Parallaction::PARALLACTIONGameDescription *)desc;
 	bool res = true;
 
@@ -83,7 +83,7 @@ bool ParallactionMetaEngineConnect::createInstance(OSystem *syst, Engine **engin
 	return res;
 }
 
-SaveStateList ParallactionMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList ParallactionMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 
 	Common::String pattern(ConfMan.getDomain(target)->getVal("gameid") + ".0##");
@@ -109,9 +109,9 @@ SaveStateList ParallactionMetaEngineConnect::listSaves(const char *target) const
 	return saveList;
 }
 
-int ParallactionMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+int ParallactionMetaEngine::getMaximumSaveSlot() const { return 99; }
 
-void ParallactionMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void ParallactionMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = ConfMan.getDomain(target)->getVal("gameid");
 	filename += Common::String::format(".0%02d", slot);
 
@@ -119,7 +119,7 @@ void ParallactionMetaEngineConnect::removeSaveState(const char *target, int slot
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(PARALLACTION)
-	REGISTER_PLUGIN_DYNAMIC(PARALLACTION, PLUGIN_TYPE_ENGINE, ParallactionMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(PARALLACTION, PLUGIN_TYPE_ENGINE, ParallactionMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(PARALLACTION, PLUGIN_TYPE_ENGINE, ParallactionMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(PARALLACTION, PLUGIN_TYPE_ENGINE, ParallactionMetaEngine);
 #endif
diff --git a/engines/pegasus/detection.cpp b/engines/pegasus/detection.cpp
index 090f7935d2..b14ea22bfb 100644
--- a/engines/pegasus/detection.cpp
+++ b/engines/pegasus/detection.cpp
@@ -91,9 +91,9 @@ static const PegasusGameDescription gameDescriptions[] = {
 } // End of namespace Pegasus
 
 
-class PegasusMetaEngine : public AdvancedMetaEngine {
+class PegasusMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	PegasusMetaEngine() : AdvancedMetaEngine(Pegasus::gameDescriptions, sizeof(Pegasus::PegasusGameDescription), pegasusGames) {
+	PegasusMetaEngineStatic() : AdvancedMetaEngineStatic(Pegasus::gameDescriptions, sizeof(Pegasus::PegasusGameDescription), pegasusGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -109,4 +109,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(PEGASUS_DETECTION, PLUGIN_TYPE_METAENGINE, PegasusMetaEngine);
+REGISTER_PLUGIN_STATIC(PEGASUS_DETECTION, PLUGIN_TYPE_METAENGINE, PegasusMetaEngineStatic);
diff --git a/engines/pegasus/metaengine.cpp b/engines/pegasus/metaengine.cpp
index d6616ec67c..33f0896307 100644
--- a/engines/pegasus/metaengine.cpp
+++ b/engines/pegasus/metaengine.cpp
@@ -61,7 +61,7 @@ bool PegasusEngine::isWindows() const {
 
 } // End of namespace Pegasus
 
-class PegasusMetaEngineConnect : public AdvancedMetaEngineConnect {
+class PegasusMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "pegasus";
@@ -76,14 +76,14 @@ public:
 	Common::KeymapArray initKeymaps(const char *target) const override;
 };
 
-bool PegasusMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool PegasusMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves)
 		|| (f == kSupportsLoadingDuringStartup)
 		|| (f == kSupportsDeleteSave);
 }
 
-SaveStateList PegasusMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList PegasusMetaEngine::listSaves(const char *target) const {
 	// The original had no pattern, so the user must rename theirs
 	// Note that we ignore the target because saves are compatible between
 	// all versions
@@ -102,17 +102,17 @@ SaveStateList PegasusMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void PegasusMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void PegasusMetaEngine::removeSaveState(const char *target, int slot) const {
 	// See listSaves() for info on the pattern
 	Common::StringArray fileNames = Pegasus::PegasusEngine::listSaveFiles();
 	g_system->getSavefileManager()->removeSavefile(fileNames[slot].c_str());
 }
 
-Common::KeymapArray PegasusMetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray PegasusMetaEngine::initKeymaps(const char *target) const {
 	return Pegasus::PegasusEngine::initKeymaps();
 }
 
-bool PegasusMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool PegasusMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Pegasus::PegasusGameDescription *gd = (const Pegasus::PegasusGameDescription *)desc;
 
 	if (gd)
@@ -122,7 +122,7 @@ bool PegasusMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, co
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(PEGASUS)
-	REGISTER_PLUGIN_DYNAMIC(PEGASUS, PLUGIN_TYPE_ENGINE, PegasusMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(PEGASUS, PLUGIN_TYPE_ENGINE, PegasusMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(PEGASUS, PLUGIN_TYPE_ENGINE, PegasusMetaEngineConnect);
-#endif
\ No newline at end of file
+	REGISTER_PLUGIN_STATIC(PEGASUS, PLUGIN_TYPE_ENGINE, PegasusMetaEngine);
+#endif
diff --git a/engines/petka/detection.cpp b/engines/petka/detection.cpp
index ee2db73a33..77e19299f2 100644
--- a/engines/petka/detection.cpp
+++ b/engines/petka/detection.cpp
@@ -33,9 +33,9 @@ static const PlainGameDescriptor petkaGames[] = {
 
 #include "petka/detection_tables.h"
 
-class PetkaMetaEngine : public AdvancedMetaEngine {
+class PetkaMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	PetkaMetaEngine() : AdvancedMetaEngine(Petka::gameDescriptions, sizeof(ADGameDescription), petkaGames) {
+	PetkaMetaEngineStatic() : AdvancedMetaEngineStatic(Petka::gameDescriptions, sizeof(ADGameDescription), petkaGames) {
 		_gameIds = petkaGames;
 		_maxScanDepth = 2;
 	}
@@ -53,4 +53,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(PETKA_DETECTION, PLUGIN_TYPE_METAENGINE, PetkaMetaEngine);
+REGISTER_PLUGIN_STATIC(PETKA_DETECTION, PLUGIN_TYPE_METAENGINE, PetkaMetaEngineStatic);
diff --git a/engines/petka/metaengine.cpp b/engines/petka/metaengine.cpp
index c4adc64296..18c3729ca6 100644
--- a/engines/petka/metaengine.cpp
+++ b/engines/petka/metaengine.cpp
@@ -27,7 +27,7 @@
 
 #include "petka/petka.h"
 
-class PetkaMetaEngineConnect : public AdvancedMetaEngineConnect {
+class PetkaMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "petka";
@@ -41,7 +41,7 @@ public:
 	virtual bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool PetkaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool PetkaMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave) ||
@@ -51,7 +51,7 @@ bool PetkaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSavesSupportPlayTime);
 }
 
-SaveStateList PetkaMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList PetkaMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::String pattern = Common::String::format("%s.s##", target);
 	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
@@ -76,11 +76,11 @@ SaveStateList PetkaMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void PetkaMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void PetkaMetaEngine::removeSaveState(const char *target, int slot) const {
 	g_system->getSavefileManager()->removeSavefile(Petka::generateSaveName(slot, target));
 }
 
-SaveStateDescriptor PetkaMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor PetkaMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(Petka::generateSaveName(slot, target)));
 
 	if (f) {
@@ -94,7 +94,7 @@ SaveStateDescriptor PetkaMetaEngineConnect::querySaveMetaInfos(const char *targe
 	return SaveStateDescriptor();
 }
 
-bool PetkaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool PetkaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc)
 		*engine = new Petka::PetkaEngine(syst, desc);
 
@@ -102,7 +102,7 @@ bool PetkaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, cons
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(PETKA)
-	REGISTER_PLUGIN_DYNAMIC(PETKA, PLUGIN_TYPE_ENGINE, PetkaMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(PETKA, PLUGIN_TYPE_ENGINE, PetkaMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(PETKA, PLUGIN_TYPE_ENGINE, PetkaMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(PETKA, PLUGIN_TYPE_ENGINE, PetkaMetaEngine);
 #endif
diff --git a/engines/pink/detection.cpp b/engines/pink/detection.cpp
index c6ffafa324..4d34fc7227 100644
--- a/engines/pink/detection.cpp
+++ b/engines/pink/detection.cpp
@@ -38,9 +38,9 @@ static const char *directoryGlobs[] = {
 };
 
 
-class PinkMetaEngine : public AdvancedMetaEngine {
+class PinkMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	PinkMetaEngine() : AdvancedMetaEngine(Pink::gameDescriptions, sizeof(ADGameDescription), pinkGames) {
+	PinkMetaEngineStatic() : AdvancedMetaEngineStatic(Pink::gameDescriptions, sizeof(ADGameDescription), pinkGames) {
 		_gameIds = pinkGames;
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
@@ -59,4 +59,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(PINK_DETECTION, PLUGIN_TYPE_METAENGINE, PinkMetaEngine);
+REGISTER_PLUGIN_STATIC(PINK_DETECTION, PLUGIN_TYPE_METAENGINE, PinkMetaEngineStatic);
diff --git a/engines/pink/metaengine.cpp b/engines/pink/metaengine.cpp
index 3891e7049d..3ccc372348 100644
--- a/engines/pink/metaengine.cpp
+++ b/engines/pink/metaengine.cpp
@@ -34,7 +34,7 @@ Common::Language PinkEngine::getLanguage() const {
 
 } // End of Namespace Pink
 
-class PinkMetaEngineConnect : public AdvancedMetaEngineConnect {
+class PinkMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "pink";
@@ -50,7 +50,7 @@ public:
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 };
 
-bool PinkMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool PinkMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsDeleteSave) ||
@@ -62,7 +62,7 @@ bool PinkMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSimpleSavesNames);
 }
 
-SaveStateList PinkMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList PinkMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::String pattern = Common::String::format("%s.s##", target);
 	Common::StringArray filenames = saveFileMan->listSavefiles(pattern);
@@ -87,11 +87,11 @@ SaveStateList PinkMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void PinkMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void PinkMetaEngine::removeSaveState(const char *target, int slot) const {
 	g_system->getSavefileManager()->removeSavefile(Pink::generateSaveName(slot, target));
 }
 
-SaveStateDescriptor PinkMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor PinkMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::ScopedPtr<Common::InSaveFile> f(g_system->getSavefileManager()->openForLoading(Pink::generateSaveName(slot, target)));
 
 	if (f) {
@@ -105,7 +105,7 @@ SaveStateDescriptor PinkMetaEngineConnect::querySaveMetaInfos(const char *target
 	return SaveStateDescriptor();
 }
 
-bool PinkMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool PinkMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc)
 		*engine = new Pink::PinkEngine(syst, desc);
 
@@ -113,8 +113,8 @@ bool PinkMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(PINK)
-	REGISTER_PLUGIN_DYNAMIC(PINK, PLUGIN_TYPE_ENGINE, PinkMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(PINK, PLUGIN_TYPE_ENGINE, PinkMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(PINK, PLUGIN_TYPE_ENGINE, PinkMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(PINK, PLUGIN_TYPE_ENGINE, PinkMetaEngine);
 #endif
 
diff --git a/engines/plumbers/detection.cpp b/engines/plumbers/detection.cpp
index 435b0f1b68..70c49f56ce 100644
--- a/engines/plumbers/detection.cpp
+++ b/engines/plumbers/detection.cpp
@@ -62,9 +62,9 @@ static const ADGameDescription gameDescriptions[] = {
 
 } // End of namespace Plumbers
 
-class PlumbersMetaEngine : public AdvancedMetaEngine {
+class PlumbersMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	PlumbersMetaEngine() : AdvancedMetaEngine(Plumbers::gameDescriptions, sizeof(ADGameDescription), plumbersGames) {
+	PlumbersMetaEngineStatic() : AdvancedMetaEngineStatic(Plumbers::gameDescriptions, sizeof(ADGameDescription), plumbersGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -80,4 +80,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(PLUMBERS_DETECTION, PLUGIN_TYPE_METAENGINE, PlumbersMetaEngine);
+REGISTER_PLUGIN_STATIC(PLUMBERS_DETECTION, PLUGIN_TYPE_METAENGINE, PlumbersMetaEngineStatic);
diff --git a/engines/plumbers/metaengine.cpp b/engines/plumbers/metaengine.cpp
index a5c745c122..fd775cc855 100644
--- a/engines/plumbers/metaengine.cpp
+++ b/engines/plumbers/metaengine.cpp
@@ -31,7 +31,7 @@ const char *PlumbersGame::getGameId() const { return _gameDescription->gameId; }
 Common::Platform PlumbersGame::getPlatform() const { return _gameDescription->platform; }
 } // End of namespace Plumbers
 
-class PlumbersMetaEngineConnect : public AdvancedMetaEngineConnect {
+class PlumbersMetaEngine : public AdvancedMetaEngine {
 	const char *getName() const override {
 		return "plumbers";
 	}
@@ -40,19 +40,19 @@ class PlumbersMetaEngineConnect : public AdvancedMetaEngineConnect {
 	bool hasFeature(MetaEngineFeature f) const override;
 };
 
-bool PlumbersMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool PlumbersMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc)
 		*engine = new Plumbers::PlumbersGame(syst, desc);
 
 	return desc != nullptr;
 }
 
-bool PlumbersMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool PlumbersMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return false;
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(PLUMBERS)
-	REGISTER_PLUGIN_DYNAMIC(PLUMBERS, PLUGIN_TYPE_ENGINE, PlumbersMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(PLUMBERS, PLUGIN_TYPE_ENGINE, PlumbersMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(PLUMBERS, PLUGIN_TYPE_ENGINE, PlumbersMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(PLUMBERS, PLUGIN_TYPE_ENGINE, PlumbersMetaEngine);
 #endif
diff --git a/engines/prince/detection.cpp b/engines/prince/detection.cpp
index e04048e5fb..8de2113146 100644
--- a/engines/prince/detection.cpp
+++ b/engines/prince/detection.cpp
@@ -121,9 +121,9 @@ const static char *directoryGlobs[] = {
 	0
 };
 
-class PrinceMetaEngine : public AdvancedMetaEngine {
+class PrinceMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	PrinceMetaEngine() : AdvancedMetaEngine(Prince::gameDescriptions, sizeof(Prince::PrinceGameDescription), princeGames) {
+	PrinceMetaEngineStatic() : AdvancedMetaEngineStatic(Prince::gameDescriptions, sizeof(Prince::PrinceGameDescription), princeGames) {
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -141,4 +141,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(PRINCE_DETECTION, PLUGIN_TYPE_METAENGINE, PrinceMetaEngine);
+REGISTER_PLUGIN_STATIC(PRINCE_DETECTION, PLUGIN_TYPE_METAENGINE, PrinceMetaEngineStatic);
diff --git a/engines/prince/metaengine.cpp b/engines/prince/metaengine.cpp
index 23ea7e7667..810dec7070 100644
--- a/engines/prince/metaengine.cpp
+++ b/engines/prince/metaengine.cpp
@@ -44,7 +44,7 @@ Common::Language PrinceEngine::getLanguage() const {
 
 } // End of namespace Prince
 
-class PrinceMetaEngineConnect : public AdvancedMetaEngineConnect {
+class PrinceMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "prince";
@@ -59,7 +59,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool PrinceMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool PrinceMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsDeleteSave) ||
 		(f == kSavesSupportMetaInfo) ||
@@ -78,7 +78,7 @@ bool Prince::PrinceEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsReturnToLauncher);
 }
 
-SaveStateList PrinceMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList PrinceMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -120,7 +120,7 @@ SaveStateList PrinceMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor PrinceMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor PrinceMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(fileName);
 
@@ -154,12 +154,12 @@ SaveStateDescriptor PrinceMetaEngineConnect::querySaveMetaInfos(const char *targ
 	return SaveStateDescriptor();
 }
 
-void PrinceMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void PrinceMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-bool PrinceMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool PrinceMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	using namespace Prince;
 	const PrinceGameDescription *gd = (const PrinceGameDescription *)desc;
 	if (gd) {
@@ -169,7 +169,7 @@ bool PrinceMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, con
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(PRINCE)
-	REGISTER_PLUGIN_DYNAMIC(PRINCE, PLUGIN_TYPE_ENGINE, PrinceMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(PRINCE, PLUGIN_TYPE_ENGINE, PrinceMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(PRINCE, PLUGIN_TYPE_ENGINE, PrinceMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(PRINCE, PLUGIN_TYPE_ENGINE, PrinceMetaEngine);
 #endif
diff --git a/engines/queen/detection.cpp b/engines/queen/detection.cpp
index ccafc68a47..f6afbb9cb5 100644
--- a/engines/queen/detection.cpp
+++ b/engines/queen/detection.cpp
@@ -468,9 +468,9 @@ static const QueenGameDescription gameDescriptions[] = {
 
 } // End of namespace Queen
 
-class QueenMetaEngine : public AdvancedMetaEngine {
+class QueenMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	QueenMetaEngine() : AdvancedMetaEngine(Queen::gameDescriptions, sizeof(Queen::QueenGameDescription), queenGames, optionsList) {
+	QueenMetaEngineStatic() : AdvancedMetaEngineStatic(Queen::gameDescriptions, sizeof(Queen::QueenGameDescription), queenGames, optionsList) {
 	}
 
 	const char *getEngineId() const override {
@@ -488,7 +488,7 @@ public:
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
 };
 
-ADDetectedGame QueenMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
+ADDetectedGame QueenMetaEngineStatic::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	static ADGameDescription desc;
 
 	// Iterate over all files in the given directory
@@ -532,4 +532,4 @@ ADDetectedGame QueenMetaEngine::fallbackDetect(const FileMap &allFiles, const Co
 	return ADDetectedGame();
 }
 
-REGISTER_PLUGIN_STATIC(QUEEN_DETECTION, PLUGIN_TYPE_METAENGINE, QueenMetaEngine);
+REGISTER_PLUGIN_STATIC(QUEEN_DETECTION, PLUGIN_TYPE_METAENGINE, QueenMetaEngineStatic);
diff --git a/engines/queen/metaengine.cpp b/engines/queen/metaengine.cpp
index 8cdbbecda3..f1cdaded69 100644
--- a/engines/queen/metaengine.cpp
+++ b/engines/queen/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "queen/resource.h"
 #include "queen/detection.h"
 
-class QueenMetaEngineConnect : public AdvancedMetaEngineConnect {
+class QueenMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "queen";
@@ -43,14 +43,14 @@ public:
 	int getAutosaveSlot() const override { return 99; }
 };
 
-bool QueenMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool QueenMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
 		(f == kSupportsDeleteSave);
 }
 
-SaveStateList QueenMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList QueenMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	char saveDesc[32];
@@ -80,13 +80,13 @@ SaveStateList QueenMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void QueenMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void QueenMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("queen.s%02d", slot);
 
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-bool QueenMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool QueenMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Queen::QueenGameDescription *gd = (const Queen::QueenGameDescription *)desc;
 
 	if (gd)
@@ -96,8 +96,8 @@ bool QueenMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, cons
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(QUEEN)
-	REGISTER_PLUGIN_DYNAMIC(QUEEN, PLUGIN_TYPE_ENGINE, QueenMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(QUEEN, PLUGIN_TYPE_ENGINE, QueenMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(QUEEN, PLUGIN_TYPE_ENGINE, QueenMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(QUEEN, PLUGIN_TYPE_ENGINE, QueenMetaEngine);
 #endif
 
diff --git a/engines/saga/detection.cpp b/engines/saga/detection.cpp
index dec4adde27..25b58f254a 100644
--- a/engines/saga/detection.cpp
+++ b/engines/saga/detection.cpp
@@ -37,9 +37,9 @@ static const PlainGameDescriptor sagaGames[] = {
 
 #include "saga/detection_tables.h"
 
-class SagaMetaEngine : public AdvancedMetaEngine {
+class SagaMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	SagaMetaEngine() : AdvancedMetaEngine(Saga::gameDescriptions, sizeof(Saga::SAGAGameDescription), sagaGames) {
+	SagaMetaEngineStatic() : AdvancedMetaEngineStatic(Saga::gameDescriptions, sizeof(Saga::SAGAGameDescription), sagaGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -73,4 +73,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(SAGA_DETECTION, PLUGIN_TYPE_METAENGINE, SagaMetaEngine);
+REGISTER_PLUGIN_STATIC(SAGA_DETECTION, PLUGIN_TYPE_METAENGINE, SagaMetaEngineStatic);
diff --git a/engines/saga/metaengine.cpp b/engines/saga/metaengine.cpp
index 43d8b6bceb..0e6244d510 100644
--- a/engines/saga/metaengine.cpp
+++ b/engines/saga/metaengine.cpp
@@ -69,7 +69,7 @@ const ADGameFileDescription *SagaEngine::getFilesDescriptions() const { return _
 
 } // End of namespace Saga
 
-class SagaMetaEngineConnect : public AdvancedMetaEngineConnect {
+class SagaMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "saga";
@@ -78,7 +78,7 @@ public:
     bool hasFeature(MetaEngineFeature f) const override;
 
 	Common::Error createInstance(OSystem *syst, Engine **engine) const override {
-		return AdvancedMetaEngineConnect::createInstance(syst, engine);
+		return AdvancedMetaEngine::createInstance(syst, engine);
 	}
 	bool createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const override;
 
@@ -88,7 +88,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool SagaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool SagaMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -107,7 +107,7 @@ bool Saga::SagaEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool SagaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool SagaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Saga::SAGAGameDescription *gd = (const Saga::SAGAGameDescription *)desc;
 	if (gd) {
 		*engine = new Saga::SagaEngine(syst, gd);
@@ -115,7 +115,7 @@ bool SagaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return gd != 0;
 }
 
-SaveStateList SagaMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList SagaMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	char saveDesc[SAVE_TITLE_SIZE];
@@ -147,16 +147,16 @@ SaveStateList SagaMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int SagaMetaEngineConnect::getMaximumSaveSlot() const { return MAX_SAVES - 1; }
+int SagaMetaEngine::getMaximumSaveSlot() const { return MAX_SAVES - 1; }
 
-void SagaMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void SagaMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = target;
 	filename += Common::String::format(".s%02d", slot);
 
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor SagaMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor SagaMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	static char fileName[MAX_FILE_NAME];
 	sprintf(fileName, "%s.s%02d", target, slot);
 	char title[TITLESIZE];
@@ -231,9 +231,9 @@ SaveStateDescriptor SagaMetaEngineConnect::querySaveMetaInfos(const char *target
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(SAGA)
-	REGISTER_PLUGIN_DYNAMIC(SAGA, PLUGIN_TYPE_ENGINE, SagaMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(SAGA, PLUGIN_TYPE_ENGINE, SagaMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(SAGA, PLUGIN_TYPE_ENGINE, SagaMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(SAGA, PLUGIN_TYPE_ENGINE, SagaMetaEngine);
 #endif
 
 namespace Saga {
diff --git a/engines/sci/detection.cpp b/engines/sci/detection.cpp
index fab0ccd906..b1122debc5 100644
--- a/engines/sci/detection.cpp
+++ b/engines/sci/detection.cpp
@@ -403,9 +403,9 @@ bool OptionsWidget::save() {
 	return true;
 }
 
-class SciMetaEngine : public AdvancedMetaEngine {
+class SciMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	SciMetaEngine() : AdvancedMetaEngine(Sci::SciGameDescriptions, sizeof(ADGameDescription), s_sciGameTitles, optionsList) {
+	SciMetaEngineStatic() : AdvancedMetaEngineStatic(Sci::SciGameDescriptions, sizeof(ADGameDescription), s_sciGameTitles, optionsList) {
 		_maxScanDepth = 3;
 		_directoryGlobs = directoryGlobs;
 		_matchFullPaths = true;
@@ -434,18 +434,18 @@ public:
 	GUI::OptionsContainerWidget *buildEngineOptionsWidgetStatic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const override;
 };
 
-void SciMetaEngine::registerDefaultSettings(const Common::String &target) const {
-	AdvancedMetaEngine::registerDefaultSettings(target);
+void SciMetaEngineStatic::registerDefaultSettings(const Common::String &target) const {
+	AdvancedMetaEngineStatic::registerDefaultSettings(target);
 
 	for (const PopUpOptionsMap *entry = popUpOptionsList; entry->guioFlag; ++entry)
 		ConfMan.registerDefault(entry->configOption, entry->defaultState);
 }
 
-GUI::OptionsContainerWidget *SciMetaEngine::buildEngineOptionsWidgetStatic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
+GUI::OptionsContainerWidget *SciMetaEngineStatic::buildEngineOptionsWidgetStatic(GUI::GuiObject *boss, const Common::String &name, const Common::String &target) const {
 	return new OptionsWidget(boss, name, target);
 }
 
-ADDetectedGame SciMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
+ADDetectedGame SciMetaEngineStatic::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	/**
 	 * Fallback detection for Sci heavily depends on engine resources, so it's not possible
 	 * to use them without the engine present in a clean way.
@@ -455,7 +455,7 @@ ADDetectedGame SciMetaEngine::fallbackDetect(const FileMap &allFiles, const Comm
 	if (metaEnginePlugin) {
 		const Plugin *enginePlugin = PluginMan.getEngineFromMetaEngine(metaEnginePlugin);
 		if (enginePlugin) {
-			return enginePlugin->get<AdvancedMetaEngineConnect>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
+			return enginePlugin->get<AdvancedMetaEngine>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
 		} else {
 			static bool warn = true;
 			if (warn) {
@@ -470,4 +470,4 @@ ADDetectedGame SciMetaEngine::fallbackDetect(const FileMap &allFiles, const Comm
 
 } // End of namespace Sci
 
-REGISTER_PLUGIN_STATIC(SCI_DETECTION, PLUGIN_TYPE_METAENGINE, Sci::SciMetaEngine);
+REGISTER_PLUGIN_STATIC(SCI_DETECTION, PLUGIN_TYPE_METAENGINE, Sci::SciMetaEngineStatic);
diff --git a/engines/sci/metaengine.cpp b/engines/sci/metaengine.cpp
index c5ec465f60..73f0a9d625 100644
--- a/engines/sci/metaengine.cpp
+++ b/engines/sci/metaengine.cpp
@@ -296,7 +296,7 @@ static Common::String convertSierraGameId(Common::String sierraId, uint32 *gameF
 
 namespace Sci {
 
-class SciMetaEngineConnect : public AdvancedMetaEngineConnect {
+class SciMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "sci";
@@ -315,7 +315,7 @@ public:
 	virtual ADDetectedGame fallbackDetectExtern(uint md5Bytes, const FileMap &allFiles, const Common::FSList &fslist) const override;
 };
 
-bool SciMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool SciMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const GameIdStrToEnum *g = s_gameIdStrToEnum;
 	for (; g->gameidStr; ++g) {
 		if (0 == strcmp(desc->gameId, g->gameidStr)) {
@@ -327,7 +327,7 @@ bool SciMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return false;
 }
 
-bool SciMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool SciMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -352,7 +352,7 @@ bool SciEngine::hasFeature(EngineFeature f) const {
 		//  and some other times it won't work.
 }
 
-SaveStateList SciMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList SciMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -403,7 +403,7 @@ SaveStateList SciMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor SciMetaEngineConnect::querySaveMetaInfos(const char *target, int slotNr) const {
+SaveStateDescriptor SciMetaEngine::querySaveMetaInfos(const char *target, int slotNr) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slotNr);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
 	SaveStateDescriptor descriptor(slotNr, "");
@@ -465,9 +465,9 @@ SaveStateDescriptor SciMetaEngineConnect::querySaveMetaInfos(const char *target,
 	return descriptor;
 }
 
-int SciMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+int SciMetaEngine::getMaximumSaveSlot() const { return 99; }
 
-void SciMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void SciMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
@@ -548,7 +548,7 @@ static ADGameDescription s_fallbackDesc = {
 	GUIO3(GAMEOPTION_PREFER_DIGITAL_SFX, GAMEOPTION_ORIGINAL_SAVELOAD, GAMEOPTION_MIDI_MODE)
 };
 
-ADDetectedGame SciMetaEngineConnect::fallbackDetectExtern(uint md5Bytes, const FileMap &allFiles, const Common::FSList &fslist) const {
+ADDetectedGame SciMetaEngine::fallbackDetectExtern(uint md5Bytes, const FileMap &allFiles, const Common::FSList &fslist) const {
 	bool foundResMap = false;
 	bool foundRes000 = false;
 
@@ -716,7 +716,7 @@ ADDetectedGame SciMetaEngineConnect::fallbackDetectExtern(uint md5Bytes, const F
 } // End of namespace Sci
 
 #if PLUGIN_ENABLED_DYNAMIC(SCI)
-	REGISTER_PLUGIN_DYNAMIC(SCI, PLUGIN_TYPE_ENGINE, Sci::SciMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(SCI, PLUGIN_TYPE_ENGINE, Sci::SciMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(SCI, PLUGIN_TYPE_ENGINE, Sci::SciMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(SCI, PLUGIN_TYPE_ENGINE, Sci::SciMetaEngine);
 #endif
diff --git a/engines/scumm/detection.cpp b/engines/scumm/detection.cpp
index 0b316898b7..edae12e2a7 100644
--- a/engines/scumm/detection.cpp
+++ b/engines/scumm/detection.cpp
@@ -54,7 +54,7 @@
 
 using namespace Scumm;
 
-class ScummMetaEngine : public MetaEngine {
+class ScummMetaEngineStatic : public MetaEngineStatic {
 public:
 	const char *getEngineId() const override {
 		return "scumm";
@@ -70,11 +70,11 @@ public:
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
 };
 
-PlainGameList ScummMetaEngine::getSupportedGames() const {
+PlainGameList ScummMetaEngineStatic::getSupportedGames() const {
 	return PlainGameList(gameDescriptions);
 }
 
-PlainGameDescriptor ScummMetaEngine::findGame(const char *gameid) const {
+PlainGameDescriptor ScummMetaEngineStatic::findGame(const char *gameid) const {
 	return Engines::findGameID(gameid, gameDescriptions, obsoleteGameIDsTable);
 }
 
@@ -104,7 +104,7 @@ static Common::String generatePreferredTarget(const DetectorResult &x) {
 	return res;
 }
 
-DetectedGames ScummMetaEngine::detectGames(const Common::FSList &fslist) const {
+DetectedGames ScummMetaEngineStatic::detectGames(const Common::FSList &fslist) const {
 	DetectedGames detectedGames;
 	Common::List<DetectorResult> results;
 	::detectGames(fslist, results, 0);
@@ -129,7 +129,7 @@ DetectedGames ScummMetaEngine::detectGames(const Common::FSList &fslist) const {
 	return detectedGames;
 }
 
-const char *ScummMetaEngine::getName() const {
+const char *ScummMetaEngineStatic::getName() const {
 	return "SCUMM ["
 
 #if defined(ENABLE_SCUMM_7_8) && defined(ENABLE_HE)
@@ -149,7 +149,7 @@ const char *ScummMetaEngine::getName() const {
 		"]";
 }
 
-const char *ScummMetaEngine::getOriginalCopyright() const {
+const char *ScummMetaEngineStatic::getOriginalCopyright() const {
 	return "LucasArts SCUMM Games (C) LucasArts\n"
 	       "Humongous SCUMM Games (C) Humongous";
 }
@@ -168,7 +168,7 @@ static const ExtraGuiOption mmnesObjectLabelsOption = {
 	false
 };
 
-const ExtraGuiOptions ScummMetaEngine::getExtraGuiOptions(const Common::String &target) const {
+const ExtraGuiOptions ScummMetaEngineStatic::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	if (target.empty() || ConfMan.get("gameid", target) == "comi") {
 		options.push_back(comiObjectLabelsOption);
@@ -179,4 +179,4 @@ const ExtraGuiOptions ScummMetaEngine::getExtraGuiOptions(const Common::String &
 	return options;
 }
 
-REGISTER_PLUGIN_STATIC(SCUMM_DETECTION, PLUGIN_TYPE_METAENGINE, ScummMetaEngine);
+REGISTER_PLUGIN_STATIC(SCUMM_DETECTION, PLUGIN_TYPE_METAENGINE, ScummMetaEngineStatic);
diff --git a/engines/scumm/metaengine.cpp b/engines/scumm/metaengine.cpp
index 027287ede0..e6af0f9cd4 100644
--- a/engines/scumm/metaengine.cpp
+++ b/engines/scumm/metaengine.cpp
@@ -216,11 +216,11 @@ bool ScummEngine::isMacM68kIMuse() const {
 
 using namespace Scumm;
 
-const char *ScummMetaEngineConnect::getName() const {
+const char *ScummMetaEngine::getName() const {
     return "Scumm";
 }
 
-bool ScummMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool ScummMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -246,7 +246,7 @@ bool ScummEngine::hasFeature(EngineFeature f) const {
  *
  * This is heavily based on our MD5 detection scheme.
  */
-Common::Error ScummMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+Common::Error ScummMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
 	assert(syst);
 	assert(engine);
 	const char *gameid = ConfMan.get("gameid").c_str();
@@ -440,13 +440,13 @@ Common::Error ScummMetaEngineConnect::createInstance(OSystem *syst, Engine **eng
 	return Common::kNoError;
 }
 
-int ScummMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+int ScummMetaEngine::getMaximumSaveSlot() const { return 99; }
 
 namespace Scumm {
 bool getSavegameName(Common::InSaveFile *in, Common::String &desc, int heversion);
 } // End of namespace Scumm
 
-SaveStateList ScummMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList ScummMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -475,12 +475,12 @@ SaveStateList ScummMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-void ScummMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void ScummMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = ScummEngine::makeSavegameName(target, slot, false);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor ScummMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor ScummMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String saveDesc;
 	Graphics::Surface *thumbnail = nullptr;
 	SaveStateMetaInfos infos;
@@ -521,7 +521,7 @@ SaveStateDescriptor ScummMetaEngineConnect::querySaveMetaInfos(const char *targe
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(SCUMM)
-	REGISTER_PLUGIN_DYNAMIC(SCUMM, PLUGIN_TYPE_ENGINE, ScummMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(SCUMM, PLUGIN_TYPE_ENGINE, ScummMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(SCUMM, PLUGIN_TYPE_ENGINE, ScummMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(SCUMM, PLUGIN_TYPE_ENGINE, ScummMetaEngine);
 #endif
diff --git a/engines/scumm/metaengine.h b/engines/scumm/metaengine.h
index af18d934cc..d7f190a31b 100644
--- a/engines/scumm/metaengine.h
+++ b/engines/scumm/metaengine.h
@@ -25,7 +25,7 @@
 
 #include "engines/metaengine.h"
 
-class ScummMetaEngineConnect : public MetaEngineConnect {
+class ScummMetaEngine : public MetaEngine {
     virtual const char *getName() const override;
 
     bool hasFeature(MetaEngineFeature f) const override;
diff --git a/engines/sherlock/detection.cpp b/engines/sherlock/detection.cpp
index 7047838e24..3e3bc162c8 100644
--- a/engines/sherlock/detection.cpp
+++ b/engines/sherlock/detection.cpp
@@ -121,9 +121,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 
 #include "sherlock/detection_tables.h"
 
-class SherlockMetaEngine : public AdvancedMetaEngine {
+class SherlockMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	SherlockMetaEngine() : AdvancedMetaEngine(Sherlock::gameDescriptions, sizeof(Sherlock::SherlockGameDescription),
+	SherlockMetaEngineStatic() : AdvancedMetaEngineStatic(Sherlock::gameDescriptions, sizeof(Sherlock::SherlockGameDescription),
 		sherlockGames, optionsList) {}
 
 	const char *getEngineId() const override {
@@ -140,4 +140,4 @@ public:
 };
 
 
-REGISTER_PLUGIN_STATIC(SHERLOCK_DETECTION, PLUGIN_TYPE_METAENGINE, SherlockMetaEngine);
+REGISTER_PLUGIN_STATIC(SHERLOCK_DETECTION, PLUGIN_TYPE_METAENGINE, SherlockMetaEngineStatic);
diff --git a/engines/sherlock/metaengine.cpp b/engines/sherlock/metaengine.cpp
index e5fa0f1ea6..6ce2029735 100644
--- a/engines/sherlock/metaengine.cpp
+++ b/engines/sherlock/metaengine.cpp
@@ -48,7 +48,7 @@ Common::Language SherlockEngine::getLanguage() const {
 } // End of namespace Sherlock
 
 
-class SherlockMetaEngineConnect : public AdvancedMetaEngineConnect {
+class SherlockMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "sherlock";
@@ -85,7 +85,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool SherlockMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool SherlockMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Sherlock::SherlockGameDescription *gd = (const Sherlock::SherlockGameDescription *)desc;
 	if (gd) {
 		switch (gd->gameID) {
@@ -103,7 +103,7 @@ bool SherlockMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, c
 	return gd != 0;
 }
 
-bool SherlockMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool SherlockMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -126,20 +126,20 @@ bool Sherlock::SherlockEngine::isDemo() const {
 	return _gameDescription->desc.flags & ADGF_DEMO;
 }
 
-SaveStateList SherlockMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList SherlockMetaEngine::listSaves(const char *target) const {
 	return Sherlock::SaveManager::getSavegameList(target);
 }
 
-int SherlockMetaEngineConnect::getMaximumSaveSlot() const {
+int SherlockMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVEGAME_SLOTS;
 }
 
-void SherlockMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void SherlockMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Sherlock::SaveManager(nullptr, target).generateSaveName(slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor SherlockMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor SherlockMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Sherlock::SaveManager(nullptr, target).generateSaveName(slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
 
@@ -165,7 +165,7 @@ SaveStateDescriptor SherlockMetaEngineConnect::querySaveMetaInfos(const char *ta
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(SHERLOCK)
-	REGISTER_PLUGIN_DYNAMIC(SHERLOCK, PLUGIN_TYPE_ENGINE, SherlockMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(SHERLOCK, PLUGIN_TYPE_ENGINE, SherlockMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(SHERLOCK, PLUGIN_TYPE_ENGINE, SherlockMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(SHERLOCK, PLUGIN_TYPE_ENGINE, SherlockMetaEngine);
 #endif
diff --git a/engines/sky/detection.cpp b/engines/sky/detection.cpp
index 8db7d3f35d..e8140589fb 100644
--- a/engines/sky/detection.cpp
+++ b/engines/sky/detection.cpp
@@ -65,7 +65,7 @@ static const SkyVersion skyVersions[] = {
 	{ 0, 0, 0, 0, 0 }
 };
 
-class SkyMetaEngine : public MetaEngine {
+class SkyMetaEngineStatic : public MetaEngineStatic {
 public:
 	const char *getName() const override;
 	const char *getOriginalCopyright() const override;
@@ -80,21 +80,21 @@ public:
 	DetectedGames detectGames(const Common::FSList &fslist) const override;
 };
 
-const char *SkyMetaEngine::getName() const {
+const char *SkyMetaEngineStatic::getName() const {
 	return "Beneath a Steel Sky";
 }
 
-const char *SkyMetaEngine::getOriginalCopyright() const {
+const char *SkyMetaEngineStatic::getOriginalCopyright() const {
 	return "Beneath a Steel Sky (C) Revolution";
 }
 
-PlainGameList SkyMetaEngine::getSupportedGames() const {
+PlainGameList SkyMetaEngineStatic::getSupportedGames() const {
 	PlainGameList games;
 	games.push_back(skySetting);
 	return games;
 }
 
-const ExtraGuiOptions SkyMetaEngine::getExtraGuiOptions(const Common::String &target) const {
+const ExtraGuiOptions SkyMetaEngineStatic::getExtraGuiOptions(const Common::String &target) const {
 	Common::String guiOptions;
 	ExtraGuiOptions options;
 
@@ -113,13 +113,13 @@ const ExtraGuiOptions SkyMetaEngine::getExtraGuiOptions(const Common::String &ta
 	return options;
 }
 
-PlainGameDescriptor SkyMetaEngine::findGame(const char *gameid) const {
+PlainGameDescriptor SkyMetaEngineStatic::findGame(const char *gameid) const {
 	if (0 == scumm_stricmp(gameid, skySetting.gameId))
 		return skySetting;
 	return PlainGameDescriptor::empty();
 }
 
-DetectedGames SkyMetaEngine::detectGames(const Common::FSList &fslist) const {
+DetectedGames SkyMetaEngineStatic::detectGames(const Common::FSList &fslist) const {
 	DetectedGames detectedGames;
 	bool hasSkyDsk = false;
 	bool hasSkyDnr = false;
@@ -175,4 +175,4 @@ DetectedGames SkyMetaEngine::detectGames(const Common::FSList &fslist) const {
 	return detectedGames;
 }
 
-REGISTER_PLUGIN_STATIC(SKY_DETECTION, PLUGIN_TYPE_METAENGINE, SkyMetaEngine);
+REGISTER_PLUGIN_STATIC(SKY_DETECTION, PLUGIN_TYPE_METAENGINE, SkyMetaEngineStatic);
diff --git a/engines/sky/metaengine.cpp b/engines/sky/metaengine.cpp
index f4708e8f30..c1ba427048 100644
--- a/engines/sky/metaengine.cpp
+++ b/engines/sky/metaengine.cpp
@@ -35,7 +35,7 @@
 #include "sky/control.h"
 #include "sky/sky.h"
 
-class SkyMetaEngineConnect : public MetaEngineConnect {
+class SkyMetaEngine : public MetaEngine {
     const char *getName() const override {
         return "sky";
     }
@@ -51,7 +51,7 @@ class SkyMetaEngineConnect : public MetaEngineConnect {
     Common::KeymapArray initKeymaps(const char *target) const override;
 };
 
-bool SkyMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool SkyMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -65,7 +65,7 @@ bool Sky::SkyEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-Common::KeymapArray SkyMetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray SkyMetaEngine::initKeymaps(const char *target) const {
 	using namespace Common;
 	using namespace Sky;
 
@@ -132,13 +132,13 @@ Common::KeymapArray SkyMetaEngineConnect::initKeymaps(const char *target) const
 	return keymaps;
 }
 
-Common::Error SkyMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+Common::Error SkyMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
 	assert(engine);
 	*engine = new Sky::SkyEngine(syst);
 	return Common::kNoError;
 }
 
-SaveStateList SkyMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList SkyMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	SaveStateList saveList;
 
@@ -183,9 +183,9 @@ SaveStateList SkyMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int SkyMetaEngineConnect::getMaximumSaveSlot() const { return MAX_SAVE_GAMES; }
+int SkyMetaEngine::getMaximumSaveSlot() const { return MAX_SAVE_GAMES; }
 
-void SkyMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void SkyMetaEngine::removeSaveState(const char *target, int slot) const {
 	if (slot == 0)	// do not delete the auto save
 		return;
 
@@ -233,9 +233,9 @@ void SkyMetaEngineConnect::removeSaveState(const char *target, int slot) const {
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(SKY)
-	REGISTER_PLUGIN_DYNAMIC(SKY, PLUGIN_TYPE_ENGINE, SkyMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(SKY, PLUGIN_TYPE_ENGINE, SkyMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(SKY, PLUGIN_TYPE_ENGINE, SkyMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(SKY, PLUGIN_TYPE_ENGINE, SkyMetaEngine);
 #endif
 
 namespace Sky {
diff --git a/engines/sludge/detection.cpp b/engines/sludge/detection.cpp
index 8ab37da31c..c5392f600f 100644
--- a/engines/sludge/detection.cpp
+++ b/engines/sludge/detection.cpp
@@ -65,9 +65,9 @@ static Sludge::SludgeGameDescription s_fallbackDesc =
 
 static char s_fallbackFileNameBuffer[51];
 
-class SludgeMetaEngine : public AdvancedMetaEngine {
+class SludgeMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	SludgeMetaEngine() : AdvancedMetaEngine(Sludge::gameDescriptions, sizeof(Sludge::SludgeGameDescription), sludgeGames) {
+	SludgeMetaEngineStatic() : AdvancedMetaEngineStatic(Sludge::gameDescriptions, sizeof(Sludge::SludgeGameDescription), sludgeGames) {
 		_maxScanDepth = 1;
 	}
 
@@ -87,7 +87,7 @@ public:
 	ADDetectedGame fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const override;
 };
 
-ADDetectedGame SludgeMetaEngine::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
+ADDetectedGame SludgeMetaEngineStatic::fallbackDetect(const FileMap &allFiles, const Common::FSList &fslist) const {
 	// reset fallback description
 	s_fallbackDesc.desc.gameId = "sludge";
 	s_fallbackDesc.desc.extra = "";
@@ -146,4 +146,4 @@ ADDetectedGame SludgeMetaEngine::fallbackDetect(const FileMap &allFiles, const C
 	return ADDetectedGame();
 }
 
-REGISTER_PLUGIN_STATIC(SLUDGE_DETECTION, PLUGIN_TYPE_METAENGINE, SludgeMetaEngine);
+REGISTER_PLUGIN_STATIC(SLUDGE_DETECTION, PLUGIN_TYPE_METAENGINE, SludgeMetaEngineStatic);
diff --git a/engines/sludge/metaengine.cpp b/engines/sludge/metaengine.cpp
index 96385daea5..26f9295a53 100644
--- a/engines/sludge/metaengine.cpp
+++ b/engines/sludge/metaengine.cpp
@@ -40,7 +40,7 @@ const char *SludgeEngine::getGameFile() const {
 
 } // End of namespace Sludge
 
-class SludgeMetaEngineConnect : public AdvancedMetaEngineConnect {
+class SludgeMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "sludge";
@@ -56,7 +56,7 @@ public:
 };
 
 #if PLUGIN_ENABLED_DYNAMIC(SLUDGE)
-	REGISTER_PLUGIN_DYNAMIC(SLUDGE, PLUGIN_TYPE_ENGINE, SludgeMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(SLUDGE, PLUGIN_TYPE_ENGINE, SludgeMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(SLUDGE, PLUGIN_TYPE_ENGINE, SludgeMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(SLUDGE, PLUGIN_TYPE_ENGINE, SludgeMetaEngine);
 #endif
diff --git a/engines/startrek/detection.cpp b/engines/startrek/detection.cpp
index 587fda7115..73caac797e 100644
--- a/engines/startrek/detection.cpp
+++ b/engines/startrek/detection.cpp
@@ -287,9 +287,9 @@ static const StarTrekGameDescription gameDescriptions[] = {
 
 } // End of namespace StarTrek
 
-class StarTrekMetaEngine : public AdvancedMetaEngine {
+class StarTrekMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	StarTrekMetaEngine() : AdvancedMetaEngine(StarTrek::gameDescriptions, sizeof(StarTrek::StarTrekGameDescription), starTrekGames) {
+	StarTrekMetaEngineStatic() : AdvancedMetaEngineStatic(StarTrek::gameDescriptions, sizeof(StarTrek::StarTrekGameDescription), starTrekGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -307,4 +307,4 @@ public:
 
 
 
-REGISTER_PLUGIN_STATIC(STARTREK_DETECTION, PLUGIN_TYPE_METAENGINE, StarTrekMetaEngine);
+REGISTER_PLUGIN_STATIC(STARTREK_DETECTION, PLUGIN_TYPE_METAENGINE, StarTrekMetaEngineStatic);
diff --git a/engines/startrek/metaengine.cpp b/engines/startrek/metaengine.cpp
index f7c5007a62..3775629358 100644
--- a/engines/startrek/metaengine.cpp
+++ b/engines/startrek/metaengine.cpp
@@ -54,7 +54,7 @@ Common::Language StarTrekEngine::getLanguage() const {
 
 } // End of Namespace StarTrek
 
-class StarTrekMetaEngineConnect : public AdvancedMetaEngineConnect {
+class StarTrekMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "startrek";
@@ -69,7 +69,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool StarTrekMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool StarTrekMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 	    (f == kSupportsLoadingDuringStartup) ||
@@ -81,7 +81,7 @@ bool StarTrekMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 	    (f == kSimpleSavesNames);
 }
 
-bool StarTrekMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool StarTrekMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const StarTrek::StarTrekGameDescription *gd = (const StarTrek::StarTrekGameDescription *)desc;
 
 	*engine = new StarTrek::StarTrekEngine(syst, gd);
@@ -89,7 +89,7 @@ bool StarTrekMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, c
 	return (gd != 0);
 }
 
-SaveStateList StarTrekMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList StarTrekMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -132,16 +132,16 @@ SaveStateList StarTrekMetaEngineConnect::listSaves(const char *target) const {
 }
 
 
-int StarTrekMetaEngineConnect::getMaximumSaveSlot() const {
+int StarTrekMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-void StarTrekMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void StarTrekMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-SaveStateDescriptor StarTrekMetaEngineConnect::querySaveMetaInfos(const char *target, int slotNr) const {
+SaveStateDescriptor StarTrekMetaEngine::querySaveMetaInfos(const char *target, int slotNr) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slotNr);
 
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(fileName);
@@ -200,7 +200,7 @@ SaveStateDescriptor StarTrekMetaEngineConnect::querySaveMetaInfos(const char *ta
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(STARTREK)
-    REGISTER_PLUGIN_DYNAMIC(STARTREK, PLUGIN_TYPE_ENGINE, StarTrekMetaEngineConnect);
+    REGISTER_PLUGIN_DYNAMIC(STARTREK, PLUGIN_TYPE_ENGINE, StarTrekMetaEngine);
 #else
-    REGISTER_PLUGIN_STATIC(STARTREK, PLUGIN_TYPE_ENGINE, StarTrekMetaEngineConnect);
+    REGISTER_PLUGIN_STATIC(STARTREK, PLUGIN_TYPE_ENGINE, StarTrekMetaEngine);
 #endif
diff --git a/engines/supernova/detection.cpp b/engines/supernova/detection.cpp
index ed0bf4bcf3..ef84049b02 100644
--- a/engines/supernova/detection.cpp
+++ b/engines/supernova/detection.cpp
@@ -101,9 +101,9 @@ static const ADGameDescription gameDescriptions[] = {
 };
 }
 
-class SupernovaMetaEngine: public AdvancedMetaEngine {
+class SupernovaMetaEngineStatic: public AdvancedMetaEngineStatic {
 public:
-	SupernovaMetaEngine() : AdvancedMetaEngine(Supernova::gameDescriptions, sizeof(ADGameDescription), supernovaGames, optionsList) {
+	SupernovaMetaEngineStatic() : AdvancedMetaEngineStatic(Supernova::gameDescriptions, sizeof(ADGameDescription), supernovaGames, optionsList) {
 	}
 
 	const char *getEngineId() const override {
@@ -120,4 +120,4 @@ public:
 };
 
 
-REGISTER_PLUGIN_STATIC(SUPERNOVA_DETECTION, PLUGIN_TYPE_METAENGINE, SupernovaMetaEngine);
+REGISTER_PLUGIN_STATIC(SUPERNOVA_DETECTION, PLUGIN_TYPE_METAENGINE, SupernovaMetaEngineStatic);
diff --git a/engines/supernova/metaengine.cpp b/engines/supernova/metaengine.cpp
index 36c756c8c6..855a92d769 100644
--- a/engines/supernova/metaengine.cpp
+++ b/engines/supernova/metaengine.cpp
@@ -31,7 +31,7 @@
 
 #include "supernova/supernova.h"
 
-class SupernovaMetaEngineConnect : public AdvancedMetaEngineConnect {
+class SupernovaMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "supernova";
@@ -48,7 +48,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool SupernovaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool SupernovaMetaEngine::hasFeature(MetaEngineFeature f) const {
 	switch (f) {
 	case kSupportsLoadingDuringStartup:
 	case kSupportsListSaves:
@@ -63,7 +63,7 @@ bool SupernovaMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 	}
 }
 
-bool SupernovaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool SupernovaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Supernova::SupernovaEngine(syst);
 	}
@@ -71,7 +71,7 @@ bool SupernovaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine,
 	return desc != nullptr;
 }
 
-SaveStateList SupernovaMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList SupernovaMetaEngine::listSaves(const char *target) const {
 	Common::StringArray filenames;
 	Common::String pattern;
 	if (!strncmp(target, "msn1", 4))
@@ -109,7 +109,7 @@ SaveStateList SupernovaMetaEngineConnect::listSaves(const char *target) const {
 	return saveFileList;
 }
 
-void SupernovaMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void SupernovaMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename;
 	if (!strncmp(target, "msn1", 4))
 		filename = Common::String::format("msn_save.%03d", slot);
@@ -118,7 +118,7 @@ void SupernovaMetaEngineConnect::removeSaveState(const char *target, int slot) c
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor SupernovaMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor SupernovaMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName;
 	if (!strncmp(target, "msn1", 4))
 		fileName = Common::String::format("msn_save.%03d", slot);
@@ -177,7 +177,7 @@ SaveStateDescriptor SupernovaMetaEngineConnect::querySaveMetaInfos(const char *t
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(SUPERNOVA)
-    REGISTER_PLUGIN_DYNAMIC(SUPERNOVA, PLUGIN_TYPE_ENGINE, SupernovaMetaEngineConnect);
+    REGISTER_PLUGIN_DYNAMIC(SUPERNOVA, PLUGIN_TYPE_ENGINE, SupernovaMetaEngine);
 #else
-    REGISTER_PLUGIN_STATIC(SUPERNOVA, PLUGIN_TYPE_ENGINE, SupernovaMetaEngineConnect);
+    REGISTER_PLUGIN_STATIC(SUPERNOVA, PLUGIN_TYPE_ENGINE, SupernovaMetaEngine);
 #endif
diff --git a/engines/sword1/detection.cpp b/engines/sword1/detection.cpp
index abfaa57518..421cf5437e 100644
--- a/engines/sword1/detection.cpp
+++ b/engines/sword1/detection.cpp
@@ -71,7 +71,7 @@ static const char *const g_filesToCheck[NUM_FILES_TO_CHECK] = { // these files h
 	// the engine needs several more files to work, but checking these should be sufficient
 };
 
-class SwordMetaEngine : public MetaEngine {
+class SwordMetaEngineStatic : public MetaEngineStatic {
 public:
 	const char *getEngineId() const override {
 		return "sword1";
@@ -89,7 +89,7 @@ public:
 	DetectedGames detectGames(const Common::FSList &fslist) const override;
 };
 
-PlainGameList SwordMetaEngine::getSupportedGames() const {
+PlainGameList SwordMetaEngineStatic::getSupportedGames() const {
 	PlainGameList games;
 	games.push_back(sword1FullSettings);
 	games.push_back(sword1DemoSettings);
@@ -100,7 +100,7 @@ PlainGameList SwordMetaEngine::getSupportedGames() const {
 	return games;
 }
 
-PlainGameDescriptor SwordMetaEngine::findGame(const char *gameId) const {
+PlainGameDescriptor SwordMetaEngineStatic::findGame(const char *gameId) const {
 	if (0 == scumm_stricmp(gameId, sword1FullSettings.gameId))
 		return sword1FullSettings;
 	if (0 == scumm_stricmp(gameId, sword1DemoSettings.gameId))
@@ -133,7 +133,7 @@ void Sword1CheckDirectory(const Common::FSList &fslist, bool *filesFound) {
 	}
 }
 
-DetectedGames SwordMetaEngine::detectGames(const Common::FSList &fslist) const {
+DetectedGames SwordMetaEngineStatic::detectGames(const Common::FSList &fslist) const {
 	int i, j;
 	DetectedGames detectedGames;
 	bool filesFound[NUM_FILES_TO_CHECK];
@@ -217,4 +217,4 @@ DetectedGames SwordMetaEngine::detectGames(const Common::FSList &fslist) const {
 	return detectedGames;
 }
 
-REGISTER_PLUGIN_STATIC(SWORD1_DETECTION, PLUGIN_TYPE_METAENGINE, SwordMetaEngine);
+REGISTER_PLUGIN_STATIC(SWORD1_DETECTION, PLUGIN_TYPE_METAENGINE, SwordMetaEngineStatic);
diff --git a/engines/sword1/metaengine.cpp b/engines/sword1/metaengine.cpp
index 437b27fa9e..4f95ff15c4 100644
--- a/engines/sword1/metaengine.cpp
+++ b/engines/sword1/metaengine.cpp
@@ -31,7 +31,7 @@
 
 #include "engines/metaengine.h"
 
-class SwordMetaEngineConnect : public MetaEngineConnect {
+class SwordMetaEngine : public MetaEngine {
 public:
     const char *getName() const override {
 		return "sword1";
@@ -47,7 +47,7 @@ public:
 	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
 };
 
-bool SwordMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool SwordMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 	    (f == kSupportsLoadingDuringStartup) ||
@@ -65,13 +65,13 @@ bool Sword1::SwordEngine::hasFeature(EngineFeature f) const {
 	    (f == kSupportsLoadingDuringRuntime);
 }
 
-Common::Error SwordMetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+Common::Error SwordMetaEngine::createInstance(OSystem *syst, Engine **engine) const {
 	assert(engine);
 	*engine = new Sword1::SwordEngine(syst);
 	return Common::kNoError;
 }
 
-SaveStateList SwordMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList SwordMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	SaveStateList saveList;
 	char saveName[40];
@@ -99,13 +99,13 @@ SaveStateList SwordMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int SwordMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+int SwordMetaEngine::getMaximumSaveSlot() const { return 999; }
 
-void SwordMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void SwordMetaEngine::removeSaveState(const char *target, int slot) const {
 	g_system->getSavefileManager()->removeSavefile(Common::String::format("sword1.%03d", slot));
 }
 
-SaveStateDescriptor SwordMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor SwordMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("sword1.%03d", slot);
 	char name[40];
 	uint32 playTime = 0;
@@ -163,9 +163,9 @@ SaveStateDescriptor SwordMetaEngineConnect::querySaveMetaInfos(const char *targe
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(SWORD1)
-	REGISTER_PLUGIN_DYNAMIC(SWORD1, PLUGIN_TYPE_ENGINE, SwordMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(SWORD1, PLUGIN_TYPE_ENGINE, SwordMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(SWORD1, PLUGIN_TYPE_ENGINE, SwordMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(SWORD1, PLUGIN_TYPE_ENGINE, SwordMetaEngine);
 #endif
 
 namespace Sword1 {
diff --git a/engines/sword2/detection.cpp b/engines/sword2/detection.cpp
index 9f7abb1fea..e9b6203e50 100644
--- a/engines/sword2/detection.cpp
+++ b/engines/sword2/detection.cpp
@@ -36,7 +36,7 @@ static const ExtraGuiOption sword2ExtraGuiOption = {
 	false
 };
 
-class Sword2MetaEngine : public MetaEngine {
+class Sword2MetaEngineStatic : public MetaEngineStatic {
 public:
 	const char *getEngineId() const override {
 		return "sword2";
@@ -55,7 +55,7 @@ public:
 	DetectedGames detectGames(const Common::FSList &fslist) const override;
 };
 
-PlainGameList Sword2MetaEngine::getSupportedGames() const {
+PlainGameList Sword2MetaEngineStatic::getSupportedGames() const {
 	const Sword2::GameSettings *g = Sword2::sword2_settings;
 	PlainGameList games;
 	while (g->gameid) {
@@ -65,13 +65,13 @@ PlainGameList Sword2MetaEngine::getSupportedGames() const {
 	return games;
 }
 
-const ExtraGuiOptions Sword2MetaEngine::getExtraGuiOptions(const Common::String &target) const {
+const ExtraGuiOptions Sword2MetaEngineStatic::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	options.push_back(sword2ExtraGuiOption);
 	return options;
 }
 
-PlainGameDescriptor Sword2MetaEngine::findGame(const char *gameid) const {
+PlainGameDescriptor Sword2MetaEngineStatic::findGame(const char *gameid) const {
 	const Sword2::GameSettings *g = Sword2::sword2_settings;
 	while (g->gameid) {
 		if (0 == scumm_stricmp(gameid, g->gameid))
@@ -81,7 +81,7 @@ PlainGameDescriptor Sword2MetaEngine::findGame(const char *gameid) const {
 	return PlainGameDescriptor::of(g->gameid, g->description);
 }
 
-DetectedGames Sword2MetaEngine::detectGames(const Common::FSList &fslist) const {
+DetectedGames Sword2MetaEngineStatic::detectGames(const Common::FSList &fslist) const {
 	// The required game data files can be located in the game directory, or in
 	// a subdirectory called "clusters". In the latter case, we don't want to
 	// detect the game in that subdirectory, as this will detect the game twice
@@ -101,4 +101,4 @@ DetectedGames Sword2MetaEngine::detectGames(const Common::FSList &fslist) const
 	return detectGamesImpl(fslist);
 }
 
-REGISTER_PLUGIN_STATIC(SWORD2_DETECTION, PLUGIN_TYPE_METAENGINE, Sword2MetaEngine);
+REGISTER_PLUGIN_STATIC(SWORD2_DETECTION, PLUGIN_TYPE_METAENGINE, Sword2MetaEngineStatic);
diff --git a/engines/sword2/metaengine.cpp b/engines/sword2/metaengine.cpp
index cee3d1011e..acefded123 100644
--- a/engines/sword2/metaengine.cpp
+++ b/engines/sword2/metaengine.cpp
@@ -36,7 +36,7 @@
 #include "sword2/saveload.h"
 #include "sword2/detection_internal.h"
 
-class Sword2MetaEngineConnect : public MetaEngineConnect {
+class Sword2MetaEngine : public MetaEngine {
 public:
     const char *getName() const override {
 		return "sword2";
@@ -51,7 +51,7 @@ public:
 	Common::Error createInstance(OSystem *syst, Engine **engine) const override;
 };
 
-bool Sword2MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool Sword2MetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -67,7 +67,7 @@ bool Sword2::Sword2Engine::hasFeature(EngineFeature f) const {
 		(f == kSupportsLoadingDuringRuntime);
 }
 
-SaveStateList Sword2MetaEngineConnect::listSaves(const char *target) const {
+SaveStateList Sword2MetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	char saveDesc[SAVE_DESCRIPTION_LEN];
@@ -97,16 +97,16 @@ SaveStateList Sword2MetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int Sword2MetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+int Sword2MetaEngine::getMaximumSaveSlot() const { return 999; }
 
-void Sword2MetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void Sword2MetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = target;
 	filename += Common::String::format(".%03d", slot);
 
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-Common::Error Sword2MetaEngineConnect::createInstance(OSystem *syst, Engine **engine) const {
+Common::Error Sword2MetaEngine::createInstance(OSystem *syst, Engine **engine) const {
 	assert(syst);
 	assert(engine);
 
@@ -131,7 +131,7 @@ Common::Error Sword2MetaEngineConnect::createInstance(OSystem *syst, Engine **en
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(SWORD2)
-	REGISTER_PLUGIN_DYNAMIC(SWORD2, PLUGIN_TYPE_ENGINE, Sword2MetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(SWORD2, PLUGIN_TYPE_ENGINE, Sword2MetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(SWORD2, PLUGIN_TYPE_ENGINE, Sword2MetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(SWORD2, PLUGIN_TYPE_ENGINE, Sword2MetaEngine);
 #endif
diff --git a/engines/sword25/detection.cpp b/engines/sword25/detection.cpp
index 40ac500ea2..9962cbf2c8 100644
--- a/engines/sword25/detection.cpp
+++ b/engines/sword25/detection.cpp
@@ -44,9 +44,9 @@ static const ExtraGuiOption sword25ExtraGuiOption = {
 	false
 };
 
-class Sword25MetaEngine : public AdvancedMetaEngine {
+class Sword25MetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	Sword25MetaEngine() : AdvancedMetaEngine(Sword25::gameDescriptions, sizeof(ADGameDescription), sword25Game) {
+	Sword25MetaEngineStatic() : AdvancedMetaEngineStatic(Sword25::gameDescriptions, sizeof(ADGameDescription), sword25Game) {
 		_guiOptions = GUIO1(GUIO_NOMIDI);
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
@@ -67,10 +67,10 @@ public:
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
 };
 
-const ExtraGuiOptions Sword25MetaEngine::getExtraGuiOptions(const Common::String &target) const {
+const ExtraGuiOptions Sword25MetaEngineStatic::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	options.push_back(sword25ExtraGuiOption);
 	return options;
 }
 
-REGISTER_PLUGIN_STATIC(SWORD25_DETECTION, PLUGIN_TYPE_METAENGINE, Sword25MetaEngine);
+REGISTER_PLUGIN_STATIC(SWORD25_DETECTION, PLUGIN_TYPE_METAENGINE, Sword25MetaEngineStatic);
diff --git a/engines/sword25/metaengine.cpp b/engines/sword25/metaengine.cpp
index bc8affb9ac..0c7fc563a8 100644
--- a/engines/sword25/metaengine.cpp
+++ b/engines/sword25/metaengine.cpp
@@ -31,7 +31,7 @@ uint32 Sword25Engine::getGameFlags() const { return _gameDescription->flags; }
 
 } // End of namespace Sword25
 
-class Sword25MetaEngineConnect : public AdvancedMetaEngineConnect {
+class Sword25MetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "sword25";
@@ -44,19 +44,19 @@ public:
 	SaveStateList listSaves(const char *target) const override;
 };
 
-bool Sword25MetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool Sword25MetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Sword25::Sword25Engine(syst, desc);
 	}
 	return desc != 0;
 }
 
-bool Sword25MetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool Sword25MetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves);
 }
 
-SaveStateList Sword25MetaEngineConnect::listSaves(const char *target) const {
+SaveStateList Sword25MetaEngine::listSaves(const char *target) const {
 	Common::String pattern = target;
 	pattern = pattern + ".###";
 	SaveStateList saveList;
@@ -77,7 +77,7 @@ SaveStateList Sword25MetaEngineConnect::listSaves(const char *target) const {
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(SWORD25)
-	REGISTER_PLUGIN_DYNAMIC(SWORD25, PLUGIN_TYPE_ENGINE, Sword25MetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(SWORD25, PLUGIN_TYPE_ENGINE, Sword25MetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(SWORD25, PLUGIN_TYPE_ENGINE, Sword25MetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(SWORD25, PLUGIN_TYPE_ENGINE, Sword25MetaEngine);
 #endif
diff --git a/engines/teenagent/detection.cpp b/engines/teenagent/detection.cpp
index ad1b1629ea..623603dd2e 100644
--- a/engines/teenagent/detection.cpp
+++ b/engines/teenagent/detection.cpp
@@ -78,9 +78,9 @@ static const ADGameDescription teenAgentGameDescriptions[] = {
 
 
 
-class TeenAgentMetaEngine : public AdvancedMetaEngine {
+class TeenAgentMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	TeenAgentMetaEngine() : AdvancedMetaEngine(teenAgentGameDescriptions, sizeof(ADGameDescription), teenAgentGames) {
+	TeenAgentMetaEngineStatic() : AdvancedMetaEngineStatic(teenAgentGameDescriptions, sizeof(ADGameDescription), teenAgentGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -96,4 +96,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(TEENAGENT_DETECTION, PLUGIN_TYPE_METAENGINE, TeenAgentMetaEngine);
+REGISTER_PLUGIN_STATIC(TEENAGENT_DETECTION, PLUGIN_TYPE_METAENGINE, TeenAgentMetaEngineStatic);
diff --git a/engines/teenagent/metaengine.cpp b/engines/teenagent/metaengine.cpp
index 74f21474dc..d6f3883943 100644
--- a/engines/teenagent/metaengine.cpp
+++ b/engines/teenagent/metaengine.cpp
@@ -35,7 +35,7 @@ enum {
 	MAX_SAVES = 20
 };
 
-class TeenAgentMetaEngineConnect : public AdvancedMetaEngineConnect {
+class TeenAgentMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "teenagent";
@@ -131,7 +131,7 @@ public:
 };
 
 #if PLUGIN_ENABLED_DYNAMIC(TEENAGENT)
-	REGISTER_PLUGIN_DYNAMIC(TEENAGENT, PLUGIN_TYPE_ENGINE, TeenAgentMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TEENAGENT, PLUGIN_TYPE_ENGINE, TeenAgentMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TEENAGENT, PLUGIN_TYPE_ENGINE, TeenAgentMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(TEENAGENT, PLUGIN_TYPE_ENGINE, TeenAgentMetaEngine);
 #endif
diff --git a/engines/testbed/detection.cpp b/engines/testbed/detection.cpp
index dcc22dc13b..90180fc1fe 100644
--- a/engines/testbed/detection.cpp
+++ b/engines/testbed/detection.cpp
@@ -42,9 +42,9 @@ static const ADGameDescription testbedDescriptions[] = {
 	AD_TABLE_END_MARKER
 };
 
-class TestbedMetaEngine : public AdvancedMetaEngine {
+class TestbedMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	TestbedMetaEngine() : AdvancedMetaEngine(testbedDescriptions, sizeof(ADGameDescription), testbed_setting) {
+	TestbedMetaEngineStatic() : AdvancedMetaEngineStatic(testbedDescriptions, sizeof(ADGameDescription), testbed_setting) {
 		_md5Bytes = 512;
 	}
 
@@ -61,4 +61,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(TESTBED_DETECTION, PLUGIN_TYPE_METAENGINE, TestbedMetaEngine);
+REGISTER_PLUGIN_STATIC(TESTBED_DETECTION, PLUGIN_TYPE_METAENGINE, TestbedMetaEngineStatic);
diff --git a/engines/testbed/metaengine.cpp b/engines/testbed/metaengine.cpp
index b0c00692cf..6b49b347ae 100644
--- a/engines/testbed/metaengine.cpp
+++ b/engines/testbed/metaengine.cpp
@@ -29,7 +29,7 @@
 #include "testbed/testbed.h"
 #include "testbed/testsuite.h"
 
-class TestbedMetaEngineConnect : public AdvancedMetaEngineConnect {
+class TestbedMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "testbed";
@@ -65,7 +65,7 @@ public:
 };
 
 #if PLUGIN_ENABLED_DYNAMIC(TESTBED)
-	REGISTER_PLUGIN_DYNAMIC(TESTBED, PLUGIN_TYPE_ENGINE, TestbedMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TESTBED, PLUGIN_TYPE_ENGINE, TestbedMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TESTBED, PLUGIN_TYPE_ENGINE, TestbedMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(TESTBED, PLUGIN_TYPE_ENGINE, TestbedMetaEngine);
 #endif
diff --git a/engines/tinsel/detection.cpp b/engines/tinsel/detection.cpp
index e39e82c8c8..13eed4bb39 100644
--- a/engines/tinsel/detection.cpp
+++ b/engines/tinsel/detection.cpp
@@ -36,9 +36,9 @@ static const PlainGameDescriptor tinselGames[] = {
 
 #include "tinsel/detection_tables.h"
 
-class TinselMetaEngine : public AdvancedMetaEngine {
+class TinselMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	TinselMetaEngine() : AdvancedMetaEngine(Tinsel::gameDescriptions, sizeof(Tinsel::TinselGameDescription), tinselGames) {
+	TinselMetaEngineStatic() : AdvancedMetaEngineStatic(Tinsel::gameDescriptions, sizeof(Tinsel::TinselGameDescription), tinselGames) {
 	}
 
 	const char *getEngineId() const  override{
@@ -68,7 +68,7 @@ typedef Common::Array<const ADGameDescription *> ADGameDescList;
  * Fallback detection scans the list of Discworld 2 targets to see if it can detect an installation
  * where the files haven't been renamed (i.e. don't have the '1' just before the extension)
  */
-ADDetectedGame TinselMetaEngine::fallbackDetect(const FileMap &allFilesXXX, const Common::FSList &fslist) const {
+ADDetectedGame TinselMetaEngineStatic::fallbackDetect(const FileMap &allFilesXXX, const Common::FSList &fslist) const {
 	Common::String extra;
 	FileMap allFiles;
 	SizeMD5Map filesSizeMD5;
@@ -204,4 +204,4 @@ ADDetectedGame TinselMetaEngine::fallbackDetect(const FileMap &allFilesXXX, cons
 	return matched;
 }
 
-REGISTER_PLUGIN_STATIC(TINSEL_DETECTION, PLUGIN_TYPE_METAENGINE, TinselMetaEngine);
+REGISTER_PLUGIN_STATIC(TINSEL_DETECTION, PLUGIN_TYPE_METAENGINE, TinselMetaEngineStatic);
diff --git a/engines/tinsel/metaengine.cpp b/engines/tinsel/metaengine.cpp
index a5a5eb3c67..91a33d7a9f 100644
--- a/engines/tinsel/metaengine.cpp
+++ b/engines/tinsel/metaengine.cpp
@@ -63,7 +63,7 @@ bool TinselEngine::isV1CD() const {
 
 } // End of namespace Tinsel
 
-class TinselMetaEngineConnect : public AdvancedMetaEngineConnect {
+class TinselMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const  override{
 		return "tinsel";
@@ -78,7 +78,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool TinselMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool TinselMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -105,7 +105,7 @@ bool Tinsel::TinselEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsLoadingDuringRuntime);
 }
 
-SaveStateDescriptor TinselMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor TinselMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName;
 	fileName = Common::String::format("%s.%03u", target, slot);
 
@@ -147,7 +147,7 @@ namespace Tinsel {
 extern int getList(Common::SaveFileManager *saveFileMan, const Common::String &target);
 }
 
-SaveStateList TinselMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList TinselMetaEngine::listSaves(const char *target) const {
 	Common::String pattern = target;
 	pattern = pattern + ".###";
 	Common::StringArray files = g_system->getSavefileManager()->listSavefiles(pattern);
@@ -179,7 +179,7 @@ SaveStateList TinselMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-bool TinselMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool TinselMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Tinsel::TinselGameDescription *gd = (const Tinsel::TinselGameDescription *)desc;
 	if (gd) {
 		*engine = new Tinsel::TinselEngine(syst, gd);
@@ -187,9 +187,9 @@ bool TinselMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, con
 	return gd != 0;
 }
 
-int TinselMetaEngineConnect::getMaximumSaveSlot() const { return 99; }
+int TinselMetaEngine::getMaximumSaveSlot() const { return 99; }
 
-void TinselMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void TinselMetaEngine::removeSaveState(const char *target, int slot) const {
 	Tinsel::setNeedLoad();
 	// Same issue here as with loadGameState(): we need the physical savegame
 	// slot. Refer to bug #3387551.
@@ -211,9 +211,9 @@ void TinselMetaEngineConnect::removeSaveState(const char *target, int slot) cons
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(TINSEL)
-	REGISTER_PLUGIN_DYNAMIC(TINSEL, PLUGIN_TYPE_ENGINE, TinselMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TINSEL, PLUGIN_TYPE_ENGINE, TinselMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TINSEL, PLUGIN_TYPE_ENGINE, TinselMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(TINSEL, PLUGIN_TYPE_ENGINE, TinselMetaEngine);
 #endif
 
 namespace Tinsel {
diff --git a/engines/titanic/detection.cpp b/engines/titanic/detection.cpp
index c3aaf829b2..f71f76d9a4 100644
--- a/engines/titanic/detection.cpp
+++ b/engines/titanic/detection.cpp
@@ -34,9 +34,9 @@ static const PlainGameDescriptor TitanicGames[] = {
 
 #include "titanic/detection_tables.h"
 
-class TitanicMetaEngine : public AdvancedMetaEngine {
+class TitanicMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	TitanicMetaEngine() : AdvancedMetaEngine(Titanic::gameDescriptions, sizeof(Titanic::TitanicGameDescription), TitanicGames) {
+	TitanicMetaEngineStatic() : AdvancedMetaEngineStatic(Titanic::gameDescriptions, sizeof(Titanic::TitanicGameDescription), TitanicGames) {
 		_maxScanDepth = 3;
 	}
 
@@ -53,4 +53,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(TITANIC_DETECTION, PLUGIN_TYPE_METAENGINE, TitanicMetaEngine);
+REGISTER_PLUGIN_STATIC(TITANIC_DETECTION, PLUGIN_TYPE_METAENGINE, TitanicMetaEngineStatic);
diff --git a/engines/titanic/metaengine.cpp b/engines/titanic/metaengine.cpp
index 1883f04e2c..13315642df 100644
--- a/engines/titanic/metaengine.cpp
+++ b/engines/titanic/metaengine.cpp
@@ -45,7 +45,7 @@ Common::Language TitanicEngine::getLanguage() const {
 
 } // End of namespace Titanic
 
-class TitanicMetaEngineConnect : public AdvancedMetaEngineConnect {
+class TitanicMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "titanic";
@@ -60,7 +60,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool TitanicMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool TitanicMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -79,14 +79,14 @@ bool Titanic::TitanicEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool TitanicMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool TitanicMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Titanic::TitanicGameDescription *gd = (const Titanic::TitanicGameDescription *)desc;
 	*engine = new Titanic::TitanicEngine(syst, gd);
 
 	return gd != 0;
 }
 
-SaveStateList TitanicMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList TitanicMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -120,16 +120,16 @@ SaveStateList TitanicMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int TitanicMetaEngineConnect::getMaximumSaveSlot() const {
+int TitanicMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVES;
 }
 
-void TitanicMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void TitanicMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor TitanicMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor TitanicMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
 
@@ -162,7 +162,7 @@ SaveStateDescriptor TitanicMetaEngineConnect::querySaveMetaInfos(const char *tar
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(TITANIC)
-	REGISTER_PLUGIN_DYNAMIC(TITANIC, PLUGIN_TYPE_ENGINE, TitanicMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TITANIC, PLUGIN_TYPE_ENGINE, TitanicMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TITANIC, PLUGIN_TYPE_ENGINE, TitanicMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(TITANIC, PLUGIN_TYPE_ENGINE, TitanicMetaEngine);
 #endif
diff --git a/engines/toltecs/detection.cpp b/engines/toltecs/detection.cpp
index 201d6aba02..a4b7e1d3ae 100644
--- a/engines/toltecs/detection.cpp
+++ b/engines/toltecs/detection.cpp
@@ -216,9 +216,9 @@ static const ExtraGuiOption toltecsExtraGuiOption = {
 	false
 };
 
-class ToltecsMetaEngine : public AdvancedMetaEngine {
+class ToltecsMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	ToltecsMetaEngine() : AdvancedMetaEngine(Toltecs::gameDescriptions, sizeof(Toltecs::ToltecsGameDescription), toltecsGames) {
+	ToltecsMetaEngineStatic() : AdvancedMetaEngineStatic(Toltecs::gameDescriptions, sizeof(Toltecs::ToltecsGameDescription), toltecsGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -236,10 +236,10 @@ public:
 	const ExtraGuiOptions getExtraGuiOptions(const Common::String &target) const override;
 };
 
-const ExtraGuiOptions ToltecsMetaEngine::getExtraGuiOptions(const Common::String &target) const {
+const ExtraGuiOptions ToltecsMetaEngineStatic::getExtraGuiOptions(const Common::String &target) const {
 	ExtraGuiOptions options;
 	options.push_back(toltecsExtraGuiOption);
 	return options;
 }
 
-REGISTER_PLUGIN_STATIC(TOLTECS_DETECTION, PLUGIN_TYPE_METAENGINE, ToltecsMetaEngine);
+REGISTER_PLUGIN_STATIC(TOLTECS_DETECTION, PLUGIN_TYPE_METAENGINE, ToltecsMetaEngineStatic);
diff --git a/engines/toltecs/metaengine.cpp b/engines/toltecs/metaengine.cpp
index e3dda22ed2..d47df0d129 100644
--- a/engines/toltecs/metaengine.cpp
+++ b/engines/toltecs/metaengine.cpp
@@ -44,7 +44,7 @@ Common::Language ToltecsEngine::getLanguage() const {
 
 } // End of namespace Toltecs
 
-class ToltecsMetaEngineConnect : public AdvancedMetaEngineConnect {
+class ToltecsMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "toltecs";
@@ -59,7 +59,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool ToltecsMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool ToltecsMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -78,7 +78,7 @@ bool Toltecs::ToltecsEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool ToltecsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool ToltecsMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Toltecs::ToltecsGameDescription *gd = (const Toltecs::ToltecsGameDescription *)desc;
 	if (gd) {
 		*engine = new Toltecs::ToltecsEngine(syst, gd);
@@ -86,7 +86,7 @@ bool ToltecsMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, co
 	return gd != 0;
 }
 
-SaveStateList ToltecsMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList ToltecsMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Toltecs::ToltecsEngine::SaveHeader header;
 	Common::String pattern = target;
@@ -116,11 +116,11 @@ SaveStateList ToltecsMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int ToltecsMetaEngineConnect::getMaximumSaveSlot() const {
+int ToltecsMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-void ToltecsMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void ToltecsMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::String filename = Toltecs::ToltecsEngine::getSavegameFilename(target, slot);
 
@@ -144,7 +144,7 @@ void ToltecsMetaEngineConnect::removeSaveState(const char *target, int slot) con
 	}
 }
 
-SaveStateDescriptor ToltecsMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor ToltecsMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Toltecs::ToltecsEngine::getSavegameFilename(target, slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
 
@@ -183,8 +183,8 @@ SaveStateDescriptor ToltecsMetaEngineConnect::querySaveMetaInfos(const char *tar
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(TOLTECS)
-	REGISTER_PLUGIN_DYNAMIC(TOLTECS, PLUGIN_TYPE_ENGINE, ToltecsMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TOLTECS, PLUGIN_TYPE_ENGINE, ToltecsMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TOLTECS, PLUGIN_TYPE_ENGINE, ToltecsMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(TOLTECS, PLUGIN_TYPE_ENGINE, ToltecsMetaEngine);
 #endif
 
diff --git a/engines/tony/detection.cpp b/engines/tony/detection.cpp
index d02ddea22c..9708f1564f 100644
--- a/engines/tony/detection.cpp
+++ b/engines/tony/detection.cpp
@@ -33,9 +33,9 @@ static const PlainGameDescriptor tonyGames[] = {
 
 #include "tony/detection_tables.h"
 
-class TonyMetaEngine : public AdvancedMetaEngine {
+class TonyMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	TonyMetaEngine() : AdvancedMetaEngine(Tony::gameDescriptions, sizeof(Tony::TonyGameDescription), tonyGames) {
+	TonyMetaEngineStatic() : AdvancedMetaEngineStatic(Tony::gameDescriptions, sizeof(Tony::TonyGameDescription), tonyGames) {
 	}
 
 	const char *getEngineId() const override {
@@ -51,4 +51,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(TONY_DETECTION, PLUGIN_TYPE_METAENGINE, TonyMetaEngine);
+REGISTER_PLUGIN_STATIC(TONY_DETECTION, PLUGIN_TYPE_METAENGINE, TonyMetaEngineStatic);
diff --git a/engines/tony/metaengine.cpp b/engines/tony/metaengine.cpp
index 8c2f6949de..dd2a019b2b 100644
--- a/engines/tony/metaengine.cpp
+++ b/engines/tony/metaengine.cpp
@@ -51,7 +51,7 @@ bool TonyEngine::isCompressed() const {
 
 } // End of namespace Tony
 
-class TonyMetaEngineConnect : public AdvancedMetaEngineConnect {
+class TonyMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "tony";
@@ -66,7 +66,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool TonyMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool TonyMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -82,7 +82,7 @@ bool Tony::TonyEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool TonyMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool TonyMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Tony::TonyGameDescription *gd = (const Tony::TonyGameDescription *)desc;
 	if (gd) {
 		*engine = new Tony::TonyEngine(syst, gd);
@@ -90,7 +90,7 @@ bool TonyMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return gd != 0;
 }
 
-SaveStateList TonyMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList TonyMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -120,17 +120,17 @@ SaveStateList TonyMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int TonyMetaEngineConnect::getMaximumSaveSlot() const {
+int TonyMetaEngine::getMaximumSaveSlot() const {
 	return 99;
 }
 
-void TonyMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void TonyMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Tony::TonyEngine::getSaveStateFileName(slot);
 
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor TonyMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor TonyMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String saveName;
 	byte difficulty;
 
@@ -157,7 +157,7 @@ SaveStateDescriptor TonyMetaEngineConnect::querySaveMetaInfos(const char *target
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(TONY)
-	REGISTER_PLUGIN_DYNAMIC(TONY, PLUGIN_TYPE_ENGINE, TonyMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TONY, PLUGIN_TYPE_ENGINE, TonyMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TONY, PLUGIN_TYPE_ENGINE, TonyMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(TONY, PLUGIN_TYPE_ENGINE, TonyMetaEngine);
 #endif
diff --git a/engines/toon/detection.cpp b/engines/toon/detection.cpp
index be3974cfdb..3636fde323 100644
--- a/engines/toon/detection.cpp
+++ b/engines/toon/detection.cpp
@@ -130,9 +130,9 @@ static const char * const directoryGlobs[] = {
 	0
 };
 
-class ToonMetaEngine : public AdvancedMetaEngine {
+class ToonMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	ToonMetaEngine() : AdvancedMetaEngine(Toon::gameDescriptions, sizeof(ADGameDescription), toonGames) {
+	ToonMetaEngineStatic() : AdvancedMetaEngineStatic(Toon::gameDescriptions, sizeof(ADGameDescription), toonGames) {
 		_maxScanDepth = 3;
 		_directoryGlobs = directoryGlobs;
 	}
@@ -154,4 +154,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(TOON_DETECTION, PLUGIN_TYPE_METAENGINE, ToonMetaEngine);
+REGISTER_PLUGIN_STATIC(TOON_DETECTION, PLUGIN_TYPE_METAENGINE, ToonMetaEngineStatic);
diff --git a/engines/toon/metaengine.cpp b/engines/toon/metaengine.cpp
index f75bad337e..138484f5ab 100644
--- a/engines/toon/metaengine.cpp
+++ b/engines/toon/metaengine.cpp
@@ -28,7 +28,7 @@
 #include "graphics/thumbnail.h"
 #include "toon/toon.h"
 
-class ToonMetaEngineConnect : public AdvancedMetaEngineConnect {
+class ToonMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "toon";
@@ -43,7 +43,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool ToonMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool ToonMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 	    (f == kSupportsLoadingDuringStartup) ||
@@ -55,14 +55,14 @@ bool ToonMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
 		(f == kSimpleSavesNames);
 }
 
-void ToonMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void ToonMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(fileName);
 }
 
-int ToonMetaEngineConnect::getMaximumSaveSlot() const { return MAX_SAVE_SLOT; }
+int ToonMetaEngine::getMaximumSaveSlot() const { return MAX_SAVE_SLOT; }
 
-SaveStateList ToonMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList ToonMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String pattern = target;
@@ -105,7 +105,7 @@ SaveStateList ToonMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-SaveStateDescriptor ToonMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor ToonMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String fileName = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *file = g_system->getSavefileManager()->openForLoading(fileName);
 
@@ -157,7 +157,7 @@ SaveStateDescriptor ToonMetaEngineConnect::querySaveMetaInfos(const char *target
 	return SaveStateDescriptor();
 }
 
-bool ToonMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool ToonMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Toon::ToonEngine(syst, desc);
 	}
@@ -165,7 +165,7 @@ bool ToonMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(TOON)
-	REGISTER_PLUGIN_DYNAMIC(TOON, PLUGIN_TYPE_ENGINE, ToonMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TOON, PLUGIN_TYPE_ENGINE, ToonMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TOON, PLUGIN_TYPE_ENGINE, ToonMetaEngineConnect);
-#endif
\ No newline at end of file
+	REGISTER_PLUGIN_STATIC(TOON, PLUGIN_TYPE_ENGINE, ToonMetaEngine);
+#endif
diff --git a/engines/touche/detection.cpp b/engines/touche/detection.cpp
index 33605d33ee..98de9aa8ad 100644
--- a/engines/touche/detection.cpp
+++ b/engines/touche/detection.cpp
@@ -119,9 +119,9 @@ static const char *directoryGlobs[] = {
 	0
 };
 
-class ToucheMetaEngine : public AdvancedMetaEngine {
+class ToucheMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	ToucheMetaEngine() : AdvancedMetaEngine(Touche::gameDescriptions, sizeof(ADGameDescription), toucheGames) {
+	ToucheMetaEngineStatic() : AdvancedMetaEngineStatic(Touche::gameDescriptions, sizeof(ADGameDescription), toucheGames) {
 		_md5Bytes = 4096;
 		_maxScanDepth = 2;
 		_directoryGlobs = directoryGlobs;
@@ -144,4 +144,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(TOUCHE_DETECTION, PLUGIN_TYPE_METAENGINE, ToucheMetaEngine);
+REGISTER_PLUGIN_STATIC(TOUCHE_DETECTION, PLUGIN_TYPE_METAENGINE, ToucheMetaEngineStatic);
diff --git a/engines/touche/metaengine.cpp b/engines/touche/metaengine.cpp
index 5d6e95e3f7..2127a137c4 100644
--- a/engines/touche/metaengine.cpp
+++ b/engines/touche/metaengine.cpp
@@ -29,7 +29,7 @@
 
 #include "touche/touche.h"
 
-class ToucheMetaEngineConnect : public AdvancedMetaEngineConnect {
+class ToucheMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "touche";
@@ -42,7 +42,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool ToucheMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool ToucheMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -57,14 +57,14 @@ bool Touche::ToucheEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSubtitleOptions);
 }
 
-bool ToucheMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool ToucheMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Touche::ToucheEngine(syst, desc->language);
 	}
 	return desc != 0;
 }
 
-SaveStateList ToucheMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList ToucheMetaEngine::listSaves(const char *target) const {
 	Common::String pattern = Touche::generateGameStateFileName(target, 0, true);
 	Common::StringArray filenames = g_system->getSavefileManager()->listSavefiles(pattern);
 	bool slotsTable[Touche::kMaxSaveStates];
@@ -93,17 +93,17 @@ SaveStateList ToucheMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int ToucheMetaEngineConnect::getMaximumSaveSlot() const {
+int ToucheMetaEngine::getMaximumSaveSlot() const {
 	return Touche::kMaxSaveStates - 1;
 }
 
-void ToucheMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void ToucheMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Touche::generateGameStateFileName(target, slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(TOUCHE)
-	REGISTER_PLUGIN_DYNAMIC(TOUCHE, PLUGIN_TYPE_ENGINE, ToucheMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TOUCHE, PLUGIN_TYPE_ENGINE, ToucheMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TOUCHE, PLUGIN_TYPE_ENGINE, ToucheMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(TOUCHE, PLUGIN_TYPE_ENGINE, ToucheMetaEngine);
 #endif
diff --git a/engines/tsage/detection.cpp b/engines/tsage/detection.cpp
index 5d5c5f6284..f7ec40c90f 100644
--- a/engines/tsage/detection.cpp
+++ b/engines/tsage/detection.cpp
@@ -36,9 +36,9 @@ static const PlainGameDescriptor tSageGameTitles[] = {
 
 #include "tsage/detection_tables.h"
 
-class TSageMetaEngine : public AdvancedMetaEngine {
+class TSageMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	TSageMetaEngine() : AdvancedMetaEngine(TsAGE::gameDescriptions, sizeof(TsAGE::tSageGameDescription), tSageGameTitles) {
+	TSageMetaEngineStatic() : AdvancedMetaEngineStatic(TsAGE::gameDescriptions, sizeof(TsAGE::tSageGameDescription), tSageGameTitles) {
 	}
 
 	const char *getEngineId() const override {
@@ -54,4 +54,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(TSAGE_DETECTION, PLUGIN_TYPE_METAENGINE, TSageMetaEngine);
+REGISTER_PLUGIN_STATIC(TSAGE_DETECTION, PLUGIN_TYPE_METAENGINE, TSageMetaEngineStatic);
diff --git a/engines/tsage/metaengine.cpp b/engines/tsage/metaengine.cpp
index a3dd011fa1..9e2edc2b90 100644
--- a/engines/tsage/metaengine.cpp
+++ b/engines/tsage/metaengine.cpp
@@ -55,7 +55,7 @@ enum {
 	MAX_SAVES = 100
 };
 
-class TSageMetaEngineConnect : public AdvancedMetaEngineConnect {
+class TSageMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "tsage";
@@ -156,7 +156,7 @@ public:
 };
 
 #if PLUGIN_ENABLED_DYNAMIC(TSAGE)
-	REGISTER_PLUGIN_DYNAMIC(TSAGE, PLUGIN_TYPE_ENGINE, TSageMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TSAGE, PLUGIN_TYPE_ENGINE, TSageMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TSAGE, PLUGIN_TYPE_ENGINE, TSageMetaEngineConnect);
-#endif
\ No newline at end of file
+	REGISTER_PLUGIN_STATIC(TSAGE, PLUGIN_TYPE_ENGINE, TSageMetaEngine);
+#endif
diff --git a/engines/tucker/detection.cpp b/engines/tucker/detection.cpp
index ebacb19e41..e0cbc9a5d3 100644
--- a/engines/tucker/detection.cpp
+++ b/engines/tucker/detection.cpp
@@ -116,9 +116,9 @@ static const ADGameDescription tuckerDemoGameDescription = {
 	GUIO1(GUIO_NOMIDI)
 };
 
-class TuckerMetaEngine : public AdvancedMetaEngine {
+class TuckerMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	TuckerMetaEngine() : AdvancedMetaEngine(tuckerGameDescriptions, sizeof(ADGameDescription), tuckerGames) {
+	TuckerMetaEngineStatic() : AdvancedMetaEngineStatic(tuckerGameDescriptions, sizeof(ADGameDescription), tuckerGames) {
 		_md5Bytes = 512;
 	}
 
@@ -151,4 +151,4 @@ public:
 
 };
 
-REGISTER_PLUGIN_STATIC(TUCKER_DETECTION, PLUGIN_TYPE_METAENGINE, TuckerMetaEngine);
+REGISTER_PLUGIN_STATIC(TUCKER_DETECTION, PLUGIN_TYPE_METAENGINE, TuckerMetaEngineStatic);
diff --git a/engines/tucker/metaengine.cpp b/engines/tucker/metaengine.cpp
index 222dad100c..068cb4a5be 100644
--- a/engines/tucker/metaengine.cpp
+++ b/engines/tucker/metaengine.cpp
@@ -29,7 +29,7 @@
 
 #include "tucker/tucker.h"
 
-class TuckerMetaEngineConnect : public AdvancedMetaEngineConnect {
+class TuckerMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "tucker";
@@ -150,7 +150,7 @@ public:
 };
 
 #if PLUGIN_ENABLED_DYNAMIC(TUCKER)
-	REGISTER_PLUGIN_DYNAMIC(TUCKER, PLUGIN_TYPE_ENGINE, TuckerMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(TUCKER, PLUGIN_TYPE_ENGINE, TuckerMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(TUCKER, PLUGIN_TYPE_ENGINE, TuckerMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(TUCKER, PLUGIN_TYPE_ENGINE, TuckerMetaEngine);
 #endif
diff --git a/engines/ultima/detection.cpp b/engines/ultima/detection.cpp
index 8f62f6fe46..3ee021a995 100644
--- a/engines/ultima/detection.cpp
+++ b/engines/ultima/detection.cpp
@@ -49,11 +49,11 @@ static const PlainGameDescriptor ULTIMA_GAMES[] = {
 
 #include "ultima/detection_tables.h"
 
-UltimaMetaEngine::UltimaMetaEngine() : AdvancedMetaEngine(Ultima::GAME_DESCRIPTIONS,
+UltimaMetaEngineStatic::UltimaMetaEngineStatic() : AdvancedMetaEngineStatic(Ultima::GAME_DESCRIPTIONS,
 	        sizeof(Ultima::UltimaGameDescription), Ultima::ULTIMA_GAMES) {
 	static const char *const DIRECTORY_GLOBS[2] = { "usecode", 0 };
 	_maxScanDepth = 2;
 	_directoryGlobs = DIRECTORY_GLOBS;
 }
 
-REGISTER_PLUGIN_STATIC(ULTIMA_DETECTION, PLUGIN_TYPE_METAENGINE, UltimaMetaEngine);
+REGISTER_PLUGIN_STATIC(ULTIMA_DETECTION, PLUGIN_TYPE_METAENGINE, UltimaMetaEngineStatic);
diff --git a/engines/ultima/detection.h b/engines/ultima/detection.h
index 388d2fb5b2..52b2eff3e3 100644
--- a/engines/ultima/detection.h
+++ b/engines/ultima/detection.h
@@ -58,10 +58,10 @@ struct UltimaGameDescription {
 
 } // End of namespace Ultima
 
-class UltimaMetaEngine : public AdvancedMetaEngine {
+class UltimaMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	UltimaMetaEngine();
-	~UltimaMetaEngine() override {}
+	UltimaMetaEngineStatic();
+	~UltimaMetaEngineStatic() override {}
 
 	const char *getEngineId() const override {
 		return "ultima";
diff --git a/engines/ultima/metaengine.cpp b/engines/ultima/metaengine.cpp
index 84aae06901..3ea84c1487 100644
--- a/engines/ultima/metaengine.cpp
+++ b/engines/ultima/metaengine.cpp
@@ -37,11 +37,11 @@
 
 #include "ultima/metaengine.h"
 
-const char *UltimaMetaEngineConnect::getName() const {
+const char *UltimaMetaEngine::getName() const {
 	return "ultima";
 }
 
-bool UltimaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool UltimaMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Ultima::UltimaGameDescription *gd = (const Ultima::UltimaGameDescription *)desc;
 	if (gd) {
 		switch (gd->gameId) {
@@ -71,12 +71,12 @@ bool UltimaMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, con
 	return gd != 0;
 }
 
-int UltimaMetaEngineConnect::getMaximumSaveSlot() const {
+int UltimaMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVES;
 }
 
-SaveStateList UltimaMetaEngineConnect::listSaves(const char *target) const {
-	SaveStateList saveList = AdvancedMetaEngineConnect::listSaves(target);
+SaveStateList UltimaMetaEngine::listSaves(const char *target) const {
+	SaveStateList saveList = AdvancedMetaEngine::listSaves(target);
 
 	Common::String gameId = getGameId(target);
 	if (gameId == "ultima6" || gameId == "ultima6_enh")
@@ -85,7 +85,7 @@ SaveStateList UltimaMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-Common::KeymapArray UltimaMetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray UltimaMetaEngine::initKeymaps(const char *target) const {
 	const Common::String gameId = getGameId(target);
 	if (gameId == "ultima4" || gameId == "ultima4_enh")
 		return Ultima::Ultima4::MetaEngine::initKeymaps();
@@ -95,7 +95,7 @@ Common::KeymapArray UltimaMetaEngineConnect::initKeymaps(const char *target) con
 	return Common::KeymapArray();
 }
 
-Common::String UltimaMetaEngineConnect::getGameId(const char *target) {
+Common::String UltimaMetaEngine::getGameId(const char *target) {
 	// Store a copy of the active domain
 	Common::String currDomain = ConfMan.getActiveDomainName();
 
@@ -109,7 +109,7 @@ Common::String UltimaMetaEngineConnect::getGameId(const char *target) {
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(ULTIMA)
-	REGISTER_PLUGIN_DYNAMIC(ULTIMA, PLUGIN_TYPE_ENGINE, UltimaMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(ULTIMA, PLUGIN_TYPE_ENGINE, UltimaMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(ULTIMA, PLUGIN_TYPE_ENGINE, UltimaMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(ULTIMA, PLUGIN_TYPE_ENGINE, UltimaMetaEngine);
 #endif
diff --git a/engines/ultima/metaengine.h b/engines/ultima/metaengine.h
index 0dc0756141..3297d0a738 100644
--- a/engines/ultima/metaengine.h
+++ b/engines/ultima/metaengine.h
@@ -28,7 +28,7 @@
 
 #define MAX_SAVES 99
 
-class UltimaMetaEngineConnect : public AdvancedMetaEngineConnect {
+class UltimaMetaEngine : public AdvancedMetaEngine {
 private:
 	/**
 	 * Gets the game Id given a target string
diff --git a/engines/ultima/nuvie/files/nuvie_io_file.cpp b/engines/ultima/nuvie/files/nuvie_io_file.cpp
index b8f0fa1357..5acfe4fa5b 100644
--- a/engines/ultima/nuvie/files/nuvie_io_file.cpp
+++ b/engines/ultima/nuvie/files/nuvie_io_file.cpp
@@ -164,7 +164,7 @@ void NuvieIOFileWrite::close() {
 	} else if (_saveFile) {
 		// Writing using savefile interface, so flush out data
 		_saveFile->write(_saveFileData.getData(), _saveFileData.size());
-		MetaEngineConnect::appendExtendedSave(_saveFile, Shared::g_ultima->getTotalPlayTime(), _description, _isAutosave);
+		MetaEngine::appendExtendedSave(_saveFile, Shared::g_ultima->getTotalPlayTime(), _description, _isAutosave);
 
 		_saveFile->finalize();
 		delete _saveFile;
diff --git a/engines/ultima/ultima8/filesys/savegame.cpp b/engines/ultima/ultima8/filesys/savegame.cpp
index 8e5a5e1dd2..58e506e266 100644
--- a/engines/ultima/ultima8/filesys/savegame.cpp
+++ b/engines/ultima/ultima8/filesys/savegame.cpp
@@ -36,7 +36,7 @@ namespace Ultima8 {
 #define SAVEGAME_VERSION 5
 
 SavegameReader::SavegameReader(Common::SeekableReadStream *rs, bool metadataOnly) : _file(rs), _version(0) {
-	if (!MetaEngineConnect::readSavegameHeader(rs, &_header))
+	if (!MetaEngine::readSavegameHeader(rs, &_header))
 		return;
 
 	// Validate the identifier for a valid savegame
diff --git a/engines/voyeur/detection.cpp b/engines/voyeur/detection.cpp
index 1afa7bec50..8c93164d04 100644
--- a/engines/voyeur/detection.cpp
+++ b/engines/voyeur/detection.cpp
@@ -34,9 +34,9 @@ static const PlainGameDescriptor voyeurGames[] = {
 
 #include "voyeur/detection_tables.h"
 
-class VoyeurMetaEngine : public AdvancedMetaEngine {
+class VoyeurMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	VoyeurMetaEngine() : AdvancedMetaEngine(Voyeur::gameDescriptions, sizeof(Voyeur::VoyeurGameDescription), voyeurGames) {
+	VoyeurMetaEngineStatic() : AdvancedMetaEngineStatic(Voyeur::gameDescriptions, sizeof(Voyeur::VoyeurGameDescription), voyeurGames) {
 		_maxScanDepth = 3;
 	}
 
@@ -53,4 +53,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(VOYEUR_DETECTION, PLUGIN_TYPE_METAENGINE, VoyeurMetaEngine);
+REGISTER_PLUGIN_STATIC(VOYEUR_DETECTION, PLUGIN_TYPE_METAENGINE, VoyeurMetaEngineStatic);
diff --git a/engines/voyeur/metaengine.cpp b/engines/voyeur/metaengine.cpp
index ee145ef19f..c59ad1ff3f 100644
--- a/engines/voyeur/metaengine.cpp
+++ b/engines/voyeur/metaengine.cpp
@@ -53,7 +53,7 @@ bool VoyeurEngine::getIsDemo() const {
 
 } // End of namespace Voyeur
 
-class VoyeurMetaEngineConnect : public AdvancedMetaEngineConnect {
+class VoyeurMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "voyeur";
@@ -67,7 +67,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool VoyeurMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool VoyeurMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 	    (f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -84,7 +84,7 @@ bool Voyeur::VoyeurEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool VoyeurMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool VoyeurMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Voyeur::VoyeurGameDescription *gd = (const Voyeur::VoyeurGameDescription *)desc;
 	if (gd) {
 		*engine = new Voyeur::VoyeurEngine(syst, gd);
@@ -92,7 +92,7 @@ bool VoyeurMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, con
 	return gd != 0;
 }
 
-SaveStateList VoyeurMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList VoyeurMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -124,16 +124,16 @@ SaveStateList VoyeurMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int VoyeurMetaEngineConnect::getMaximumSaveSlot() const {
+int VoyeurMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVES;
 }
 
-void VoyeurMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void VoyeurMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor VoyeurMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor VoyeurMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
 
@@ -156,7 +156,7 @@ SaveStateDescriptor VoyeurMetaEngineConnect::querySaveMetaInfos(const char *targ
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(VOYEUR)
-	REGISTER_PLUGIN_DYNAMIC(VOYEUR, PLUGIN_TYPE_ENGINE, VoyeurMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(VOYEUR, PLUGIN_TYPE_ENGINE, VoyeurMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(VOYEUR, PLUGIN_TYPE_ENGINE, VoyeurMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(VOYEUR, PLUGIN_TYPE_ENGINE, VoyeurMetaEngine);
 #endif
diff --git a/engines/wage/detection.cpp b/engines/wage/detection.cpp
index 6a1b243745..7432e4d4fd 100644
--- a/engines/wage/detection.cpp
+++ b/engines/wage/detection.cpp
@@ -39,9 +39,9 @@ static const PlainGameDescriptor wageGames[] = {
 
 #include "wage/detection_tables.h"
 
-class WageMetaEngine : public AdvancedMetaEngine {
+class WageMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	WageMetaEngine() : AdvancedMetaEngine(Wage::gameDescriptions, sizeof(ADGameDescription), wageGames) {
+	WageMetaEngineStatic() : AdvancedMetaEngineStatic(Wage::gameDescriptions, sizeof(ADGameDescription), wageGames) {
 		_md5Bytes = 2 * 1024 * 1024;
 		_guiOptions = GUIO2(GUIO_NOSPEECH, GUIO_NOMIDI);
 	}
@@ -59,4 +59,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(WAGE_DETECTION, PLUGIN_TYPE_METAENGINE, WageMetaEngine);
+REGISTER_PLUGIN_STATIC(WAGE_DETECTION, PLUGIN_TYPE_METAENGINE, WageMetaEngineStatic);
diff --git a/engines/wage/metaengine.cpp b/engines/wage/metaengine.cpp
index 234ec45dcf..f9627d0420 100644
--- a/engines/wage/metaengine.cpp
+++ b/engines/wage/metaengine.cpp
@@ -37,7 +37,7 @@ const char *WageEngine::getGameFile() const {
 
 } // End of namespace Wage
 
-class WageMetaEngineConnect : public AdvancedMetaEngineConnect {
+class WageMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "wage";
@@ -51,7 +51,7 @@ public:
 	void removeSaveState(const char *target, int slot) const override;
 };
 
-bool WageMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool WageMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -66,14 +66,14 @@ bool Wage::WageEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool WageMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool WageMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	if (desc) {
 		*engine = new Wage::WageEngine(syst, desc);
 	}
 	return desc != 0;
 }
 
-SaveStateList WageMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList WageMetaEngine::listSaves(const char *target) const {
 	const uint32 WAGEflag = MKTAG('W','A','G','E');
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
@@ -114,16 +114,16 @@ SaveStateList WageMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int WageMetaEngineConnect::getMaximumSaveSlot() const { return 999; }
+int WageMetaEngine::getMaximumSaveSlot() const { return 999; }
 
-void WageMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void WageMetaEngine::removeSaveState(const char *target, int slot) const {
 	g_system->getSavefileManager()->removeSavefile(Common::String::format("%s.%03d", target, slot));
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(WAGE)
-	REGISTER_PLUGIN_DYNAMIC(WAGE, PLUGIN_TYPE_ENGINE, WageMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(WAGE, PLUGIN_TYPE_ENGINE, WageMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(WAGE, PLUGIN_TYPE_ENGINE, WageMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(WAGE, PLUGIN_TYPE_ENGINE, WageMetaEngine);
 #endif
 
 namespace Wage {
diff --git a/engines/wintermute/detection.cpp b/engines/wintermute/detection.cpp
index 525342dfa6..e6f304509b 100644
--- a/engines/wintermute/detection.cpp
+++ b/engines/wintermute/detection.cpp
@@ -66,9 +66,9 @@ static const char *directoryGlobs[] = {
 	0
 };
 
-class WintermuteMetaEngine : public AdvancedMetaEngine {
+class WintermuteMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	WintermuteMetaEngine() : AdvancedMetaEngine(Wintermute::gameDescriptions, sizeof(WMEGameDescription), Wintermute::wintermuteGames, gameGuiOptions) {
+	WintermuteMetaEngineStatic() : AdvancedMetaEngineStatic(Wintermute::gameDescriptions, sizeof(WMEGameDescription), Wintermute::wintermuteGames, gameGuiOptions) {
 		// Use kADFlagUseExtraAsHint to distinguish between SD and HD versions
 		// of J.U.L.I.A. when their datafiles sit in the same directory (e.g. in Steam distribution).
 		_flags = kADFlagUseExtraAsHint;
@@ -99,7 +99,7 @@ public:
 		if (metaEnginePlugin) {
 			const Plugin *enginePlugin = PluginMan.getEngineFromMetaEngine(metaEnginePlugin);
 			if (enginePlugin) {
-				return enginePlugin->get<AdvancedMetaEngineConnect>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
+				return enginePlugin->get<AdvancedMetaEngine>().fallbackDetectExtern(_md5Bytes, allFiles, fslist);
 			} else {
 				static bool warn = true;
 				if (warn) {
@@ -115,4 +115,4 @@ public:
 
 } // End of namespace Wintermute
 
-REGISTER_PLUGIN_STATIC(WINTERMUTE_DETECTION, PLUGIN_TYPE_METAENGINE, Wintermute::WintermuteMetaEngine);
+REGISTER_PLUGIN_STATIC(WINTERMUTE_DETECTION, PLUGIN_TYPE_METAENGINE, Wintermute::WintermuteMetaEngineStatic);
diff --git a/engines/wintermute/ext/wme_galaxy.cpp b/engines/wintermute/ext/wme_galaxy.cpp
index cd70a484c5..0c90e52838 100644
--- a/engines/wintermute/ext/wme_galaxy.cpp
+++ b/engines/wintermute/ext/wme_galaxy.cpp
@@ -50,7 +50,7 @@ SXWMEGalaxyAPI::SXWMEGalaxyAPI(BaseGame *inGame, ScStack *stack) : BaseScriptabl
 
 //////////////////////////////////////////////////////////////////////////
 void SXWMEGalaxyAPI::init() {
-	const MetaEngineConnect &meta = ((WintermuteEngine *)g_engine)->getMetaEngineConnect();
+	const MetaEngine &meta = ((WintermuteEngine *)g_engine)->getMetaEngineConnect();
 	const Common::String target = BaseEngine::instance().getGameTargetName();
 	_achievementsInfo = meta.getAchievementsInfo(target);
 
diff --git a/engines/wintermute/ext/wme_steam.cpp b/engines/wintermute/ext/wme_steam.cpp
index 62bc171869..7e5b0647db 100644
--- a/engines/wintermute/ext/wme_steam.cpp
+++ b/engines/wintermute/ext/wme_steam.cpp
@@ -50,7 +50,7 @@ SXSteamAPI::SXSteamAPI(BaseGame *inGame, ScStack *stack) : BaseScriptable(inGame
 
 //////////////////////////////////////////////////////////////////////////
 void SXSteamAPI::init() {
-	const MetaEngineConnect &meta = ((WintermuteEngine *)g_engine)->getMetaEngineConnect();
+	const MetaEngine &meta = ((WintermuteEngine *)g_engine)->getMetaEngineConnect();
 	const Common::String target = BaseEngine::instance().getGameTargetName();
 	_achievementsInfo = meta.getAchievementsInfo(target);
 
diff --git a/engines/wintermute/metaengine.cpp b/engines/wintermute/metaengine.cpp
index 7c92d3b10b..533d4b88f9 100644
--- a/engines/wintermute/metaengine.cpp
+++ b/engines/wintermute/metaengine.cpp
@@ -51,7 +51,7 @@ static ADGameDescription s_fallbackDesc = {
 
 static char s_fallbackExtraBuf[256];
 
-class WintermuteMetaEngineConnect : public AdvancedMetaEngineConnect {
+class WintermuteMetaEngine : public AdvancedMetaEngine {
 public:
     const char *getName() const override {
 		return "wintermute";
@@ -67,17 +67,17 @@ public:
 
 	bool hasFeature(MetaEngineFeature f) const override {
 		switch (f) {
-		case MetaEngineConnect::kSupportsListSaves:
+		case MetaEngine::kSupportsListSaves:
 			return true;
-		case MetaEngineConnect::kSupportsLoadingDuringStartup:
+		case MetaEngine::kSupportsLoadingDuringStartup:
 			return true;
-		case MetaEngineConnect::kSupportsDeleteSave:
+		case MetaEngine::kSupportsDeleteSave:
 			return true;
-		case MetaEngineConnect::kSavesSupportCreationDate:
+		case MetaEngine::kSavesSupportCreationDate:
 			return true;
-		case MetaEngineConnect::kSavesSupportMetaInfo:
+		case MetaEngine::kSavesSupportMetaInfo:
 			return true;
-		case MetaEngineConnect::kSavesSupportThumbnail:
+		case MetaEngine::kSavesSupportThumbnail:
 			return true;
 		default:
 			return false;
@@ -190,7 +190,7 @@ public:
 			if (!file->getName().hasSuffixIgnoreCase(".dcp")) continue;
 
 			FileProperties tmp;
-			if (AdvancedMetaEngineConnect::getFilePropertiesExtern(md5Bytes, allFiles, s_fallbackDesc, file->getName(), tmp)) {
+			if (AdvancedMetaEngine::getFilePropertiesExtern(md5Bytes, allFiles, s_fallbackDesc, file->getName(), tmp)) {
 				game.hasUnknownFiles = true;
 				game.matchedFiles[file->getName()] = tmp;
 			}
@@ -203,7 +203,7 @@ public:
 } // End of namespace Wintermute
 
 #if PLUGIN_ENABLED_DYNAMIC(WINTERMUTE)
-	REGISTER_PLUGIN_DYNAMIC(WINTERMUTE, PLUGIN_TYPE_ENGINE, Wintermute::WintermuteMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(WINTERMUTE, PLUGIN_TYPE_ENGINE, Wintermute::WintermuteMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(WINTERMUTE, PLUGIN_TYPE_ENGINE, Wintermute::WintermuteMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(WINTERMUTE, PLUGIN_TYPE_ENGINE, Wintermute::WintermuteMetaEngine);
 #endif
diff --git a/engines/xeen/detection.cpp b/engines/xeen/detection.cpp
index 9a17c5b971..816788ce7b 100644
--- a/engines/xeen/detection.cpp
+++ b/engines/xeen/detection.cpp
@@ -64,9 +64,9 @@ static const ADExtraGuiOptionsMap optionsList[] = {
 	AD_EXTRA_GUI_OPTIONS_TERMINATOR
 };
 
-class XeenMetaEngine : public AdvancedMetaEngine {
+class XeenMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	XeenMetaEngine() : AdvancedMetaEngine(Xeen::gameDescriptions, sizeof(Xeen::XeenGameDescription),
+	XeenMetaEngineStatic() : AdvancedMetaEngineStatic(Xeen::gameDescriptions, sizeof(Xeen::XeenGameDescription),
 			XeenGames, optionsList) {
 		_maxScanDepth = 3;
 	}
@@ -84,4 +84,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(XEEN_DETECTION, PLUGIN_TYPE_METAENGINE, XeenMetaEngine);
+REGISTER_PLUGIN_STATIC(XEEN_DETECTION, PLUGIN_TYPE_METAENGINE, XeenMetaEngineStatic);
diff --git a/engines/xeen/metaengine.cpp b/engines/xeen/metaengine.cpp
index bbeca61390..44119b3bf4 100644
--- a/engines/xeen/metaengine.cpp
+++ b/engines/xeen/metaengine.cpp
@@ -69,7 +69,7 @@ bool XeenEngine::getIsCD() const {
 
 } // End of namespace Xeen
 
-class XeenMetaEngineConnect : public AdvancedMetaEngineConnect {
+class XeenMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "xeen";
@@ -83,7 +83,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool XeenMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool XeenMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -102,7 +102,7 @@ bool Xeen::XeenEngine::hasFeature(EngineFeature f) const {
 		(f == kSupportsSavingDuringRuntime);
 }
 
-bool XeenMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool XeenMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const Xeen::XeenGameDescription *gd = (const Xeen::XeenGameDescription *)desc;
 
 	switch (gd->gameID) {
@@ -121,7 +121,7 @@ bool XeenMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const
 	return true;
 }
 
-SaveStateList XeenMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList XeenMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	Common::StringArray filenames;
 	Common::String saveDesc;
@@ -151,16 +151,16 @@ SaveStateList XeenMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int XeenMetaEngineConnect::getMaximumSaveSlot() const {
+int XeenMetaEngine::getMaximumSaveSlot() const {
 	return MAX_SAVES;
 }
 
-void XeenMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void XeenMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	g_system->getSavefileManager()->removeSavefile(filename);
 }
 
-SaveStateDescriptor XeenMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor XeenMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03d", target, slot);
 	Common::InSaveFile *f = g_system->getSavefileManager()->openForLoading(filename);
 
@@ -187,7 +187,7 @@ SaveStateDescriptor XeenMetaEngineConnect::querySaveMetaInfos(const char *target
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(XEEN)
-	REGISTER_PLUGIN_DYNAMIC(XEEN, PLUGIN_TYPE_ENGINE, XeenMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(XEEN, PLUGIN_TYPE_ENGINE, XeenMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(XEEN, PLUGIN_TYPE_ENGINE, XeenMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(XEEN, PLUGIN_TYPE_ENGINE, XeenMetaEngine);
 #endif
diff --git a/engines/zvision/detection.cpp b/engines/zvision/detection.cpp
index c70f8d546d..52c149b955 100644
--- a/engines/zvision/detection.cpp
+++ b/engines/zvision/detection.cpp
@@ -32,9 +32,9 @@
 #include "zvision/detection.h"
 #include "zvision/detection_tables.h"
 
-class ZVisionMetaEngine : public AdvancedMetaEngine {
+class ZVisionMetaEngineStatic : public AdvancedMetaEngineStatic {
 public:
-	ZVisionMetaEngine() : AdvancedMetaEngine(ZVision::gameDescriptions, sizeof(ZVision::ZVisionGameDescription), ZVision::zVisionGames, ZVision::optionsList) {
+	ZVisionMetaEngineStatic() : AdvancedMetaEngineStatic(ZVision::gameDescriptions, sizeof(ZVision::ZVisionGameDescription), ZVision::zVisionGames, ZVision::optionsList) {
 		_maxScanDepth = 2;
 		_directoryGlobs = ZVision::directoryGlobs;
 	}
@@ -52,4 +52,4 @@ public:
 	}
 };
 
-REGISTER_PLUGIN_STATIC(ZVISION_DETECTION, PLUGIN_TYPE_METAENGINE, ZVisionMetaEngine);
+REGISTER_PLUGIN_STATIC(ZVISION_DETECTION, PLUGIN_TYPE_METAENGINE, ZVisionMetaEngineStatic);
diff --git a/engines/zvision/metaengine.cpp b/engines/zvision/metaengine.cpp
index 1732a0e5ed..f119c53bd1 100644
--- a/engines/zvision/metaengine.cpp
+++ b/engines/zvision/metaengine.cpp
@@ -51,7 +51,7 @@ uint32 ZVision::getFeatures() const {
 
 } // End of namespace ZVision
 
-class ZVisionMetaEngineConnect : public AdvancedMetaEngineConnect {
+class ZVisionMetaEngine : public AdvancedMetaEngine {
 public:
 	const char *getName() const override {
 		return "zvision";
@@ -67,7 +67,7 @@ public:
 	SaveStateDescriptor querySaveMetaInfos(const char *target, int slot) const override;
 };
 
-bool ZVisionMetaEngineConnect::hasFeature(MetaEngineFeature f) const {
+bool ZVisionMetaEngine::hasFeature(MetaEngineFeature f) const {
 	return
 		(f == kSupportsListSaves) ||
 		(f == kSupportsLoadingDuringStartup) ||
@@ -104,7 +104,7 @@ bool ZVision::ZVision::canSaveGameStateCurrently() {
 	return !_videoIsPlaying && currentLocation.world != 'g' && !(currentLocation.room == 'j' || currentLocation.room == 'a');
 }
 
-Common::KeymapArray ZVisionMetaEngineConnect::initKeymaps(const char *target) const {
+Common::KeymapArray ZVisionMetaEngine::initKeymaps(const char *target) const {
 	using namespace Common;
 	using namespace ZVision;
 
@@ -232,7 +232,7 @@ Common::KeymapArray ZVisionMetaEngineConnect::initKeymaps(const char *target) co
 	return keymaps;
 }
 
-bool ZVisionMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
+bool ZVisionMetaEngine::createInstance(OSystem *syst, Engine **engine, const ADGameDescription *desc) const {
 	const ZVision::ZVisionGameDescription *gd = (const ZVision::ZVisionGameDescription *)desc;
 	if (gd) {
 		*engine = new ZVision::ZVision(syst, gd);
@@ -240,7 +240,7 @@ bool ZVisionMetaEngineConnect::createInstance(OSystem *syst, Engine **engine, co
 	return gd != 0;
 }
 
-SaveStateList ZVisionMetaEngineConnect::listSaves(const char *target) const {
+SaveStateList ZVisionMetaEngine::listSaves(const char *target) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	ZVision::SaveGameHeader header;
 	Common::String pattern = target;
@@ -275,16 +275,16 @@ SaveStateList ZVisionMetaEngineConnect::listSaves(const char *target) const {
 	return saveList;
 }
 
-int ZVisionMetaEngineConnect::getMaximumSaveSlot() const {
+int ZVisionMetaEngine::getMaximumSaveSlot() const {
 	return 999;
 }
 
-void ZVisionMetaEngineConnect::removeSaveState(const char *target, int slot) const {
+void ZVisionMetaEngine::removeSaveState(const char *target, int slot) const {
 	Common::SaveFileManager *saveFileMan = g_system->getSavefileManager();
 	saveFileMan->removeSavefile(Common::String::format("%s.%03u", target, slot));
 }
 
-SaveStateDescriptor ZVisionMetaEngineConnect::querySaveMetaInfos(const char *target, int slot) const {
+SaveStateDescriptor ZVisionMetaEngine::querySaveMetaInfos(const char *target, int slot) const {
 	Common::String filename = Common::String::format("%s.%03u", target, slot);
 	Common::InSaveFile *in = g_system->getSavefileManager()->openForLoading(filename.c_str());
 
@@ -332,7 +332,7 @@ SaveStateDescriptor ZVisionMetaEngineConnect::querySaveMetaInfos(const char *tar
 }
 
 #if PLUGIN_ENABLED_DYNAMIC(ZVISION)
-	REGISTER_PLUGIN_DYNAMIC(ZVISION, PLUGIN_TYPE_ENGINE, ZVisionMetaEngineConnect);
+	REGISTER_PLUGIN_DYNAMIC(ZVISION, PLUGIN_TYPE_ENGINE, ZVisionMetaEngine);
 #else
-	REGISTER_PLUGIN_STATIC(ZVISION, PLUGIN_TYPE_ENGINE, ZVisionMetaEngineConnect);
+	REGISTER_PLUGIN_STATIC(ZVISION, PLUGIN_TYPE_ENGINE, ZVisionMetaEngine);
 #endif


Commit: 992abce74a14c7ad7b382b302d9e75d4afd0e2ea
    https://github.com/scummvm/scummvm/commit/992abce74a14c7ad7b382b302d9e75d4afd0e2ea
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: Rename getMetaEngine helpers

- getME -> getMetaEngineStatic (static parts)
- getMEC -> getMetaEngine (dynamic parts)

Changed paths:
    engines/cine/metaengine.cpp
    engines/dialogs.cpp
    engines/engine.cpp
    engines/engine.h
    engines/glk/metaengine.cpp
    engines/ultima/ultima8/ultima8.cpp
    engines/wintermute/ext/wme_galaxy.cpp
    engines/wintermute/ext/wme_steam.cpp


diff --git a/engines/cine/metaengine.cpp b/engines/cine/metaengine.cpp
index 60cd0fb1b7..45447f58cf 100644
--- a/engines/cine/metaengine.cpp
+++ b/engines/cine/metaengine.cpp
@@ -331,7 +331,7 @@ Common::Error CineEngine::saveGameState(int slot, const Common::String &desc, bo
 }
 
 Common::String CineEngine::getSaveStateName(int slot) const {
-	return getMetaEngineConnect().getSavegameFile(slot, _targetName.c_str());
+	return getMetaEngine().getSavegameFile(slot, _targetName.c_str());
 }
 
 bool CineEngine::canLoadGameStateCurrently() {
diff --git a/engines/dialogs.cpp b/engines/dialogs.cpp
index c17ede7993..dd0dc630ec 100644
--- a/engines/dialogs.cpp
+++ b/engines/dialogs.cpp
@@ -273,7 +273,7 @@ ConfigDialog::ConfigDialog() :
 	assert(g_engine);
 
 	const Common::String &gameDomain = ConfMan.getActiveDomainName();
-	const MetaEngine &metaEngineConnect = g_engine->getMetaEngineConnect();
+	const MetaEngine &metaEngine = g_engine->getMetaEngine();
 
 	// GUI:  Add tab widget
 	GUI::TabWidget *tab = new GUI::TabWidget(this, "GlobalConfig.TabWidget");
@@ -285,7 +285,7 @@ ConfigDialog::ConfigDialog() :
 	int tabId = tab->addTab(_("Game"), "GlobalConfig_Engine");
 
 	if (g_engine->hasFeature(Engine::kSupportsChangingOptionsDuringRuntime)) {
-		_engineOptions = metaEngineConnect.buildEngineOptionsWidgetDynamic(tab, "GlobalConfig_Engine.Container", gameDomain);
+		_engineOptions = metaEngine.buildEngineOptionsWidgetDynamic(tab, "GlobalConfig_Engine.Container", gameDomain);
 	}
 
 	if (_engineOptions) {
@@ -321,7 +321,7 @@ ConfigDialog::ConfigDialog() :
 	// The Keymap tab
 	//
 
-	Common::KeymapArray keymaps = metaEngineConnect.initKeymaps(gameDomain.c_str());
+	Common::KeymapArray keymaps = metaEngine.initKeymaps(gameDomain.c_str());
 	if (!keymaps.empty()) {
 		tab->addTab(_("Keymaps"), "GlobalConfig_KeyMapper");
 		addKeyMapperControls(tab, "GlobalConfig_KeyMapper.", keymaps, gameDomain);
@@ -330,7 +330,7 @@ ConfigDialog::ConfigDialog() :
 	//
 	// The Achievements tab
 	//
-	Common::AchievementsInfo achievementsInfo = metaEngineConnect.getAchievementsInfo(gameDomain);
+	Common::AchievementsInfo achievementsInfo = metaEngine.getAchievementsInfo(gameDomain);
 	if (achievementsInfo.descriptions.size() > 0) {
 		tab->addTab(_("Achievements"), "GlobalConfig_Achievements");
 		addAchievementsControls(tab, "GlobalConfig_Achievements.", achievementsInfo);
diff --git a/engines/engine.cpp b/engines/engine.cpp
index e0e045b1bb..10e657086b 100644
--- a/engines/engine.cpp
+++ b/engines/engine.cpp
@@ -531,7 +531,7 @@ void Engine::saveAutosaveIfEnabled() {
 
 		if (saveFlag) {
 			// First check for an existing savegame in the slot, and if present, if it's an autosave
-			SaveStateDescriptor desc = getMetaEngineConnect().querySaveMetaInfos(
+			SaveStateDescriptor desc = getMetaEngine().querySaveMetaInfos(
 				_targetName.c_str(), getAutosaveSlot());
 			saveFlag = desc.getSaveSlot() == -1 || desc.isAutosave();
 		}
@@ -865,13 +865,13 @@ EnginePlugin *Engine::getMetaEnginePlugin() const {
 
 */
 
-MetaEngineStatic &Engine::getMetaEngine() {
+MetaEngineStatic &Engine::getMetaEngineStatic() {
 	const Plugin *plugin = EngineMan.findPlugin(ConfMan.get("engineid"));
 	assert(plugin);
 	return plugin->get<MetaEngineStatic>();
 }
 
-MetaEngine &Engine::getMetaEngineConnect() {
+MetaEngine &Engine::getMetaEngine() {
 	const Plugin *metaEnginePlugin = EngineMan.findPlugin(ConfMan.get("engineid"));
 	assert(metaEnginePlugin);
 
diff --git a/engines/engine.h b/engines/engine.h
index 24d0283870..c8360fba84 100644
--- a/engines/engine.h
+++ b/engines/engine.h
@@ -379,8 +379,8 @@ public:
 	 */
 	static bool shouldQuit();
 
-	static MetaEngineStatic &getMetaEngine();
-	static MetaEngine &getMetaEngineConnect();
+	static MetaEngineStatic &getMetaEngineStatic();
+	static MetaEngine &getMetaEngine();
 
 	/**
 	 * Pause the engine. This should stop any audio playback
diff --git a/engines/glk/metaengine.cpp b/engines/glk/metaengine.cpp
index d73ad00c1b..ea9227cfff 100644
--- a/engines/glk/metaengine.cpp
+++ b/engines/glk/metaengine.cpp
@@ -145,7 +145,7 @@ Common::String GlkMetaEngine::findFileByGameId(const Common::String &gameId) con
 	folder.getChildren(fslist, Common::FSNode::kListFilesOnly);
 
 	// Get the matching MetaEngine for this Engine.
-	const MetaEngineStatic &metaEngine = g_engine->getMetaEngine();
+	const MetaEngineStatic &metaEngine = g_engine->getMetaEngineStatic();
 
 	// Iterate over the files
 	for (Common::FSList::iterator i = fslist.begin(); i != fslist.end(); ++i) {
diff --git a/engines/ultima/ultima8/ultima8.cpp b/engines/ultima/ultima8/ultima8.cpp
index d11a899ab8..88be4868eb 100644
--- a/engines/ultima/ultima8/ultima8.cpp
+++ b/engines/ultima/ultima8/ultima8.cpp
@@ -1105,7 +1105,7 @@ bool Ultima8Engine::newGame(int saveSlot) {
 
 	// First validate we still have a save file for the slot
 	if (saveSlot != -1) {
-		SaveStateDescriptor desc = getMetaEngineConnect().querySaveMetaInfos(_targetName.c_str(), saveSlot);
+		SaveStateDescriptor desc = getMetaEngine().querySaveMetaInfos(_targetName.c_str(), saveSlot);
 		if (desc.getSaveSlot() != saveSlot)
 			saveSlot = -1;
 	}
diff --git a/engines/wintermute/ext/wme_galaxy.cpp b/engines/wintermute/ext/wme_galaxy.cpp
index 0c90e52838..3d42cc4d43 100644
--- a/engines/wintermute/ext/wme_galaxy.cpp
+++ b/engines/wintermute/ext/wme_galaxy.cpp
@@ -50,7 +50,7 @@ SXWMEGalaxyAPI::SXWMEGalaxyAPI(BaseGame *inGame, ScStack *stack) : BaseScriptabl
 
 //////////////////////////////////////////////////////////////////////////
 void SXWMEGalaxyAPI::init() {
-	const MetaEngine &meta = ((WintermuteEngine *)g_engine)->getMetaEngineConnect();
+	const MetaEngine &meta = ((WintermuteEngine *)g_engine)->getMetaEngine();
 	const Common::String target = BaseEngine::instance().getGameTargetName();
 	_achievementsInfo = meta.getAchievementsInfo(target);
 
diff --git a/engines/wintermute/ext/wme_steam.cpp b/engines/wintermute/ext/wme_steam.cpp
index 7e5b0647db..c776d9ec35 100644
--- a/engines/wintermute/ext/wme_steam.cpp
+++ b/engines/wintermute/ext/wme_steam.cpp
@@ -50,7 +50,7 @@ SXSteamAPI::SXSteamAPI(BaseGame *inGame, ScStack *stack) : BaseScriptable(inGame
 
 //////////////////////////////////////////////////////////////////////////
 void SXSteamAPI::init() {
-	const MetaEngine &meta = ((WintermuteEngine *)g_engine)->getMetaEngineConnect();
+	const MetaEngine &meta = ((WintermuteEngine *)g_engine)->getMetaEngine();
 	const Common::String target = BaseEngine::instance().getGameTargetName();
 	_achievementsInfo = meta.getAchievementsInfo(target);
 


Commit: e3e8e818158514c1920aa229e574d93a7c24ec1c
    https://github.com/scummvm/scummvm/commit/e3e8e818158514c1920aa229e574d93a7c24ec1c
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
ENGINES: METAENGINE: Improve comments

Changed paths:
    engines/advancedDetector.h
    engines/metaengine.h


diff --git a/engines/advancedDetector.h b/engines/advancedDetector.h
index 33ae44c87c..a48b5cdb8a 100644
--- a/engines/advancedDetector.h
+++ b/engines/advancedDetector.h
@@ -166,7 +166,7 @@ struct ADExtraGuiOptionsMap {
 #define AD_EXTRA_GUI_OPTIONS_TERMINATOR { 0, { 0, 0, 0, 0 } }
 
 /**
- * A MetaEngine implementation based around the advanced detector code.
+ * A MetaEngineStatic implementation based around the advanced detector code.
  */
 class AdvancedMetaEngineStatic : public MetaEngineStatic {
 protected:
@@ -325,7 +325,7 @@ protected:
 };
 
 /**
- * A MetaEngineConnect implementation of AdvancedMetaEngine.
+ * A MetaEngine implementation of AdvancedMetaEngine.
  */
 class AdvancedMetaEngine : public MetaEngine {
 public:
diff --git a/engines/metaengine.h b/engines/metaengine.h
index db71cadf5a..816a19f1da 100644
--- a/engines/metaengine.h
+++ b/engines/metaengine.h
@@ -94,13 +94,13 @@ struct ExtendedSavegameHeader {
 };
 
 /**
- * A meta engine is essentially a factory for Engine instances with the
+ * A meta engine static is essentially a factory for Engine instances with the
  * added ability of listing and detecting supported games.
- * Every engine "plugin" provides a hook to get an instance of a MetaEngine
- * subclass for that "engine plugin". E.g. SCUMM povides ScummMetaEngine.
+ * Every engine "plugin" provides a hook to get an instance of a MetaEngineStatic
+ * subclass for that "engine plugin". E.g. SCUMM povides ScummMetaEngineStatic.
  * This is then in turn used by the frontend code to detect games,
  * and other useful functionality. To instantiate actual Engine objects,
- * See the class MetaEngineConnect below.
+ * See the class MetaEngine below.
  */
 class MetaEngineStatic : public PluginObject {
 public:
@@ -168,11 +168,11 @@ public:
 };
 
 /**
- * A MetaEngineConnect is another factory for Engine instances, and is very
+ * A MetaEngine is another factory for Engine instances, and is very
  * similiar to meta engines. This class, however, composes of bridged functionalities
  * that can be used to connect an actual Engine with a MetaEngine.
- * Every engine "plugin" provides a hook to get an instance of MetaEngineConnector subclass
- * for that "engine plugin.". E.g. SCUMM provides a ScummMetaEngineConnect.
+ * Every engine "plugin" provides a hook to get an instance of MetaEngine subclass
+ * for that "engine plugin.". E.g. SCUMM provides a ScummMetaEngine.
  * This is then in turn used for things like instantiating engine objects, listing savefiles,
  * querying save metadata, etc.
  * Since engine plugins can be used a external runtime libraries, these can live and build inside


Commit: 41af1b63a9b5d359958ad23677e0b3e5d8fef8c6
    https://github.com/scummvm/scummvm/commit/41af1b63a9b5d359958ad23677e0b3e5d8fef8c6
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
BASE: PLUGINS: Improve fb detection for Sci & Wintermute

Changed paths:
    base/main.cpp
    base/plugins.cpp
    engines/sci/detection.cpp
    engines/wintermute/detection.cpp


diff --git a/base/main.cpp b/base/main.cpp
index 0528746277..e93951ea97 100644
--- a/base/main.cpp
+++ b/base/main.cpp
@@ -436,6 +436,7 @@ extern "C" int scummvm_main(int argc, const char * const argv[]) {
 		gDebugChannelsOnly = true;
 
 
+	ConfMan.registerDefault("always_run_fallback_detection_extern", true);
 	PluginManager::instance().init();
  	PluginManager::instance().loadAllPlugins(); // load plugins for cached plugin manager
 	PluginManager::instance().loadDetectionPlugin(); // load detection plugin for uncached plugin manager
diff --git a/base/plugins.cpp b/base/plugins.cpp
index 18161c14bc..26253dfd8c 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -340,6 +340,7 @@ Plugin *PluginManager::getMetaEngineFromEngine(const Plugin *plugin) {
 void PluginManagerUncached::init() {
 	unloadAllPlugins();
 	_allEnginePlugins.clear();
+	ConfMan.setBool("always_run_fallback_detection_extern", false);
 
 	unloadPluginsExcept(PLUGIN_TYPE_ENGINE, NULL, false); // empty the engine plugins
 
diff --git a/engines/sci/detection.cpp b/engines/sci/detection.cpp
index b1122debc5..6e0e1c58d2 100644
--- a/engines/sci/detection.cpp
+++ b/engines/sci/detection.cpp
@@ -450,6 +450,14 @@ ADDetectedGame SciMetaEngineStatic::fallbackDetect(const FileMap &allFiles, cons
 	 * Fallback detection for Sci heavily depends on engine resources, so it's not possible
 	 * to use them without the engine present in a clean way.
 	 */
+
+	if (ConfMan.hasKey("always_run_fallback_detection_extern")) {
+		if (ConfMan.getBool("always_run_fallback_detection_extern") == false) {
+			warning("SCI: Fallback detection is disabled.");
+			return ADDetectedGame();
+		}
+	}
+
 	const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
 
 	if (metaEnginePlugin) {
@@ -459,7 +467,7 @@ ADDetectedGame SciMetaEngineStatic::fallbackDetect(const FileMap &allFiles, cons
 		} else {
 			static bool warn = true;
 			if (warn) {
-				warning("Engine plugin for Sci not found. Some games will fail to be detected until an engine plugin is present.");
+				warning("Engine plugin for Sci not present. Fallback detection is disabled.");
 				warn = false;
 			}
 		}
diff --git a/engines/wintermute/detection.cpp b/engines/wintermute/detection.cpp
index e6f304509b..4318d7e0b1 100644
--- a/engines/wintermute/detection.cpp
+++ b/engines/wintermute/detection.cpp
@@ -94,6 +94,14 @@ public:
 		 * Fallback detection for Wintermute heavily depends on engine resources, so it's not possible
 		 * to use them without the engine present in a clean way.
 		 */
+
+		if (ConfMan.hasKey("always_run_fallback_detection_extern")) {
+			if (ConfMan.getBool("always_run_fallback_detection_extern") == false) {
+				warning("WINTERMUTE: Fallback detection is disabled.");
+				return ADDetectedGame();
+			}
+		}
+
 		const Plugin *metaEnginePlugin = EngineMan.findPlugin(getEngineId());
 
 		if (metaEnginePlugin) {
@@ -103,7 +111,7 @@ public:
 			} else {
 				static bool warn = true;
 				if (warn) {
-					warning("Engine plugin for Wintermute not found. Some games will fail to be detected until an engine plugin is present.");
+					warning("Engine plugin for Wintermute not present. Fallback detection is disabled.");
 					warn = false;
 				}
 			}


Commit: ffa69bfb26e94b2c04c0cce646308f60d2883b84
    https://github.com/scummvm/scummvm/commit/ffa69bfb26e94b2c04c0cce646308f60d2883b84
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
GUI: debug statements related to plugins matching -> level 9.

Changed paths:
    base/plugins.cpp


diff --git a/base/plugins.cpp b/base/plugins.cpp
index 26253dfd8c..723f960200 100644
--- a/base/plugins.cpp
+++ b/base/plugins.cpp
@@ -297,11 +297,11 @@ Plugin *PluginManager::getEngineFromMetaEngine(const Plugin *plugin) {
 	} while (!found && PluginMan.loadNextPlugin());
 
 	if (enginePlugin) {
-		warning("MetaEngine: %s \t matched to \t Engine: %s", plugin->getName(), enginePlugin->getFileName());
+		debug(9, "MetaEngine: %s \t matched to \t Engine: %s", plugin->getName(), enginePlugin->getFileName());
 		return enginePlugin;
 	}
 
-	warning("MetaEngine: %s couldn't find a match for an engine plugin.", plugin->getName());
+	debug(9, "MetaEngine: %s couldn't find a match for an engine plugin.", plugin->getName());
 	return nullptr;
 }
 
@@ -326,11 +326,11 @@ Plugin *PluginManager::getMetaEngineFromEngine(const Plugin *plugin) {
 	}
 
 	if (metaEngine) {
-		warning("Engine: %s matched to MetaEngine: %s", plugin->getFileName(), metaEngine->getName());
+		debug(9, "Engine: %s matched to MetaEngine: %s", plugin->getFileName(), metaEngine->getName());
 		return metaEngine;
 	}
 
-	warning("Engine: %s couldn't find a match for an MetaEngine plugin.", plugin->getFileName());
+	debug(9, "Engine: %s couldn't find a match for an MetaEngine plugin.", plugin->getFileName());
 	return nullptr;
 }
 
@@ -366,6 +366,7 @@ void PluginManagerUncached::init() {
 				if (pName.hasSuffix(detectPluginName)) {
 					_detectionPlugin = (*p);
 					foundDetectPlugin = true;
+					debug(9, "Detection plugin found!");
 					continue;
 				}
 			}
@@ -446,7 +447,7 @@ void PluginManagerUncached::loadDetectionPlugin() {
 	bool linkMetaEngines = false;
 
 	if (_isDetectionLoaded) {
-		warning("Detection plugin is already loaded. Adding each available engines to the memory.");
+		debug(9, "Detection plugin is already loaded. Adding each available engines to the memory.");
 		linkMetaEngines = true;
 	} else {
 		if (_detectionPlugin) {
@@ -456,11 +457,11 @@ void PluginManagerUncached::loadDetectionPlugin() {
 				linkMetaEngines = true;
 				_isDetectionLoaded = true;
 			} else {
-				warning("Detection plugin was not loaded correctly.");
+				debug(9, "Detection plugin was not loaded correctly.");
 				return;
 			}
 		} else {
-			warning("Detection plugin not found.");
+			debug(9, "Detection plugin not found.");
 			return;
 		}
 	}
@@ -480,7 +481,7 @@ void PluginManagerUncached::unloadDetectionPlugin() {
 		_detectionPlugin->unloadPlugin();
 		_isDetectionLoaded = false;
 	} else {
-		warning("Detection plugin is already unloaded.");
+		debug(9, "Detection plugin is already unloaded.");
 	}
 }
 


Commit: a8a4c25361f17f44714d65a152664ccac6e9bccb
    https://github.com/scummvm/scummvm/commit/a8a4c25361f17f44714d65a152664ccac6e9bccb
Author: aryanrawlani28 (aryanrawlani007 at gmail.com)
Date: 2020-10-03T14:56:36+02:00

Commit Message:
PLUGINS: Rename detection plugin

- DetectionConnect -> DetectionDynamic

Changed paths:
    engines/detection.cpp


diff --git a/engines/detection.cpp b/engines/detection.cpp
index c8ea7c9b5b..fa143c4cb4 100644
--- a/engines/detection.cpp
+++ b/engines/detection.cpp
@@ -28,10 +28,10 @@
 #include "engines/detection.h"
 
 
-class DetectionConnect : public Detection {
+class DetectionDynamic : public Detection {
 public:
-    DetectionConnect() {}
-    ~DetectionConnect() {}
+    DetectionDynamic() {}
+    ~DetectionDynamic() {}
 
     const char *getName() const override {
         return "detection";
@@ -51,6 +51,6 @@ public:
     }
 };
 
-REGISTER_PLUGIN_DYNAMIC(DETECTION_DYNAMIC, PLUGIN_TYPE_DETECTION, DetectionConnect);
+REGISTER_PLUGIN_DYNAMIC(DETECTION_DYNAMIC, PLUGIN_TYPE_DETECTION, DetectionDynamic);
 
 #endif // !DETECTION_STATIC




More information about the Scummvm-git-logs mailing list