1
0
mirror of https://github.com/alliedmodders/metamod-source.git synced 2025-02-20 13:54:14 +01:00

abi is now locked

--HG--
extra : convert_revision : svn%3Ac2935e3e-5518-0410-8daf-afa5dab7d4e3/trunk%40486
This commit is contained in:
David Anderson 2007-10-08 20:21:14 +00:00
parent ddb9047904
commit 13408739bd
6 changed files with 103 additions and 41 deletions

View File

@ -38,7 +38,7 @@
#include <IPluginManager.h>
#include <ISmmAPI.h>
#define METAMOD_PLAPI_VERSION 13 /**< Version of this header file */
#define METAMOD_PLAPI_VERSION 14 /**< Version of this header file */
#define METAMOD_PLAPI_NAME "ISmmPlugin" /**< Name of the plugin interface */
namespace SourceMM

View File

@ -30,9 +30,11 @@
namespace SourceMM
{
class ISmmAPI;
class ISmmPlugin;
}
typedef SourceMM::ISmmPlugin METAMOD_PLUGIN;
/**
* @file ISmmPluginExt.h Definitions for extended plugin exposure syntax.
* @brief Provides an alternate method for loading plugins, without needing to
@ -74,14 +76,17 @@ struct MetamodLoaderInfo
* @param mli MetamodLoaderInfo structure.
* @return ISmmAPI pointer, or NULL if none.
*/
typedef SourceMM::ISmmAPI *(*METAMOD_FN_LOAD)(const MetamodVersionInfo *mvi,
const MetamodLoaderInfo *mli);
typedef METAMOD_PLUGIN *(*METAMOD_FN_LOAD)(const MetamodVersionInfo *mvi,
const MetamodLoaderInfo *mli);
/**
* @brief If a function of this type is exposed as "UnloadInterface_MMS", then
* Metamod:Source will attempt to call this function after calling
* ISmmAPI::Unload(), and before closing the library. This lets loader plugins
* clean up before exiting.
*
* Note: This function will be ignored unless CreateInterfce_MMS was exposed.
* It may be called even if ISmmAPI::Unload() could not be called.
*/
typedef void (*METAMOD_FN_UNLOAD)();

View File

@ -876,8 +876,8 @@ void MetamodSource::ConPrintf(const char *fmt, ...)
void MetamodSource::GetApiVersions(int &major, int &minor, int &plvers, int &plmin)
{
major = SM_VERS_API_MAJOR;
minor = SM_VERS_API_MINOR;
major = METAMOD_API_MAJOR;
minor = METAMOD_API_MINOR;
plvers = METAMOD_PLAPI_VERSION;
plmin = PLAPI_MIN_VERSION;
}

View File

