//================================================================
// General plugin framework
//
// AUTHOR:  Gabor Nagy
// DATE:    2026-Jan-07 01:02:40
//
// Copyright (C) 1996-2026 by Gabor Nagy. All rights reserved.
//================================================================

#ifndef _EPlugins_h
#define _EPlugins_h

#include <EParam.h>
#include <EResource.h>
#include <EClass.h>
#include <ELog.h>

#if defined (__cplusplus) && (!(defined (__CPLUSLIBS)))
extern "C" {
#endif


typedef struct EPlugin_S      EPlugin;
typedef struct EPluginLock_S  EPluginLock;


typedef int	(*EPluginLockDelFunc)(EPlugin* PPlugin, EPluginLock* PLock);
typedef int (*EPluginInitFunc)(EPlugin* PPlugin);      // Function to call at program start in the DSO
typedef int (*EPluginExitFunc)(const EBool PExiting);  // Name of the function to call when unloading the plugin

struct EPluginLock_S
{
	ENamedCore;
	EPluginLockDelFunc  LockDel;
};


typedef struct EPluginComponent_S       EPluginComponent;
typedef struct EPluginComponentClass_S  EPluginComponentClass;

struct EPluginComponentClass_S
{
	ECoreClassCore(EPluginComponent);
};



// Plugin structure
//
struct EPlugin_S
{
	EList(, EPluginLock*, Locks);           // The Plugin is in use (it has a dialog box displayed, or it globally references Objects etc.). See EPluginLock_Del
	void*            DLHandle;              // DL handle associated with the DSO (necessary for unloading the DSO)
	char*            Name;                  // Set from "E_PluginName" or from the "Plugins.list" file
	char*            Info;                  // Summary of the plugin from "E_PluginInfo"
	EPluginInitFunc  InitFunction;          // Function to call at program start in the DSO
	EPluginExitFunc  ExitFunction;          // Name of the function to call when unloading the plugin
	char*            DSOName;               // Name of the Dynamic Shared Object (DSO)
	char*            PathName;              // Path where the DSO was found
	char*            ErrorMessage;          // If there was a problem loading this plugin...
	EResource*       Resources;             // List of resources (settings) set by E_PluginInit()
	char*            ResourceFileName;
	EBool            Load, AutoReload;      // Load plugin on startup

	ETime            LastLoadedTime;

	EList(, EPluginComponent, Components);  // Plugin global variables
};
EListA_t(EPlugin);

enum
{
	EPluginFromSTARTUP = 1,
	EPluginFromUI,
	EPluginFromTIMER
};

extern const char  EPlugin_DSOSuffix[];

extern int    EPlugin_Init(void* PItem, void* PTmpData);
extern int    EPlugin_GetFields(void* PP, void* PTmpData, const char* PCmdStr, const char* PValStr);
extern int    EPlugin_Load(void* PItems, const int PNumOfItems, void* PItem, const char* PPathName, void* PTmpData, ELogFunc PLogFuntion);
extern int    EPlugin_Unload(EPlugin* PPlugin, const EBool PExiting);
extern void   EPlugin_Free(EPlugin* PPlugin, const EBool PFreeStruct);

extern EPluginLock*  EPluginLock_Add(EPlugin* PPlugin, const char* PName, EPluginLockDelFunc PLockDel);
extern int           EPluginLock_Del(EPlugin* PPlugin, EPluginLock** PLockP, const EBool PNotify);


#if defined (__cplusplus) && (!(defined (__CPLUSLIBS)))
}	// Close scope of 'extern "C"' declaration
#endif

#endif // _EPlugins_h
