Re: DSMPlugin.cpp issue [was: MSRC4 DSM requires write permission in UltraVNC folder?]

Charles Duffy <[email protected]> Sat, 01 Oct 2005 07:48:04 -0500
Newsgroups gmane.network.vnc.ultravnc.general
Message-ID <[email protected]>
Sean Covel wrote:
> This is actually a bad hack that doesn't work (I'm pretty sure it 
> doesn't work even if you DO have write access) and should be removed. If 
> you haven't posted anything on the UltraVNC forum about this problem you 
> should!

I have a patch intended to work around this issue. Emphasis on 
*intended* - I can't test it (beyond making sure it compiles with GCC) 
as I don't own a copy of Visual Studio; no Free compilers are supported 
by UltraVNC; and my Borland support patch doesn't cover building DSMs.

That said, it's probably pretty close to what's actually needed to do 
the trick, and should at least serve as a demonstration of one 
appropriate fix. Sean, I'd be curious to know if it Works For You (in 
terms of both the design and implementation).

(I haven't cross-posted this to the forum yet as it appears to be down 
on account of the $#^%! excuse for a database they're backending into).
DSMPluginRearchitect.patch (text/plain, 19 KB)
diff -ru3 UltraVnc-101-src/src/ultravnc/DSMPlugin/DSMPlugin.cpp UltraVnc-101-src.new/src/ultravnc/DSMPlugin/DSMPlugin.cpp
--- UltraVnc-101-src/src/ultravnc/DSMPlugin/DSMPlugin.cpp	2005-01-15 15:32:52.000000000 -0600
+++ UltraVnc-101-src.new/src/ultravnc/DSMPlugin/DSMPlugin.cpp	2005-10-01 07:43:39.703125000 -0500
@@ -89,7 +89,7 @@
 		lpString++;
 	}
 	*szToken = '\0' ;
-	if (( ! *lpString ) || (! *szToken)) return NULL;
+	if (( ! *lpString ) || (! *szToken)) return FALSE;
 	return FALSE;
 }
 
@@ -125,6 +125,8 @@
 	TRANSFORMBUFFER	m_PFreeBuffer = NULL;
 	RESET			m_PReset = NULL;
 
+	context = NULL;
+
 }
 
 //
@@ -135,6 +137,11 @@
 	// TODO: Log events
 	if (IsLoaded())
 		UnloadPlugin();
+#if 0
+	// TODO: if context isn't NULL, throw a warning that the plugin author screwed up.
+	if (context != NULL)
+		delete *context;
+#endif
 }
 
 
@@ -188,7 +195,7 @@
 bool CDSMPlugin::InitPlugin(void)
 {
 	// TODO: Log events
-	int nRes = (*m_PStartup)();
+	int nRes = (*m_PStartup)(&context, m_hPDll);
 	if (nRes < 0) return false;
 	else return true;
 }
@@ -199,7 +206,7 @@
 bool CDSMPlugin::ResetPlugin(void)
 {
 	// TODO: Log events
-	int nRes = (*m_PReset)();
+	int nRes = (*m_PReset)(&context);
 	if (nRes < 0) return false;
 	else return true;
 }
@@ -211,7 +218,7 @@
 bool CDSMPlugin::SetPluginParams(HWND hWnd, char* szParams)
 {
 	// TODO: Log events
-	int nRes = (*m_PSetParams)(hWnd, szParams);
+	int nRes = (*m_PSetParams)(&context, hWnd, szParams);
 	if (nRes > 0) return true; else return false;
 
 }
@@ -223,7 +230,7 @@
 char* CDSMPlugin::GetPluginParams(void)
 {
 	// 
-	return (*m_PGetParams)();
+	return (*m_PGetParams)(&context);
 
 }
 