@ -51,8 +51,8 @@ using namespace SourceMM;
*/
#define SOURCEMM_VERSION SVN_FILE_VERSION_STRING
#define SOURCEMM_DATE __DATE__
#define SM_VERS_API_MAJOR 2 //increase this on a breaking change
#define SM_VERS_API_MINOR 0 //increase this on a non-breaking API change
#define METAMOD_API_MAJOR 2 /* increase this on a breaking change */
#define METAMOD_API_MINOR 0 /* increase this on a non-breaking API change */
class MetamodSource : public ISmmAPI
{

View File

@ -60,6 +60,17 @@ using namespace SourceMM;
CPluginManager g_PluginMngr;
MetamodVersionInfo GlobVersionInfo =
{
METAMOD_API_MAJOR,
METAMOD_API_MINOR,
SH_IFACE_VERSION,
SH_IMPL_VERSION,
PLAPI_MIN_VERSION,
METAMOD_PLAPI_VERSION,
SOURCE_ENGINE_UNKNOWN
};
CPluginManager::CPluginManager()
{
m_LastId = Pl_MinId;
@ -139,7 +150,7 @@ void CPluginManager::SetAlias(const char *alias, const char *value)
}
}
CPluginManager::CPlugin::CPlugin() : m_Id(0), m_Source(0), m_API(NULL), m_Lib(NULL)
CPluginManager::CPlugin::CPlugin() : m_Id(0), m_Source(0), m_API(NULL), m_Lib(NULL), m_UnloadFn(NULL)
{
}
@ -415,63 +426,96 @@ CPluginManager::CPlugin *CPluginManager::_Load(const char *file, PluginId source
}
else
{
CreateInterfaceFn pfn = (CreateInterfaceFn)(dlsym(pl->m_Lib, PL_EXPOSURE_C));
if (!pfn)
pl->m_API = NULL;
/**
* First, try the new "advanced" interface
*/
METAMOD_FN_LOAD fnLoad = (METAMOD_FN_LOAD)dlsym(pl->m_Lib, "CreateInterface_MMS");
if (fnLoad != NULL)
{
if (error)
if (GlobVersionInfo.source_engine == SOURCE_ENGINE_UNKNOWN)
{
UTIL_Format(error, maxlen, "Function %s not found", PL_EXPOSURE_C);
GlobVersionInfo.source_engine = g_Metamod.GetSourceEngineBuild();
}
pl->m_Status = Pl_Error;
pl->m_API = fnLoad(&GlobVersionInfo, NULL);
pl->m_UnloadFn = (METAMOD_FN_UNLOAD)dlsym(pl->m_Lib, "UnloadInterface_MMS");
}
else
/**
* If we didn't get anything, try the normal/simple interface.
*/
if (pl->m_API == NULL)
{
pl->m_API = static_cast<ISmmPlugin *>((pfn)(METAMOD_PLAPI_NAME, NULL));
if (!pl->m_API)
CreateInterfaceFn pfn = (CreateInterfaceFn)(dlsym(pl->m_Lib, PL_EXPOSURE_C));
if (!pfn)
{
if (error)
{
UTIL_Format(error, maxlen, "Failed to get API");
UTIL_Format(error, maxlen, "Function %s not found", PL_EXPOSURE_C);
}
pl->m_Status = Pl_Error;
}
else
{
int api = pl->m_API->GetApiVersion();
if (api < PLAPI_MIN_VERSION)
pl->m_API = static_cast<ISmmPlugin *>((pfn)(METAMOD_PLAPI_NAME, NULL));
if (!pl->m_API)
{
if (error)
{
UTIL_Format(error, maxlen, "Plugin API %d is out of date with required minimum (%d)", api, PLAPI_MIN_VERSION);
UTIL_Format(error, maxlen, "Failed to get API");
}
pl->m_Status = Pl_Error;
}
else if (api > METAMOD_PLAPI_VERSION)
}
}
if (pl->m_API != NULL)
{
int api = pl->m_API->GetApiVersion();
if (api < PLAPI_MIN_VERSION)
{
if (error)
{
if (error)
if (api == 13)
{
UTIL_Format(error, maxlen, "Plugin API %d is newer than internal version (%d)", api, METAMOD_PLAPI_VERSION);
UTIL_Format(error, maxlen, "Plugin uses experimental Metamod build, probably 1.6.x (%d < %d)", api, PLAPI_MIN_VERSION);
}
pl->m_Status = Pl_Error;
}
else
{
if (pl->m_API->Load(pl->m_Id, &g_Metamod, error, maxlen, m_AllLoaded))
else if (api <= 12 && api >= 7)
{
pl->m_Status = Pl_Running;
if (m_AllLoaded)
{
//API 4 is when we added this callback
//Removing this code as the min version is now 5
//if (pl->m_API->GetApiVersion() >= 4)
pl->m_API->AllPluginsLoaded();
}
UTIL_Format(error, maxlen, "Older Metamod version required, probably 1.4.x (%d < %d)", api, PLAPI_MIN_VERSION);
}
else
{
pl->m_Status = Pl_Refused;
UTIL_Format(error, maxlen, "Older Metamod version required, probably 1.0 (%d < %d)", api, PLAPI_MIN_VERSION);
}
}
pl->m_Status = Pl_Error;
}
else if (api > METAMOD_PLAPI_VERSION)
{
if (error)
{
UTIL_Format(error, maxlen, "Plugin requires newer Metamod version (%d > %d)", api, METAMOD_PLAPI_VERSION);
}
pl->m_Status = Pl_Error;
}
else
{
if (pl->m_API->Load(pl->m_Id, &g_Metamod, error, maxlen, m_AllLoaded))
{
pl->m_Status = Pl_Running;
if (m_AllLoaded)
{
pl->m_API->AllPluginsLoaded();
}
}
else
{
pl->m_Status = Pl_Refused;
}
}
}
}
@ -483,6 +527,11 @@ CPluginManager::CPlugin *CPluginManager::_Load(const char *file, PluginId source
g_SourceHook.UnloadPlugin(pl->m_Id);
UnregAllConCmds(pl);
if (pl->m_UnloadFn != NULL)
{
pl->m_UnloadFn();
}
dlclose(pl->m_Lib);
pl->m_Lib = NULL;
pl->m_API = NULL;
@ -510,6 +559,11 @@ bool CPluginManager::_Unload(CPluginManager::CPlugin *pl, bool force, char *erro
UnregAllConCmds(pl);
if (pl->m_UnloadFn != NULL)
{
pl->m_UnloadFn();
}
//Clean up the DLL
dlclose(pl->m_Lib);
pl->m_Lib = NULL;

View File

@ -38,7 +38,8 @@
#include <convar.h>
#include <sh_list.h>
#include <sh_string.h>
#include "IPluginManager.h"
#include <IPluginManager.h>
#include <ISmmPluginExt.h>
#include "metamod_oslink.h"
/**
@ -58,10 +59,11 @@
* 10: Added VSP listen functions to ISmmAPI and IMetamodListener (2007-02-09)
* 11: New SourceHook version v4.5 (May, 2007)
* 12: Orange Box API
* MC 13: Breaking of API for next SH version and other API changes
* 13: Breaking of API for next SH version and other API changes
* MC 14: ABI stability reached for 1.6.0 changes
*/
#define PLAPI_MIN_VERSION 13
#define PLAPI_MIN_VERSION 14
struct CNameAlias
{
@ -91,6 +93,7 @@ public:
SourceHook::List<ConCommandBase *> m_Cvars;
SourceHook::List<ConCommandBase *> m_Cmds;
SourceHook::List<IMetamodListener *> m_Events;
METAMOD_FN_UNLOAD m_UnloadFn;
};
public:
CPluginManager();