1 #include "stdafx.h"
2 #include "VBA.h"
3 #include "rpi.h"
4 
5 extern void SuperEagle(u8*,u32,u8*,u8*,u32,int,int);
6 
7 static HINSTANCE rpiDLL = NULL;
8 static RENDPLUG_Output fnOutput = NULL;
9 static RENDPLUG_GetInfo fnGetInfo = NULL;
10 static RENDER_PLUGIN_INFO MyPlugInfo;
11 static RENDER_PLUGIN_OUTP MyPlugOutput;
12 static int nScaleFactor;
13 
14 extern int systemRedShift, systemGreenShift, systemBlueShift;
15 extern int realsystemRedShift, realsystemGreenShift, realsystemBlueShift;
16 extern int realsystemColorDepth;
17 u8 *pBuffer16 = NULL;
18 u32 Buffer16Size = 0;
19 
rpiInit(const char * sPluginName)20 bool rpiInit(const char *sPluginName)
21 {
22 	rpiCleanup();
23 
24 	char sBuffer[256];
25 	char *ptr;
26 
27 	GetModuleFileName(NULL, sBuffer, sizeof(sBuffer));
28 	ptr = strrchr(sBuffer, '\\');
29 	if (ptr)
30 		*ptr = '\0';
31 	strcat(sBuffer, "\\plugins\\");
32 	strcat(sBuffer, sPluginName);
33 
34   	rpiDLL = LoadLibrary(sBuffer);
35   	if (!rpiDLL)
36   		return false;
37 
38 	fnGetInfo = (RENDPLUG_GetInfo) GetProcAddress(rpiDLL, "RenderPluginGetInfo");
39 	fnOutput = (RENDPLUG_Output) GetProcAddress(rpiDLL, "RenderPluginOutput");
40 	if (fnGetInfo == NULL || fnOutput == NULL)
41 	{
42 		FreeLibrary(rpiDLL);
43 		rpiDLL = NULL;
44 		return false;
45 	}
46 
47 	RENDER_PLUGIN_INFO *pRPI = fnGetInfo();
48 	if (pRPI == NULL)
49 	{
50 		FreeLibrary(rpiDLL);
51 		rpiDLL = NULL;
52 		return false;
53 	}
54 
55 	memcpy(&MyPlugInfo, pRPI, sizeof(MyPlugInfo));
56 
57 	unsigned long Flags = MyPlugInfo.Flags & 0x0000F0000;
58 
59 	if (Flags == RPI_OUT_SCL2)
60 	{
61 		nScaleFactor = 2;
62 	}
63 	else if (Flags == RPI_OUT_SCL3)
64 	{
65 		nScaleFactor = 3;
66 	}
67 	else if (Flags == RPI_OUT_SCL4)
68 	{
69 		nScaleFactor = 4;
70 	}
71 	else
72 	{
73 		nScaleFactor = 2;
74 	}
75 
76 	return true;
77 }
78 
rpiFilter(u8 * srcPtr,u32 srcPitch,u8 * deltaPtr,u8 * dstPtr,u32 dstPitch,int width,int height)79 void rpiFilter(u8 *srcPtr, u32 srcPitch, u8 *deltaPtr, u8 *dstPtr, u32 dstPitch, int width, int height)
80 {
81 	u8 *pBuff;
82 
83 	if (realsystemColorDepth == 32)
84 	{
85 		// Kega filters are 16 bit only.  Assumes we've forced 16 bit input
86 		ASSERT(systemColorDepth == 16);
87 		u32 bufferNeeded = dstPitch * (height + nScaleFactor) * nScaleFactor;
88 		if (Buffer16Size < bufferNeeded)
89 		{
90 			Buffer16Size = bufferNeeded;
91 			if (pBuffer16)
92 				free(pBuffer16);
93 			pBuffer16 =  (u8 *)malloc(Buffer16Size);
94 		}
95 		pBuff = pBuffer16;
96 	}
97 	else
98 		pBuff = dstPtr;
99 
100 	MyPlugOutput.Size = sizeof(MyPlugOutput);
101 	MyPlugOutput.Flags = MyPlugInfo.Flags;
102 	MyPlugOutput.SrcPtr = srcPtr;
103 	MyPlugOutput.SrcPitch = srcPitch;
104 	MyPlugOutput.SrcW = width;
105 	// Without this funky math on the height value, the RPI filter isn't fully
106 	// rendering the frame.  I don't like passing in values that seem
107 	// to be greater than the buffer size, but it's the only way to get
108 	// proper results.
109 	MyPlugOutput.SrcH = height+(nScaleFactor/2);
110 	MyPlugOutput.DstPtr = pBuff;
111 	MyPlugOutput.DstPitch = dstPitch;
112 	MyPlugOutput.DstW = width * nScaleFactor;
113 	MyPlugOutput.DstH = (height+(nScaleFactor/2)) * nScaleFactor;
114 	MyPlugOutput.OutW = width * nScaleFactor;
115 	MyPlugOutput.OutH = (height+(nScaleFactor/2)) * nScaleFactor;
116 
117 	fnOutput(&MyPlugOutput);
118 
119 	if (realsystemColorDepth == 32)
120 	{
121 		register int i,j;
122 		int rshiftDiff = realsystemRedShift - systemRedShift;
123 		int gshiftDiff = realsystemGreenShift - systemGreenShift;
124 		int bshiftDiff = realsystemBlueShift - systemBlueShift;
125 
126 		u16 *pI, *pICur;
127 		u32 *pO, *pOCur;
128 
129 		pI = pICur = (u16 *)pBuff;
130 		pO = pOCur = (u32 *)dstPtr;
131 
132 		if (rshiftDiff >= 0)
133 		{
134 			for(j=0;j<height*nScaleFactor;j++)
135 			{
136 				for(i=0;i<width*nScaleFactor;i++)
137 				{
138 					*(pOCur++) = ((*pICur & 0xF800) << rshiftDiff) |
139 						      ((*pICur & 0x07E0) << gshiftDiff) |
140 						      ((*pICur & 0x001F) << bshiftDiff);
141 					*(pICur++);
142 				}
143 				pI = pICur = (u16 *)((char *)pI + dstPitch);
144 				pO = pOCur = (u32 *)((char *)pO + dstPitch);
145 			}
146 		}
147 		else
148 		{
149 			// red shift is negative.  That means we're most likely swapping RGB to BGR
150 			// shift operators don't support negative values.
151 
152 			rshiftDiff = -rshiftDiff;
153 			for(j=0;j<height*nScaleFactor;j++)
154 			{
155 				for(i=0;i<width*nScaleFactor;i++)
156 				{
157 					*(pOCur++) = ((*pICur & 0xF800) >> rshiftDiff) |
158 						      ((*pICur & 0x07E0) << gshiftDiff) |
159 						      ((*pICur & 0x001F) << bshiftDiff);
160 					*(pICur++);
161 				}
162 				pI = pICur = (u16 *)((char *)pI + dstPitch);
163 				pO = pOCur = (u32 *)((char *)pO + dstPitch);
164 			}
165 
166 		}
167 	}
168 }
169 
rpiScaleFactor()170 int rpiScaleFactor()
171 {
172 	return nScaleFactor;
173 }
174 
rpiCleanup()175 void rpiCleanup()
176 {
177 	if (rpiDLL != NULL)
178 	{
179 		FreeLibrary(rpiDLL);
180 		rpiDLL = NULL;
181 	}
182 	if (pBuffer16)
183 	{
184 		free(pBuffer16);
185 		pBuffer16 = NULL;
186 		Buffer16Size = 0;
187 	}
188 }
189