@@ -280,34 +287,8 @@
 //
 bool CDSMPlugin::LoadPlugin(char* szPlugin, bool fAllowMulti)
 {
-	// sf@2003 - Multi dll trick 
-	// I really don't like doing this kind of dirty workaround but I have no time to do
-	// better for now. Used only by a listening viewer.
-	// Create a numbered temporary copy of the original plugin dll and load it (viewer only, for now)
-	if (fAllowMulti)
-	{
-		bool fDllCopyCreated = false;
-		int i = 1;
-		char szDllCopyName[196];
-		while (!fDllCopyCreated)
-		{
-			strcpy(szDllCopyName, szPlugin);
-			szDllCopyName[strlen(szPlugin) - 4] = '\0'; //remove the ".dsm" extension
-			sprintf(szDllCopyName, "%s-tmp.d%d", szDllCopyName, i++);
-			fDllCopyCreated = (bool) CopyFile(szPlugin, szDllCopyName, false); 
-			// Note: Let's be really dirty; Overwrite if it's possible only (dll not loaded). 
-			// This way if for some reason (abnormal process termination) the dll wasn't previously 
-			// normally deleted we overwrite/clean it with the new one at the same time.
-			if (i > 99) break; // Just in case...
-		}
-		strcpy(m_szDllName, szDllCopyName);
-		m_hPDll = LoadLibrary(m_szDllName);
-	}
-	else // Use the original plugin dll
-	{
-		ZeroMemory(m_szDllName, strlen(m_szDllName));
-		m_hPDll = LoadLibrary(szPlugin);
-	}
+	ZeroMemory(m_szDllName, strlen(m_szDllName));
+	m_hPDll = LoadLibrary(szPlugin);
 
 	if (m_hPDll == NULL) return false;
 
@@ -342,15 +323,15 @@
 {
 	// TODO: Log events
 	// Force the DSMplugin to free the buffers it allocated
-	if (m_pTransBuffer != NULL) (*m_PFreeBuffer)(m_pTransBuffer);
-	if (m_pRestBuffer != NULL) (*m_PFreeBuffer)(m_pRestBuffer);
+	if (m_pTransBuffer != NULL) (*m_PFreeBuffer)(&context, m_pTransBuffer);
+	if (m_pRestBuffer != NULL) (*m_PFreeBuffer)(&context, m_pRestBuffer);
 	
 	m_pTransBuffer = NULL;
 	m_pRestBuffer = NULL;
 
 	SetLoaded(false);
 
-	if ((*m_PShutdown)())
+	if ((*m_PShutdown)(&context))
 	{
 		bool fFreed = false;
 		fFreed = FreeLibrary(m_hPDll); 
@@ -373,7 +354,7 @@
 	// FixME: possible pb with this mutex in WinVNC
 	omni_mutex_lock l(m_TransMutex);
 
-	m_pTransBuffer = (*m_PTransformBuffer)(pDataBuffer, nDataLen, pnTransformedDataLen);
+	m_pTransBuffer = (*m_PTransformBuffer)(&context, pDataBuffer, nDataLen, pnTransformedDataLen);
 
 	return m_pTransBuffer;
 }
@@ -385,13 +366,13 @@
 BYTE* CDSMPlugin::RestoreBufferStep1(BYTE* pRestoredDataBuffer, int nDataLen, int* pnRestoredDataLen)
 {
 	//m_RestMutex.lock();
-	m_pRestBuffer = (*m_PRestoreBuffer)(pRestoredDataBuffer, nDataLen, pnRestoredDataLen);
+	m_pRestBuffer = (*m_PRestoreBuffer)(&context, pRestoredDataBuffer, nDataLen, pnRestoredDataLen);
 	return m_pRestBuffer;
 }
 
 BYTE* CDSMPlugin::RestoreBufferStep2(BYTE* pRestoredDataBuffer, int nDataLen, int* pnRestoredDataLen)
 {
-	m_pRestBuffer = (*m_PRestoreBuffer)(pRestoredDataBuffer, nDataLen, pnRestoredDataLen);
+	m_pRestBuffer = (*m_PRestoreBuffer)(&context, pRestoredDataBuffer, nDataLen, pnRestoredDataLen);
 	//m_RestMutex.unlock();
 	return NULL;
 }
diff -ru3 UltraVnc-101-src/src/ultravnc/DSMPlugin/DSMPlugin.h UltraVnc-101-src.new/src/ultravnc/DSMPlugin/DSMPlugin.h
--- UltraVnc-101-src/src/ultravnc/DSMPlugin/DSMPlugin.h	2005-02-17 22:48:18.000000000 -0600
+++ UltraVnc-101-src.new/src/ultravnc/DSMPlugin/DSMPlugin.h	2005-10-01 07:14:55.015625000 -0500
@@ -43,14 +43,14 @@
 
 // A plugin dll must export the following functions (with same convention)
 typedef char* (__cdecl  *DESCRIPTION)(void);
-typedef int   (__cdecl  *STARTUP)(void);
-typedef int   (__cdecl  *SHUTDOWN)(void);
-typedef int   (__cdecl  *SETPARAMS)(HWND, char*);
-typedef char* (__cdecl  *GETPARAMS)(void);
-typedef BYTE* (__cdecl  *TRANSFORMBUFFER)(BYTE*, int, int*);
-typedef BYTE* (__cdecl  *RESTOREBUFFER)(BYTE*, int, int*);
-typedef void  (__cdecl  *FREEBUFFER)(BYTE*);
-typedef int   (__cdecl  *RESET)(void);
+typedef int   (__cdecl  *STARTUP)(void**, HINSTANCE);
+typedef int   (__cdecl  *SHUTDOWN)(void**);
+typedef int   (__cdecl  *SETPARAMS)(void**,HWND, char*);
+typedef char* (__cdecl  *GETPARAMS)(void**);
+typedef BYTE* (__cdecl  *TRANSFORMBUFFER)(void**,BYTE*, int, int*);
+typedef BYTE* (__cdecl  *RESTOREBUFFER)(void**,BYTE*, int, int*);
+typedef void  (__cdecl  *FREEBUFFER)(void**,BYTE*);
+typedef int   (__cdecl  *RESET)(void**);
 
 
 //
@@ -88,6 +88,8 @@
 	omni_mutex m_RestMutex;
 
 private:
+	void *context;
+	
 	bool m_fLoaded;
 	bool m_fEnabled;
 
diff -ru3 UltraVnc-101-src/src/ultravnc/DSMPlugin/TestPlugin/TestPlugin.cpp UltraVnc-101-src.new/src/ultravnc/DSMPlugin/TestPlugin/TestPlugin.cpp
--- UltraVnc-101-src/src/ultravnc/DSMPlugin/TestPlugin/TestPlugin.cpp	2005-04-16 14:00:56.000000000 -0500
+++ UltraVnc-101-src.new/src/ultravnc/DSMPlugin/TestPlugin/TestPlugin.cpp	2005-10-01 07:16:26.640625000 -0500
@@ -46,28 +46,25 @@
 // 
 //////////////////////////////////////////////////////////////////////////////
 
+#define TESTPLUGIN_EXPORTS
 #include "TestPlugin.h"
 
-HINSTANCE hInstance;
-PLUGINSTRUCT* pPlugin = NULL;  // struct (or class instance) that handles all Plugin params.
-							   // Given as an example.
- 
-// Internal Plugin vars, depending on what it does
-char  szExternalKey[255];	// To store the password/key transmitted via SetParams() by UltraVNC apps
-char  szLoaderType[32];     // To store the type of application that has loaded the plugin 
-BYTE* pLocalTransBuffer = NULL; // Local Transformation buffer (freed on VNC demand)
-BYTE* pLocalRestBuffer = NULL;  // Local Restoration buffer (freed on VNC demand)
-int   nLocalTransBufferSize = 0;
-int   nLocalRestBufferSize = 0;
-//
-
+typedef struct {
+	HINSTANCE hInstance;
+	char  szExternalKey[255];	// To store the password/key transmitted via SetParams() by UltraVNC apps
+	char  szLoaderType[32];		// To store the type of application that has loaded the plugin 
+	BYTE* pLocalTransBuffer;	// Local Transformation buffer (freed on VNC demand)
+	BYTE* pLocalRestBuffer;		// Local Restoration buffer (freed on VNC demand)
+	int   nLocalTransBufferSize;
+	int   nLocalRestBufferSize;
+} pluginState;
 
 // Plugin Description
 // Please use the following format (with ',' (comma) as separator)
 // Name-Description,Author,Date,Version,FileName-Comment
 // For the version, we recommend the following format: x.y.z
 // The other fields (Name-Description, Author, Date, FileName-Comment) are format free (don't use ',' in them, of course)
-#define PLUGIN_DESCRIPTION  "TestPlugin,Sam,Nov 21 2002,1.0.0,TestPlugin.dsm"
+#define PLUGIN_DESCRIPTION  "TestPlugin,Duff,Oct 01 2005,2.0.0,TestPlugin.dsm"
 
 
 
@@ -95,10 +92,16 @@
 // Initialize the plugin and all its internals
 // Return -1 if error
 //
-TESTPLUGIN_API int Startup(void)
+TESTPLUGIN_API int Startup(void **context, HINSTANCE hInstance)
 {
+	*context = (void*)(new pluginState);
+	((pluginState*)(*context))->pLocalTransBuffer		= NULL;
+	((pluginState*)(*context))->nLocalTransBufferSize	= 0;
+	((pluginState*)(*context))->pLocalRestBuffer		= NULL;
+	((pluginState*)(*context))->nLocalRestBufferSize	= 0;
+	((pluginState*)(*context))->hInstance			= hInstance;
 	// Init everything
-	memset(szExternalKey, 0, sizeof(szExternalKey));
+	memset(((pluginState*)(*context))->szExternalKey, 0, sizeof(((pluginState*)(*context))->szExternalKey));
 	// Create threads if any
 	return 1;
 }
@@ -108,10 +111,12 @@
 // Stop and Clean up the plugin 
 // Return -1 if error
 // 
-TESTPLUGIN_API int Shutdown(void)
+TESTPLUGIN_API int Shutdown(void **context)
 {
 	// Terminate Threads if any
 	// Cleanup everything
+	delete ((pluginState*)(*context));
+	*context = NULL;
 	return 1;
 }
 
@@ -120,11 +125,11 @@
 // Stop and Clean up the plugin 
 // Return -1 if error
 // 
-TESTPLUGIN_API int Reset(void)
+TESTPLUGIN_API int Reset(void **context)
 {
 	// Reset the plugin (buffers, keys, whatever that 
 	// requires to be reset between 2 connections
-
+	memset(((pluginState*)(*context))->szExternalKey, 0, sizeof(((pluginState*)(*context))->szExternalKey));
 	return 1;
 }
 
@@ -163,25 +168,25 @@
 //   (this info can be used for application/environnement dependent
 //    operations (config saving...))
 //   
-TESTPLUGIN_API int SetParams(HWND hVNC, char* szParams)
+TESTPLUGIN_API int SetParams(void **context, HWND hVNC, char* szParams)
 {
 	// CASE 1
 	// Get the environnement (szLoaderType) value that is always sent from 
 	// VNC viewer or server
-	MyStrToken(szLoaderType, szParams, 2, ',');
+	MyStrToken(((pluginState*)(*context))->szLoaderType, szParams, 2, ',');
 
 	// If hVNC != 0, display for instance the Plugin Config Dialog box 
 	if (hVNC)
 	{
 		// Display the Plugin Config dialog box
-		DoDialog();
+		DoDialog(context);
 	}
 
 	// CASE 2: 
 	// Use szParams to setup the Plugin.
 	// In this example Plugin, the externalkey is not used but we store it anyway.for demo.
 	// (it corresponds to the VNC password as we require it in the GetParams() function below)
-	MyStrToken(szExternalKey, szParams, 1, ',');
+	MyStrToken(((pluginState*)(*context))->szExternalKey, szParams, 1, ',');
 
 	return 1;
 }
@@ -196,13 +201,13 @@
 // Thus this function is called once before the SetParams() function is called
 //  - Return "VNCPasswordNeeded" if VNC password must be transmitted by the UltraVNC app
 //  - Return any other Plugin parameters value otherwise (not used in WinVNC & vncviewer for now)
-TESTPLUGIN_API char* GetParams(void)
+TESTPLUGIN_API char* GetParams(void **context)
 {
-	if (strlen(szExternalKey) > 0)
-		return szExternalKey; // Return the already stored externalkey params
+	if (strlen(((pluginState*)(*context))->szExternalKey) > 0)
+		return "IveGotAllINeedThanks";
+		// return strlen(((pluginState*)(*context))->szExternalKey); // Return the already stored externalkey params // err... returning an int for a char*?
 	else
 		return "VNCPasswordNeeded";
-	    // return "IveGotAllINeedThanks";
 }
 
 // 
@@ -212,9 +217,9 @@
 // buffer containing the resulting data.
 // The length of the resulting data is given by pnTransformedDataLen
 //
-TESTPLUGIN_API BYTE* TransformBuffer(BYTE* pDataBuffer, int nDataLen, int* pnTransformedDataLen)
+TESTPLUGIN_API BYTE* TransformBuffer(void **context, BYTE* pDataBuffer, int nDataLen, int* pnTransformedDataLen)
 {
-	BYTE* pTransBuffer = CheckLocalTransBufferSize(GiveTransDataLen(nDataLen));
+	BYTE* pTransBuffer = CheckLocalTransBufferSize(context, GiveTransDataLen(nDataLen));
 	if (pTransBuffer == NULL)
 	{
 		*pnTransformedDataLen = -1;
@@ -259,7 +264,7 @@
 // - Calls RestoreBuffer again to actually restore data into the given destination buffer.
 // This way the copies of data buffers are reduced to the minimum.
 // 
-TESTPLUGIN_API BYTE* RestoreBuffer(BYTE* pRestoredDataBuffer, int nDataLen, int* pnRestoredDataLen)
+TESTPLUGIN_API BYTE* RestoreBuffer(void **context, BYTE* pRestoredDataBuffer, int nDataLen, int* pnRestoredDataLen)
 {
 	// If given buffer is NULL, allocate necessary space here and return the pointer.
 	// Additionaly, calculate the resulting length based on nDataLen and return it at the same time.
@@ -268,7 +273,7 @@
 		// Give the size of the transformed data buffer, based on the original data length
 		*pnRestoredDataLen = GiveTransDataLen(nDataLen);
 		// Ensure the pLocalRestBuffer that receive transformed data is big enought
-		BYTE* pBuffer = CheckLocalRestBufferSize(*pnRestoredDataLen);
+		BYTE* pBuffer = CheckLocalRestBufferSize(context, *pnRestoredDataLen);
 		return pBuffer; // Actually pBuffer = pLocalRestBuffer
 	}
 
@@ -282,13 +287,13 @@
 	int i;
 	for (i = 0; i < nDataLen; i++)
 	{
-		pRestoredDataBuffer[i] = pLocalRestBuffer[i];
+		pRestoredDataBuffer[i] = ((pluginState*)(*context))->pLocalRestBuffer[i];
 	}
 
 	// return the resulting data length
 	*pnRestoredDataLen = GiveRestDataLen(nDataLen);
 
-	return pLocalRestBuffer;
+	return ((pluginState*)(*context))->pLocalRestBuffer;
 }
 
 
@@ -297,7 +302,7 @@
 // in TransformBuffer and RestoreBuffer, using the method adapted
 // to the used allocation method.
 //
-TESTPLUGIN_API void FreeBuffer(BYTE* pBuffer)
+TESTPLUGIN_API void FreeBuffer(void **context, BYTE* pBuffer)
 {
 	if (pBuffer != NULL) 
 		free(pBuffer);
@@ -350,10 +355,10 @@
 //
 // Display the Plugin Config Dialog box
 //
-int DoDialog(void)
+int DoDialog(void** context)
 {
- 	return DialogBoxParam(hInstance, MAKEINTRESOURCE(IDD_CONFIG_DIALOG), 
-		NULL, (DLGPROC) ConfigDlgProc, (LONG) pPlugin);
+ 	return DialogBoxParam(((pluginState*)(*context))->hInstance, MAKEINTRESOURCE(IDD_CONFIG_DIALOG), 
+		NULL, (DLGPROC) ConfigDlgProc, (LONG) (*context));
 }
 
 
@@ -362,7 +367,7 @@
 //
 BOOL CALLBACK ConfigDlgProc(HWND hwnd,  UINT uMsg,  WPARAM wParam, LPARAM lParam )
 {
-	PLUGINSTRUCT* _this = (PLUGINSTRUCT*) GetWindowLong(hwnd, GWL_USERDATA);
+	pluginState *_this = (pluginState*) GetWindowLong(hwnd, GWL_USERDATA);
 
 	switch (uMsg)
 	{
@@ -460,24 +465,24 @@
 // Allocate more space for the local transformation buffer if necessary
 // and returns the pointer to this buffer
 //
-BYTE* CheckLocalTransBufferSize(int nBufferSize)
+BYTE* CheckLocalTransBufferSize(void** context, int nBufferSize)
 {
-	if (nLocalTransBufferSize >= nBufferSize) return pLocalTransBuffer;
+	if (((pluginState*)(*context))->nLocalTransBufferSize >= nBufferSize) return ((pluginState*)(*context))->pLocalTransBuffer;
 
 	BYTE *pNewBuffer = (BYTE *) malloc (nBufferSize + 256);
 	if (pNewBuffer == NULL) 
 	{
 		return NULL;
 	}
-	if (pLocalTransBuffer != NULL)
-		free(pLocalTransBuffer);
+	if (((pluginState*)(*context))->pLocalTransBuffer != NULL)
+		free(((pluginState*)(*context))->pLocalTransBuffer);
 
-	pLocalTransBuffer = pNewBuffer;
-	nLocalTransBufferSize = nBufferSize + 256;
+	((pluginState*)(*context))->pLocalTransBuffer = pNewBuffer;
+	((pluginState*)(*context))->nLocalTransBufferSize = nBufferSize + 256;
 
-	memset(pLocalTransBuffer, 0, nLocalTransBufferSize);
+	memset(((pluginState*)(*context))->pLocalTransBuffer, 0, ((pluginState*)(*context))->nLocalTransBufferSize);
 
-	return pLocalTransBuffer;
+	return ((pluginState*)(*context))->pLocalTransBuffer;
 }
 
 
@@ -485,24 +490,24 @@
 // Allocate more space for the local restoration buffer if necessary
 // and returns the pointer to this buffer
 //
-BYTE* CheckLocalRestBufferSize(int nBufferSize)
+BYTE* CheckLocalRestBufferSize(void **context, int nBufferSize)
 {
-	if (nLocalRestBufferSize >= nBufferSize) return pLocalRestBuffer;
+	if (((pluginState*)(*context))->nLocalRestBufferSize >= nBufferSize) return ((pluginState*)(*context))->pLocalRestBuffer;
 
 	BYTE *pNewBuffer = (BYTE *) malloc (nBufferSize + 256);
 	if (pNewBuffer == NULL) 
 	{
 		return NULL;
 	}
-	if (pLocalRestBuffer != NULL)
-		free(pLocalRestBuffer);
+	if (((pluginState*)(*context))->pLocalRestBuffer != NULL)
+		free(((pluginState*)(*context))->pLocalRestBuffer);
 
-	pLocalRestBuffer = pNewBuffer;
-	nLocalRestBufferSize = nBufferSize + 256;
+	((pluginState*)(*context))->pLocalRestBuffer = pNewBuffer;
+	((pluginState*)(*context))->nLocalRestBufferSize = nBufferSize + 256;
 
-	memset(pLocalRestBuffer, 0, nLocalRestBufferSize);
+	memset(((pluginState*)(*context))->pLocalRestBuffer, 0, ((pluginState*)(*context))->nLocalRestBufferSize);
 
-	return pLocalRestBuffer;
+	return ((pluginState*)(*context))->pLocalRestBuffer;
 }
 
 
@@ -515,15 +520,6 @@
                        LPVOID lpReserved
 					 )
 {
-    switch (dwReason)
-	{
-		case DLL_PROCESS_ATTACH:
-			hInstance = hInst;
-		case DLL_THREAD_ATTACH:
-		case DLL_THREAD_DETACH:
-		case DLL_PROCESS_DETACH:
-			break;
-    }
     return TRUE;
 }
 
diff -ru3 UltraVnc-101-src/src/ultravnc/DSMPlugin/TestPlugin/TestPlugin.h UltraVnc-101-src.new/src/ultravnc/DSMPlugin/TestPlugin/TestPlugin.h
--- UltraVnc-101-src/src/ultravnc/DSMPlugin/TestPlugin/TestPlugin.h	2005-04-15 22:27:16.000000000 -0500
+++ UltraVnc-101-src.new/src/ultravnc/DSMPlugin/TestPlugin/TestPlugin.h	2005-10-01 07:14:29.000000000 -0500
@@ -58,6 +58,7 @@
 #include "resource.h"
 
 // Plugin struct example - Of course some classes can be used instead...
+#if 0
 typedef struct
 {
 	char szDescription[256];
@@ -66,6 +67,7 @@
 	int nInternalParam2;  // And so on.. add what you need.
 
 } PLUGINSTRUCT;
+#endif
 
 
 //
@@ -74,11 +76,11 @@
 BOOL MyStrToken(LPSTR szToken, LPSTR lpString, int nTokenNum, char cSep);
 int GiveTransDataLen(int nDataLen);
 int GiveRestDataLen(int nDataLen);
-BYTE* CheckLocalTransBufferSize(int nBufferSize);
-BYTE* CheckLocalRestBufferSize(int nBufferSize);
+BYTE* CheckLocalTransBufferSize(void **context, int nBufferSize);
+BYTE* CheckLocalRestBufferSize(void **context, int nBufferSize);
 // Config procs if necessary (the plugin is allowed to have no config dialog at all)
 BOOL CALLBACK ConfigDlgProc(HWND hwnd,  UINT uMsg,  WPARAM wParam, LPARAM lParam );
-int DoDialog(void);
+int DoDialog(void **context);
 
 
 //
@@ -88,12 +90,12 @@
 extern "C"
 {
 TESTPLUGIN_API char* Description(void);
-TESTPLUGIN_API int Startup(void);
-TESTPLUGIN_API int Shutdown(void);
-TESTPLUGIN_API int Reset(void);
-TESTPLUGIN_API int SetParams(HWND hVNC, char* szParams);
-TESTPLUGIN_API char* GetParams(void);
-TESTPLUGIN_API BYTE* TransformBuffer(BYTE* pDataBuffer, int nDataLen, int* pnTransformedDataLen);
-TESTPLUGIN_API BYTE* RestoreBuffer(BYTE* pTransBuffer, int nTransDataLen, int* pnRestoredDataLen);
-TESTPLUGIN_API void FreeBuffer(BYTE* pBuffer);
+TESTPLUGIN_API int Startup(void** context, HINSTANCE *hInstance);
+TESTPLUGIN_API int Shutdown(void** context);
+TESTPLUGIN_API int Reset(void** context);
+TESTPLUGIN_API int SetParams(void** context, HWND hVNC, char* szParams);
+TESTPLUGIN_API char* GetParams(void** context);
+TESTPLUGIN_API BYTE* TransformBuffer(void** context, BYTE* pDataBuffer, int nDataLen, int* pnTransformedDataLen);
+TESTPLUGIN_API BYTE* RestoreBuffer(void** context, BYTE* pTransBuffer, int nTransDataLen, int* pnRestoredDataLen);
+TESTPLUGIN_API void FreeBuffer(void** context, BYTE* pBuffer);
 }