#include #include #include #include "ragesecplugin.h" // GENERAL NOTES: // You'll frequently see references to the object RageSecPluginManagerServices. For all intents and purposes // this is your interface into the game. There won't be a lot exposed. This is a catch all parameter that // may be necessary for the DLL to get/set from the game itself. For the most part, I don't expect any // usage of the parameter itself, though it's available. // // The order of operations, that you should expect: // RageSecPlugin_Init() // ::Create() - Currently unchecked return value // ::Configure() - Currently unchecked return value // ::Work() - Currently unchecked return value // ::Destroy() - Currently unchecked return value // // The only functions you *need* are the RageSecPlugin_Init() and Work() functions // If you're not allocating any memory or doing anything fancy that requires configuration, you // should be okay removing these functions, and just setting the appropriate pointers to NULL // within the RageSecPlugin_Init() function // After everything compiles, take the compile DLL and place it in // X:\gta5\tools_ng\bin\RageSecPlugins\myDll.dll // It will automatically be detected by RageSec Engine, assuming you've done everything // correctly. To verify, the logging you want to add to your commandline.txt file is // -ragesecengine_all=debug3 // It doesn't matter what you name the DLL - all DLL's in that directory get picked up. // Standard declarations for exporting a DLL - pay this no mind #ifndef PLUGIN_API #ifdef WIN32 #define PLUGIN_API __declspec(dllexport) #else #define PLUGIN_API #endif #endif // IMPORTANT - Change this Plugin ID to a random 32-bit unsigned integer. #define PLUGIN_ID 0xABCD // This is where you should put any additional global definitions that you // might need. #define DEBUGGER_CHECK_POLLING_MS 5*1000 // Keep in mind that all of these variables need to be thread-safe, as // all the work is going to be executing in one of the RageSec Thread Pools // In this example, I'm not being appropriately thread safe for the sake of // brevity char *buffer; char *nameOfDll; // PURPOSE: This is where you should do any memory allocation that you might need. // This gets called after initialization, and before configuration // DO NOT DO ANY HEAVY LIFTING HERE. bool DllDebuggerCheckPlugin_Create(RageSecPluginManagerServices * services) { OutputDebugStringA("DllDebuggerCheckPlugin_Create"); // Create a generic buffer to write to buffer = new char[256]; memset((void*)buffer,0, 256); // Create the memory to fill the name of our DLL nameOfDll = new char[16]; memset((void*)nameOfDll,0, 16); return true; } // PURPOSE: Here's another step after memory creation that you have an // opportunity to configure any data that you might need. This is a // good place to set basic initial values or, you know, configuration // DO NOT DO ANY HEAVY LIFTING HERE. bool DllDebuggerCheckPlugin_Configure(RageSecPluginManagerServices * services) { OutputDebugStringA("DllDebuggerCheckPlugin_Configure"); sprintf(nameOfDll, "Ravenclaw"); return true; } // PURPOSE: This function allows you to clean up any memory that you've // allocated. // DO NOT DO ANY HEAVY LIFTING HERE. bool DllDebuggerCheckPlugin_Destroy(RageSecPluginManagerServices * services) { OutputDebugStringA("DllDebuggerCheckPlugin_Destroy"); delete nameOfDll; delete buffer; return true; } // PURPOSE: This is where your heavy lifting should go. This will execute on a worker // thread, and be executed depending on the execution type that you've indicated. bool DllDebuggerCheckPlugin_Work(RageSecPluginManagerServices * services) { // Insert heavy lifting logic here... OutputDebugStringA("DllDebuggerCheckPlugin_Work"); if(IsDebuggerPresent()) { sprintf(buffer, "%s:Debugger DETECTED from RageSecDLL",nameOfDll); //MessageBoxA(NULL, buffer, "RageSecPlugin::Work()", MB_OK); return false; } else { sprintf(buffer, "%s:Debugger NOT detected from RageSecDLL",nameOfDll); //MessageBoxA(NULL, buffer, "RageSecPlugin::Work()", MB_OK); return true; } } // This is the initialization function - this will always be called, and is // the very first entry point of the DLL. This should be nothing more // fancy than declaring your plugin parameters, and passing it along // to be registered. Any additional memory you need to create, should // go in the Create function // // IMPORTANT: Do not change the name of this function. It is what // RageSec looks for to initialize the plugin. The rest of the function // names won't matter, as you'll be providing the function pointers // to the RageSecPluginParameters object PLUGIN_API bool RageSecPlugin_Init(RageSecPluginManagerServices * services) { OutputDebugStringA("RageSecPlugin_Init"); // Declare local objects, for ease RageSecPluginParameters rs; RageSecPluginExtendedInformation ei; // This can be one of the following: // - EXECUTE_ONCE - Will execute once and never again // - EXECUTE_PERIODIC - Will execute periodically, depending on the value in ei.frequencyInMs // - EXECUTE_PERIODIC_RANDOM - Will execute periodically, between 0ms and the number of ms in set in ei.frequencyInMs // - EXECUTE_SCHEDULED - Will execute once, and never again, with a delay provided in ei.startTime // - EXECUTE_ALWAYS - Will continually execute, forever and ever, with no delay between executions // There isn't a lot of reason for this one - so be careful if you're usin git. // // This plugin will periodically be run rs.type = EXECUTE_PERIODIC; // Just initializing this for good engineering ei.startTime = 0; // I'm going to execute this plugin, every "DEBUGGER_CHECK_POLLING_MS" milliseconds ei.frequencyInMs = DEBUGGER_CHECK_POLLING_MS; // This is important: the versioning of the plugin needs to match that of the executable. // I default it to the #define's provided in the header file for safety rs.version.major = PLUGIN_VERSION_MAJOR; rs.version.minor = PLUGIN_VERSION_MINOR; // Set my function pointers for all the real work rs.Create = &DllDebuggerCheckPlugin_Create; rs.Configure = &DllDebuggerCheckPlugin_Configure; rs.Destroy = &DllDebuggerCheckPlugin_Destroy; rs.DoWork = &DllDebuggerCheckPlugin_Work; // Set the extended information parameter rs.extendedInfo = ei; // Register the plugin services->Register(&rs,PLUGIN_ID); return true; } // Being sure that you actually changed it // Steve suggested that I put this in the game - but if I'm compiling it as a separate // unit, I'd want to let you know as you're compiling the plugin. #if PLUGIN_ID == 0x1234 #error "Please change the PLUGIN_ID define to something other than 0x1234" #endif