// RivaTuner.cpp : Defines the initialization routines for the DLL.
//
// created by Unwinder
/////////////////////////////////////////////////////////////////////////////
#include "stdafx.h"

#include <time.h>
#include <stdio.h>
#include <float.h>
#include <windows.h>

#include "RivaTuner.h"
#include "RTHMSharedMemory.h"
/////////////////////////////////////////////////////////////////////////////
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
typedef struct DATA { char data[65536]; } DATA, *LPDATA;
/////////////////////////////////////////////////////////////////////////////
void _stdcall Init()
{ 
}
/////////////////////////////////////////////////////////////////////////////
void _stdcall CleanUp()
{
}
/////////////////////////////////////////////////////////////////////////////
DATA _stdcall GetID()
{
	DATA result;
	memset(&result, 0, sizeof(result));

	strcpy(result.data, "RivaTuner plugin v1.0");
	return result;
}
/////////////////////////////////////////////////////////////////////////////
DATA _stdcall GetData(LPCSTR lpParam)
{
	DATA result;
	memset(&result, 0, sizeof(result));

	DWORD x0 = 5;
	DWORD x1 = 160;
	DWORD x2 = 210;
	DWORD y0 = 5;
	DWORD dy = 10;

	if (*lpParam == '@')
	{
		char c;
		sscanf(lpParam, "%c,%d,%d,%d,%d,%d", &c, &x0, &x1, &x2, &y0, &dy);
	}

	HANDLE hMapFile = OpenFileMapping(FILE_MAP_ALL_ACCESS, FALSE, "RTHMSharedMemory");

	if (hMapFile)
	{
		LPVOID pMapAddr = MapViewOfFile(hMapFile, FILE_MAP_ALL_ACCESS, 0, 0, 0);

		if (pMapAddr)
		{
			LPRTHM_SHARED_MEMORY_HEADER_V_1_0	lpHeaderV10	= (LPRTHM_SHARED_MEMORY_HEADER_V_1_0)pMapAddr;

			if (lpHeaderV10->dwSignature == 'RTHM')
				//check if we're connected to valid memory
			{
				DWORD dwSources = lpHeaderV10->dwNumEntries;
					//get number of data sources

				for (DWORD dwSource=0; dwSource<dwSources; dwSource++)
					//process each data source
				{
					if (lpHeaderV10->dwVersion == 0x10000)
						//we must use special handling code for shared memory v1.0, because entry size field (which is 
						//reuiqred for unified access to entries) was added to header in v1.1 only
					{
						LPRTHM_SHARED_MEMORY_ENTRY_V_1_0 lpEntry = (LPRTHM_SHARED_MEMORY_ENTRY_V_1_0)((LPBYTE)(lpHeaderV10 + 1) + dwSource * sizeof(RTHM_SHARED_MEMORY_ENTRY_V_1_0));
							//get ptr to  the current data source's entry

						if (*lpParam == '@')
						{
							char szBuf[MAX_PATH];

							sprintf(szBuf, "%%Common.CreateNewLine(,%d,%d) '%s'", x0, y0, lpEntry->czSrc);
							strcat(result.data, szBuf);

							char szVal[MAX_PATH];
							if (lpEntry->data == FLT_MAX)
								strcpy(szVal, "N/A");
							else
								sprintf(szVal, "%.2f", lpEntry->data);

							sprintf(szBuf, "%%Common.CreateNewLine(,%d,%d) ': %s'", x1, y0, szVal);
							strcat(result.data, szBuf);

							if (lpEntry->data != FLT_MAX)
							{
								sprintf(szBuf, "%%Common.CreateNewLine(,%d,%d) '%s'", x2, y0, lpEntry->czDim);
								strcat(result.data, szBuf);
							}

							y0 += dy;
						}
						else
							if (!stricmp(lpParam, lpEntry->czSrc) && lpEntry->data != FLT_MAX)
								sprintf(result.data, "%.2f", lpEntry->data);
					}
					else
					{
						LPRTHM_SHARED_MEMORY_HEADER	lpHeader	= (LPRTHM_SHARED_MEMORY_HEADER)pMapAddr;
						LPRTHM_SHARED_MEMORY_ENTRY	lpEntry		= (LPRTHM_SHARED_MEMORY_ENTRY)((LPBYTE)(lpHeader + 1) + dwSource * lpHeader->dwEntrySize);

						if (*lpParam == '@')
						{
							char szBuf[MAX_PATH];

							char szSrc[MAX_PATH];
							if (lpEntry->offset == 0.0f)
								strcpy(szSrc, lpEntry->czSrc);
							else
								sprintf(szSrc, "%s (%+.1f)", lpEntry->czSrc, lpEntry->offset);
							sprintf(szBuf, "%%Common.CreateNewLine(,%d,%d) '%s'", x0, y0, szSrc);
							strcat(result.data, szBuf);

							char szVal[MAX_PATH];
							if (lpEntry->data == FLT_MAX)
								strcpy(szVal, "N/A");
							else
								sprintf(szVal, "%.2f", lpEntry->dataTransformed + lpEntry->offset);

							sprintf(szBuf, "%%Common.CreateNewLine(,%d,%d) ': %s'", x1, y0, szVal);
							strcat(result.data, szBuf);

							if (lpEntry->data != FLT_MAX)
							{
								sprintf(szBuf, "%%Common.CreateNewLine(,%d,%d) '%s'", x2, y0, lpEntry->czDim);
								strcat(result.data, szBuf);
							}

							y0 += dy;
						}
						else
							if (!stricmp(lpParam, lpEntry->czSrc) && lpEntry->data != FLT_MAX)
								sprintf(result.data, "%.2f", lpEntry->dataTransformed + lpEntry->offset);
					}
				}
			}


			UnmapViewOfFile(pMapAddr);
		}

		CloseHandle(hMapFile);
	}

	return result;
}
/////////////////////////////////////////////////////////////////////////////