1 /*---------------------------------------------------------------------------*
2
3 Copyright (C) Nintendo. All rights reserved.
4
5 These coded instructions, statements, and computer programs contain
6 proprietary information of Nintendo of America Inc. and/or Nintendo
7 Company Ltd., and are protected by Federal copyright law. They may
8 not be disclosed to third parties or copied or duplicated in any form,
9 in whole or in part, without the prior written consent of Nintendo.
10
11 *---------------------------------------------------------------------------*/
12 // ------------------------------------------------------------------
13 // DDS_Helpers.cpp
14 // ------------------------------------------------------------------
15 #include "stdafx.h"
16 #include <stdio.h>
17 #include <stdlib.h>
18 #include <assert.h>
19 #include <limits.h>
20 #include "ddraw.h"
21 #include "d3d9types.h"
22 #include "DDS.h"
23 #include "DDS_Helpers.h"
24 #include "resource.h"
25
26 namespace DDSReader
27 {
IsD3D10Format(const GX2Surface * pSurface)28 bool IsD3D10Format(const GX2Surface* pSurface)
29 {
30 assert(pSurface);
31
32 if(!pSurface)
33 return false;
34
35 switch (pSurface->format)
36 {
37 case GX2_SURFACE_FORMAT_T_BC1_UNORM:
38 case GX2_SURFACE_FORMAT_T_BC2_UNORM:
39 case GX2_SURFACE_FORMAT_T_BC3_UNORM:
40 case GX2_SURFACE_FORMAT_T_BC4_UNORM:
41 case GX2_SURFACE_FORMAT_T_BC4_SNORM:
42 case GX2_SURFACE_FORMAT_T_BC5_UNORM:
43 case GX2_SURFACE_FORMAT_T_BC5_SNORM:
44 return true;
45 }
46
47 return false;
48 }
49
GetGX2TextureInfo(const DDSD2 * pDDSD,GX2Surface * pSurface,ChannelFormat channelFormat,TextureDataType textureDataType,MS_CubeFace * pCubeFaceMask)50 bool GetGX2TextureInfo(const DDSD2* pDDSD, GX2Surface* pSurface, ChannelFormat channelFormat,
51 TextureDataType textureDataType,MS_CubeFace* pCubeFaceMask)
52 {
53 u32 cubeFaceMask = 0;
54 HMODULE hTexUtilDLL = LoadLibrary(LIB_DLL_TEXUTILS);
55 if ( !hTexUtilDLL )
56 {
57 printf("Failed to load DLL %s. Exiting.", LIB_DLL_TEXUTILS);
58 FreeLibrary(hTexUtilDLL);
59 exit(1);
60 }
61 PTC2GetSourceSurfaceSize fpTC2GetSourceSurfaceSize = reinterpret_cast<PTC2GetSourceSurfaceSize>(GetProcAddress(hTexUtilDLL, "TC2GetSourceSurfaceSize"));
62
63 if(pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_CUBEMAP)
64 {
65 pSurface->depth = 0;
66 pSurface->dim = GX2_SURFACE_DIM_CUBE;
67 cubeFaceMask = MS_CF_None;
68
69 if(pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_CUBEMAP_POSITIVEX)
70 {
71 pSurface->depth++;
72 cubeFaceMask |= MS_CF_PositiveX;
73 }
74 if(pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_CUBEMAP_POSITIVEY)
75 {
76 pSurface->depth++;
77 cubeFaceMask |= MS_CF_PositiveY;
78 }
79 if(pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_CUBEMAP_POSITIVEZ)
80 {
81 pSurface->depth++;
82 cubeFaceMask |= MS_CF_PositiveZ;
83 }
84 if(pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_CUBEMAP_NEGATIVEX)
85 {
86 pSurface->depth++;
87 cubeFaceMask |= MS_CF_NegativeX;
88 }
89 if(pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_CUBEMAP_NEGATIVEY)
90 {
91 pSurface->depth++;
92 cubeFaceMask |= MS_CF_NegativeY;
93 }
94 if(pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_CUBEMAP_NEGATIVEZ)
95 {
96 pSurface->depth++;
97 cubeFaceMask |= MS_CF_NegativeZ;
98 }
99 }
100 else if(pDDSD->ddsCaps.dwCaps2 & DDSCAPS2_VOLUME && pDDSD->dwFlags & DDSD_DEPTH)
101 {
102 pSurface->depth = pDDSD->dwDepth;
103 pSurface->dim = GX2_SURFACE_DIM_3D;
104 }
105 else if(pDDSD->dwFlags & DDSD_DEPTH)
106 {
107 pSurface->depth = pDDSD->dwDepth;
108 pSurface->dim = GX2_SURFACE_DIM_2D_ARRAY;
109 }
110 else
111 {
112 pSurface->depth = 1;
113 pSurface->dim = GX2_SURFACE_DIM_2D;
114 }
115
116 if(pDDSD->dwFlags & DDSD_MIPMAPCOUNT)
117 {
118 pSurface->numMips = pDDSD->dwMipMapCount;
119 }
120 else
121 {
122 pSurface->numMips = pDDSD->dwMipMapCount;
123 }
124
125 if(pSurface->numMips < 1)
126 {
127 pSurface->numMips = 1;
128 }
129
130 pSurface->width = pDDSD->dwWidth;
131 pSurface->height = pDDSD->dwHeight;
132 pSurface->tileMode = GX2_TILE_MODE_LINEAR_SPECIAL;
133 pSurface->use = GX2_SURFACE_USE_TEXTURE;
134 pSurface->alignment = 1;
135
136 switch (channelFormat)
137 {
138 case CF_Compressed:
139 if (pDDSD->ddpfPixelFormat.dwFourCC == MAKEFOURCC('D', 'X', 'T', '1') &&
140 (textureDataType == TDT_XRGB || textureDataType == TDT_ARGB))
141 {
142 pSurface->format = GX2_SURFACE_FORMAT_T_BC1_UNORM;
143 break;
144 }
145 else if (pDDSD->ddpfPixelFormat.dwFourCC == MAKEFOURCC('D', 'X', 'T', '3') &&
146 (textureDataType == TDT_XRGB || textureDataType == TDT_ARGB))
147 {
148 pSurface->format = GX2_SURFACE_FORMAT_T_BC2_UNORM;
149 break;
150 }
151 else if (pDDSD->ddpfPixelFormat.dwFourCC == MAKEFOURCC('D', 'X', 'T', '5') &&
152 (textureDataType == TDT_XRGB || textureDataType == TDT_ARGB))
153 {
154 pSurface->format = GX2_SURFACE_FORMAT_T_BC3_UNORM;
155 break;
156 }
157 else if ( (pDDSD->ddpfPixelFormat.dwFourCC == MAKEFOURCC('A', 'T', 'I', '1') ||
158 pDDSD->ddpfPixelFormat.dwFourCC == MAKEFOURCC('B', 'C', '4', 'U' ) ) &&
159 textureDataType == TDT_R)
160 {
161 pSurface->format = GX2_SURFACE_FORMAT_T_BC4_UNORM;
162 break;
163 }
164 else if ( (pDDSD->ddpfPixelFormat.dwFourCC == MAKEFOURCC('A', 'T', 'I', '2') ||
165 pDDSD->ddpfPixelFormat.dwFourCC == MAKEFOURCC('B', 'C', '5', 'U' ) ) &&
166 textureDataType == TDT_RG)
167 {
168 pSurface->format = GX2_SURFACE_FORMAT_T_BC5_UNORM;
169 break;
170 }
171 else if((pDDSD->ddpfPixelFormat.dwLuminanceBitCount == 8) &&
172 (pDDSD->ddpfPixelFormat.dwFlags & DDPF_LUMINANCE) &&
173 (pDDSD->ddpfPixelFormat.dwFlags & DDPF_ALPHAPIXELS))
174 {
175 pSurface->format = GX2_SURFACE_FORMAT_T_R4_G4_UNORM;
176 break;
177 }
178 else if((pDDSD->ddpfPixelFormat.dwLuminanceBitCount == 16) &&
179 (pDDSD->ddpfPixelFormat.dwFlags & DDPF_LUMINANCE) &&
180 (pDDSD->ddpfPixelFormat.dwFlags & DDPF_ALPHAPIXELS))
181 {
182 pSurface->format = GX2_SURFACE_FORMAT_TC_R8_G8_UNORM;
183 break;
184 }
185 else if((pDDSD->ddpfPixelFormat.dwLuminanceBitCount == 16) &&
186 (pDDSD->ddpfPixelFormat.dwFlags & DDPF_LUMINANCE) &&
187 ((pDDSD->ddpfPixelFormat.dwFlags | DDPF_LUMINANCE) == DDPF_LUMINANCE))
188 {
189 pSurface->format = GX2_SURFACE_FORMAT_TCD_R16_UNORM;
190 break;
191 }
192 else if((pDDSD->ddpfPixelFormat.dwLuminanceBitCount == 8) &&
193 (pDDSD->ddpfPixelFormat.dwFlags & DDPF_LUMINANCE) &&
194 ((pDDSD->ddpfPixelFormat.dwFlags | DDPF_LUMINANCE) == DDPF_LUMINANCE))
195 {
196 pSurface->format = GX2_SURFACE_FORMAT_TC_R8_UNORM;
197 break;
198 }
199 else
200 {
201 printf("Unsupported texture data type");
202 FreeLibrary(hTexUtilDLL);
203 return false;
204 }
205 break;
206 case CF_8bit:
207 switch (textureDataType)
208 {
209 case TDT_XRGB:
210 case TDT_ARGB:
211 pSurface->format = GX2_SURFACE_FORMAT_TCS_R8_G8_B8_A8_UNORM;
212 break;
213 case TDT_R:
214 pSurface->format = GX2_SURFACE_FORMAT_TC_R8_UNORM;
215 case TDT_RG:
216 pSurface->format = GX2_SURFACE_FORMAT_TC_R8_G8_UNORM;
217 break;
218 case TDT_RGB:
219 if (pDDSD->ddpfPixelFormat.dwRBitMask == 0x0000f800 && pDDSD->ddpfPixelFormat.dwGBitMask == 0x000007e0 && pDDSD->ddpfPixelFormat.dwBBitMask == 0x0000001f)
220 {
221 // Loader will flip RGB/BGR order
222 pSurface->format = GX2_SURFACE_FORMAT_TCS_R5_G6_B5_UNORM;
223 }
224 else
225 {
226 assert(!"Unsupported texture data type");
227 FreeLibrary(hTexUtilDLL);
228 return false;
229 }
230 break;
231 default:
232 assert(!"Unsupported texture data type");
233 FreeLibrary(hTexUtilDLL);
234 return false;
235 }
236 break;
237 case CF_Float16:
238 switch (textureDataType)
239 {
240 case TDT_XRGB:
241 case TDT_ARGB:
242 pSurface->format = GX2_SURFACE_FORMAT_TC_R16_G16_B16_A16_FLOAT;
243 break;
244 case TDT_R:
245 pSurface->format = GX2_SURFACE_FORMAT_TC_R16_FLOAT;
246 break;
247 case TDT_RG:
248 pSurface->format = GX2_SURFACE_FORMAT_TC_R16_G16_FLOAT;
249 break;
250 default:
251 assert(!"Unsupported texture data type");
252 FreeLibrary(hTexUtilDLL);
253 return false;
254 }
255 break;
256 case CF_Float32:
257 switch (textureDataType)
258 {
259 case TDT_R:
260 pSurface->format = GX2_SURFACE_FORMAT_TCD_R32_FLOAT;
261 break;
262 case TDT_RG:
263 pSurface->format = GX2_SURFACE_FORMAT_TC_R32_G32_FLOAT;
264 break;
265 case TDT_XRGB:
266 case TDT_ARGB:
267 pSurface->format = GX2_SURFACE_FORMAT_TC_R32_G32_B32_A32_FLOAT;
268 break;
269 default:
270 assert(!"Unsupported texture data type");
271 FreeLibrary(hTexUtilDLL);
272 return false;
273 }
274 break;
275 case CF_16bit:
276 switch (textureDataType)
277 {
278 case TDT_XRGB:
279 case TDT_ARGB:
280 pSurface->format = GX2_SURFACE_FORMAT_TC_R16_G16_B16_A16_UNORM;
281 break;
282 case TDT_RG:
283 pSurface->format = GX2_SURFACE_FORMAT_TC_R16_G16_UNORM;
284 break;
285 default:
286 assert(!"Unsupported texture data type");
287 FreeLibrary(hTexUtilDLL);
288 return false;
289 }
290 break;
291 case CF_32bit:
292 switch (textureDataType)
293 {
294 case TDT_XRGB:
295 case TDT_ARGB:
296 pSurface->format = GX2_SURFACE_FORMAT_TC_R32_G32_B32_A32_UINT;
297 break;
298 default:
299 assert(!"Unsupported texture data type");
300 FreeLibrary(hTexUtilDLL);
301 return false;
302 }
303 break;
304 case CF_1555:
305 if (pDDSD->ddpfPixelFormat.dwRBitMask==0x00007c00) {
306 // Loader will flip RGB/BGR order
307 pSurface->format = GX2_SURFACE_FORMAT_TC_R5_G5_B5_A1_UNORM;
308 } else {
309 assert(!"Unsupported texture data type");
310 FreeLibrary(hTexUtilDLL);
311 return false;
312 }
313 break;
314 case CF_4444:
315 pSurface->format = GX2_SURFACE_FORMAT_TC_R4_G4_B4_A4_UNORM;
316 break;
317 case CF_2101010:
318 switch (textureDataType)
319 {
320 case TDT_XRGB:
321 case TDT_ARGB:
322 if (pDDSD->ddpfPixelFormat.dwRBitMask==0x000003ff)
323 {
324 pSurface->format = GX2_SURFACE_FORMAT_TCS_R10_G10_B10_A2_UNORM;
325 }
326 else if (pDDSD->ddpfPixelFormat.dwRBitMask==0x3ff00000)
327 {
328 // Loader will flip RGB/BGR order
329 pSurface->format = GX2_SURFACE_FORMAT_TCS_R10_G10_B10_A2_UNORM;
330 }
331 else
332 {
333 pSurface->format = GX2_SURFACE_FORMAT_TCS_A2_B10_G10_R10_UNORM;
334 }
335 break;
336 default:
337 assert(!"Unsupported texture data type");
338 FreeLibrary(hTexUtilDLL);
339 return false;
340 }
341 break;
342 default:
343 assert(!"Unsupported channel format");
344 FreeLibrary(hTexUtilDLL);
345 return false;
346 }
347
348 if (!fpTC2GetSourceSurfaceSize(pSurface))
349 {
350 FreeLibrary(hTexUtilDLL);
351 return false;
352 }
353
354 FreeLibrary(hTexUtilDLL);
355 return true;
356 }
357
GenericLoadFunction(FILE * & pFile,DDSD2 * & pDDSD,GX2Surface * & pSurface,void * & extra,ChannelFormat channelFormat,TextureDataType textureDataType,PreLoopFunction fnPreLoop,LoopFunction fnLoop,PostLoopFunction fnPostLoop)358 TU_Error GenericLoadFunction(FILE*& pFile, DDSD2*& pDDSD, GX2Surface*& pSurface, void*& extra, ChannelFormat channelFormat,
359 TextureDataType textureDataType, PreLoopFunction fnPreLoop, LoopFunction fnLoop, PostLoopFunction fnPostLoop)
360 {
361 u32 dwWidth, dwHeight;
362 TU_Error err;
363 MS_CubeFace cubeFaceMask = MS_CF_None;
364
365 memset(pSurface, 0, sizeof(*pSurface));
366 if (!GetGX2TextureInfo(pDDSD, pSurface, channelFormat, textureDataType, &cubeFaceMask))
367 {
368 return PE_Unknown;
369 }
370
371 pSurface->imagePtr = malloc(pSurface->imageSize + pSurface->mipSize);
372
373 if (pSurface->mipSize)
374 {
375 pSurface->mipPtr = (void*)((u8*)pSurface->imagePtr + pSurface->imageSize);
376 }
377
378 err = fnPreLoop(pFile, pDDSD, pSurface, extra);
379 if(err != PE_OK)
380 {
381 return err;
382 }
383
384 if(pSurface->dim == GX2_SURFACE_DIM_2D || pSurface->dim == GX2_SURFACE_DIM_CUBE)
385 {
386 for(u32 nFace = 0; nFace < pSurface->depth; nFace++)
387 {
388 dwWidth = pDDSD->dwWidth;
389 dwHeight = pDDSD->dwHeight;
390 for(u32 nMipLevel = 0; nMipLevel < pSurface->numMips; nMipLevel++)
391 {
392 err = fnLoop(pFile, pDDSD, pSurface, extra, nMipLevel, nFace, dwWidth, dwHeight);
393 if(err != PE_OK)
394 return err;
395 dwWidth = (dwWidth>1) ? (dwWidth>>1) : 1;
396 dwHeight = (dwHeight>1) ? (dwHeight>>1) : 1;
397 }
398 }
399 }
400 else if(pSurface->dim == GX2_SURFACE_DIM_3D)
401 {
402 dwWidth = pDDSD->dwWidth;
403 dwHeight = pDDSD->dwHeight;
404 for(u32 nMipLevel = 0; nMipLevel < pSurface->numMips; nMipLevel++)
405 {
406 int nMaxSlices = MaxFacesOrSlices(pSurface, nMipLevel);
407 for(int nSlice=0; nSlice<nMaxSlices; nSlice++)
408 {
409 err = fnLoop(pFile, pDDSD, pSurface, extra, nMipLevel, nSlice, dwWidth, dwHeight);
410 if(err != PE_OK)
411 return err;
412 }
413 dwWidth = dwWidth>1 ? dwWidth>>1 : 1;
414 dwHeight = dwHeight>1 ? dwHeight>>1 : 1;
415 }
416 }
417 else if(pSurface->dim == GX2_SURFACE_DIM_2D_ARRAY)
418 {
419 dwWidth = pDDSD->dwWidth;
420 dwHeight = pDDSD->dwHeight;
421 int nMaxSlices = pDDSD->dwDepth;
422 for(u32 nMipLevel = 0; nMipLevel < pSurface->numMips; nMipLevel++)
423 {
424 for(int nSlice=0; nSlice<nMaxSlices; nSlice++)
425 {
426 err = fnLoop(pFile, pDDSD, pSurface, extra, nMipLevel, nSlice, dwWidth, dwHeight);
427 if(err != PE_OK)
428 return err;
429 }
430 dwWidth = dwWidth>1 ? dwWidth>>1 : 1;
431 dwHeight = dwHeight>1 ? dwHeight>>1 : 1;
432 }
433 }
434 else
435 {
436 ASSERT(0);
437 return PE_Unknown;
438 }
439
440 return fnPostLoop(pFile, pDDSD, pSurface, extra);
441 }
442
GenericFreeFunction(GX2Surface * & pSurface)443 TU_Error GenericFreeFunction(GX2Surface*& pSurface)
444 {
445 if(pSurface == NULL)
446 {
447 assert(pSurface);
448 return PE_Unknown;
449 }
450
451 if(pSurface->imagePtr != NULL)
452 {
453 free(pSurface->imagePtr);
454 pSurface->imagePtr = NULL;
455 pSurface->mipPtr = NULL;
456 }
457 return PE_OK;
458 }
459
460
PreLoopDefault(FILE * &,DDSD2 * &,GX2Surface * &,void * &)461 TU_Error PreLoopDefault(FILE*&, DDSD2*&, GX2Surface*&, void*&)
462 {
463 return PE_OK;
464 }
465
LoopDefault(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * & extra,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)466 TU_Error LoopDefault(FILE*& pFile, DDSD2*&, GX2Surface*& pSurface, void*& extra,
467 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
468 {
469 MipLevel mipLevel;
470
471 ChannelFormat channelFormat = *reinterpret_cast<ChannelFormat*>(extra);
472 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
473 {
474 return PE_Unknown;
475 }
476
477 if(fread(mipLevel.pData, GetMipSize(pSurface, nMipLevel, nFaceOrSlice), 1, pFile) != 1)
478 return PE_Unknown;
479
480 return PE_OK;
481 }
482
PostLoopDefault(FILE * &,DDSD2 * &,GX2Surface * &,void * &)483 TU_Error PostLoopDefault(FILE*&, DDSD2*&, GX2Surface*&, void*&)
484 {
485 return PE_OK;
486 }
487
PreLoopFourCC(FILE * & pFile,DDSD2 * & pDDSD,GX2Surface * & pSurface,void * & extra)488 TU_Error PreLoopFourCC(FILE*& pFile, DDSD2*& pDDSD, GX2Surface*& pSurface, void*& extra)
489 {
490 u32 dwWidth;
491 u32 dwHeight;
492 u32 dwDepth;
493 u32 dwPixels = 0;
494 switch(pSurface->dim)
495 {
496 case GX2_SURFACE_DIM_2D:
497 case GX2_SURFACE_DIM_CUBE:
498 dwWidth = pSurface->width;
499 dwHeight = pSurface->height;
500 for(u32 i = 0; i < pSurface->numMips; i++)
501 {
502 dwPixels += dwWidth * dwHeight * pSurface->depth;
503 dwWidth = dwWidth>1 ? dwWidth>>1 : 1;
504 dwHeight = dwHeight>1 ? dwHeight>>1 : 1;
505 }
506 break;
507 case GX2_SURFACE_DIM_2D_ARRAY:
508 case GX2_SURFACE_DIM_3D:
509 dwWidth = pSurface->width;
510 dwHeight = pSurface->height;
511 dwDepth = pSurface->depth;
512 for(u32 i = 0; i < pSurface->numMips; i++)
513 {
514 dwPixels += dwWidth * dwHeight * dwDepth;
515 dwWidth = dwWidth>1 ? dwWidth>>1 : 1;
516 dwHeight = dwHeight>1 ? dwHeight>>1 : 1;
517 dwDepth = dwDepth>1 ? dwDepth>>1 : 1;
518 }
519 break;
520 default:
521 assert(0);
522 fclose(pFile);
523 return PE_Unknown;
524 }
525
526 extra = NULL;
527
528 return PE_OK;
529 }
530
LoopFourCC(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)531 TU_Error LoopFourCC(FILE*& pFile, DDSD2*&, GX2Surface*& pSurface, void*& /*extra*/,
532 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
533 {
534 MipLevel mipLevel;
535
536 if(!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
537 {
538 return PE_Unknown;
539 }
540
541 //read in the data....
542 if(fread(mipLevel.pData, mipLevel.byteSize, 1, pFile) != 1)
543 {
544 return PE_Unknown;
545 }
546 return PE_OK;
547 }
548
PostLoopFourCC(FILE * &,DDSD2 * &,GX2Surface * &,void * &)549 TU_Error PostLoopFourCC(FILE*&, DDSD2*&, GX2Surface*&, void*&)
550 {
551 return PE_OK;
552 }
553
PreLoopRGB565(FILE * &,DDSD2 * & pDDSD,GX2Surface * & pSurface,void * & extra)554 TU_Error PreLoopRGB565(FILE*&, DDSD2*& pDDSD, GX2Surface*& pSurface, void*& extra)
555 {
556 return PE_OK;
557 }
558
LoopRGB565(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * & extra,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)559 TU_Error LoopRGB565(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*& extra, u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
560 {
561 // Allocate the permanent buffer and unpack the bitmap data into it
562 MipLevel mipLevel;
563 u32 size = (dwWidth * dwHeight) * 2;
564 u16* pData = NULL;
565 u32 count = 0;
566 u16 value;
567
568 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
569 {
570 return PE_Unknown;
571 }
572
573 if(fread(mipLevel.pData, size, 1, pFile) != 1)
574 {
575 return PE_Unknown;
576 }
577
578 pData = (u16*)mipLevel.pData;
579
580 for (count = 0; count < (size / 2); count++)
581 {
582 value = *(pData + count);
583 *(pData + count) = ((value & 0xf800) >> 11) | (value & 0x07e0) | ((value & 0x1f) << 11);
584 }
585
586 return PE_OK;
587 }
588
PostLoopRGB565(FILE * &,DDSD2 * &,GX2Surface * &,void * & extra)589 TU_Error PostLoopRGB565(FILE*&, DDSD2*&, GX2Surface*&, void*& extra)
590 {
591 return PE_OK;
592 }
593
PreLoopRGB888(FILE * &,DDSD2 * & pDDSD,GX2Surface * & pSurface,void * & extra)594 TU_Error PreLoopRGB888(FILE*&, DDSD2*& pDDSD, GX2Surface*& pSurface, void*& extra)
595 {
596 // Allocate a temporary buffer and read the bitmap data into it
597 u32 dwTempSize = pDDSD->dwWidth * pDDSD->dwHeight * 3;
598 extra = malloc(dwTempSize);
599 return extra ? PE_OK : PE_Unknown;
600 }
601
LoopRGB888(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * & extra,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)602 TU_Error LoopRGB888(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*& extra,
603 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
604 {
605 MipLevel mipLevel;
606
607 if(fread(extra, dwWidth * dwHeight * 3, 1, pFile) != 1)
608 {
609 free(extra);
610 return PE_Unknown;
611 }
612
613 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
614 {
615 free(extra);
616 return PE_Unknown;
617 }
618
619 // Allocate the permanent buffer and unpack the bitmap data into it
620 if(!mipLevel.pData)
621 {
622 free(extra);
623 return PE_Unknown;
624 }
625
626 u32* pData = (u32*)mipLevel.pData;
627 u8* pTempPtr = (u8*)extra;
628 u8* pEnd = (u8*)pTempPtr + (dwWidth * dwHeight * 3);
629 u8 red, green, blue;
630 while(pTempPtr < pEnd)
631 {
632 blue = *pTempPtr++;
633 green = *pTempPtr++;
634 red = *pTempPtr++;
635
636 *pData++ = (0xff << 24) | (blue << 16) | (green << 8) | red;
637 }
638
639 return PE_OK;
640 }
641
PostLoopRGB888(FILE * &,DDSD2 * &,GX2Surface * &,void * & extra)642 TU_Error PostLoopRGB888(FILE*&, DDSD2*&, GX2Surface*&, void*& extra)
643 {
644 free(extra);
645 return PE_OK;
646 }
647
PreLoopRGB8888(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)648 TU_Error PreLoopRGB8888(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
649 {
650 return PE_OK;
651 }
652
LoopRGB8888(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * & extra,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)653 TU_Error LoopRGB8888(FILE*& pFile, DDSD2*&, GX2Surface*& pSurface, void*& extra,
654 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
655 {
656 u32 size = (dwWidth * dwHeight * 4);
657 MipLevel mipLevel;
658
659 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
660 {
661 return PE_Unknown;
662 }
663
664 ARGB8888Struct* pARGB8888Struct = reinterpret_cast<ARGB8888Struct*>(extra);
665 if(!(pARGB8888Struct->nFlags & EF_UseBitMasks))
666 { //not using bitmasks
667 if(fread(mipLevel.pData, size, 1, pFile) != 1)
668 {
669 return PE_Unknown;
670 }
671 }
672 else
673 { //using bitmasks
674 if(fread(pARGB8888Struct->pMemory, size, 1, pFile) != 1)
675 {
676 return PE_Unknown;
677 }
678 u8* pData = mipLevel.pData;
679 u32* pTempPtr = (u32*)pARGB8888Struct->pMemory;
680 u32* pEnd = (u32*)pARGB8888Struct->pMemory + (size / 4);
681 while(pTempPtr < pEnd)
682 {
683 *(pData + 0) = static_cast<s8> ((*pTempPtr & pARGB8888Struct->nRMask) >> pARGB8888Struct->nRShift);
684 *(pData + 1) = static_cast<s8> ((*pTempPtr & pARGB8888Struct->nGMask) >> pARGB8888Struct->nGShift);
685 *(pData + 2) = static_cast<s8> ((*pTempPtr & pARGB8888Struct->nBMask) >> pARGB8888Struct->nBShift);
686 *(pData + 3) = static_cast<s8> ((*pTempPtr & 0xFF000000) >> 24); //take alpha whether or not its used
687 pData += 4;
688 pTempPtr++;
689 }
690 }
691 return PE_OK;
692 }
693
PostLoopRGB8888(FILE * &,DDSD2 * &,GX2Surface * &,void * &)694 TU_Error PostLoopRGB8888(FILE*&, DDSD2*&, GX2Surface*&, void*&)
695 {
696 return PE_OK;
697 }
698
699
PreLoopABGR32F(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)700 TU_Error PreLoopABGR32F(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
701 {
702 return PE_OK;
703 }
704
LoopABGR32F(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)705 TU_Error LoopABGR32F(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
706 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
707 {
708 u32 size = dwWidth * dwHeight * 16;
709 MipLevel mipLevel;
710
711 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
712 {
713 return PE_Unknown;
714 }
715
716 if(fread(mipLevel.pData, size, 1, pFile) != 1)
717 {
718 return PE_Unknown;
719 }
720
721 return PE_OK;
722 }
723
LoopR32F(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)724 TU_Error LoopR32F(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
725 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
726 {
727 u32 size = dwWidth * dwHeight * 4;
728 MipLevel mipLevel;
729
730 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
731 {
732 return PE_Unknown;
733 }
734
735 if(fread(mipLevel.pData, size, 1, pFile) != 1)
736 {
737 return PE_Unknown;
738 }
739
740 return PE_OK;
741 }
742
LoopGR32F(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)743 TU_Error LoopGR32F(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
744 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
745 {
746 u32 size = dwWidth * dwHeight * 8;
747 MipLevel mipLevel;
748 //u64 value;
749 //u32 count;
750 //u64 *pData = NULL;
751
752 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
753 {
754 return PE_Unknown;
755 }
756
757 if(fread(mipLevel.pData, size, 1, pFile) != 1)
758 {
759 return PE_Unknown;
760 }
761
762 /*pData = (u64*)mipLevel.pData;
763
764 for (count = 0; count < size / 8; count++)
765 {
766 value = *(pData + count);
767 *(pData + count) = ((value & 0x00000000ffffffff) << 32) | ((value & 0xffffffff00000000) >> 32);
768 }*/
769
770 return PE_OK;
771 }
772
PostLoopABGR32F(FILE * &,DDSD2 * &,GX2Surface * &,void * &)773 TU_Error PostLoopABGR32F(FILE*&, DDSD2*&, GX2Surface*&, void*&)
774 {
775 return PE_OK;
776 }
777
PreLoopABGR16F(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)778 TU_Error PreLoopABGR16F(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
779 {
780 return PE_OK;
781 }
782
LoopABGR16F(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)783 TU_Error LoopABGR16F(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
784 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
785 {
786 MipLevel mipLevel;
787
788 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
789 {
790 return PE_Unknown;
791 }
792
793 u32 size = dwWidth * dwHeight * 8;
794
795 if(fread(mipLevel.pData, size, 1, pFile) != 1)
796 return PE_Unknown;
797
798 return PE_OK;
799 }
800
LoopGR16F(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)801 TU_Error LoopGR16F(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
802 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
803 {
804 MipLevel mipLevel;
805
806 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
807 {
808 return PE_Unknown;
809 }
810
811 u32 size = dwWidth * dwHeight * 4;
812
813 if(fread(mipLevel.pData, size, 1, pFile) != 1)
814 return PE_Unknown;
815
816 return PE_OK;
817 }
818
LoopR16F(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)819 TU_Error LoopR16F(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
820 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
821 {
822 MipLevel mipLevel;
823
824 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
825 {
826 return PE_Unknown;
827 }
828
829 u32 size = dwWidth * dwHeight * 2;
830
831 if(fread(mipLevel.pData, size, 1, pFile) != 1)
832 return PE_Unknown;
833
834 return PE_OK;
835 }
836
PostLoopABGR16F(FILE * &,DDSD2 * &,GX2Surface * &,void * &)837 TU_Error PostLoopABGR16F(FILE*&, DDSD2*&, GX2Surface*&, void*&)
838 {
839 return PE_OK;
840 }
841
PreLoopG8(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)842 TU_Error PreLoopG8(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
843 {
844 return PE_OK;
845 }
846
LoopG8(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)847 TU_Error LoopG8(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
848 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
849 {
850 MipLevel mipLevel;
851
852 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
853 {
854 return PE_Unknown;
855 }
856
857 u32 size = dwWidth * dwHeight;// + 0x3) & ~0x3;
858 // Allocate the permanent buffer and unpack the bitmap data into it
859
860 if(fread(mipLevel.pData, size, 1, pFile) != 1)
861 {
862 return PE_Unknown;
863 }
864
865 return PE_OK;
866 }
867
PostLoopG8(FILE * &,DDSD2 * &,GX2Surface * &,void * &)868 TU_Error PostLoopG8(FILE*&, DDSD2*&, GX2Surface*&, void*&)
869 {
870 return PE_OK;
871 }
872
PreLoopA4L4(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)873 TU_Error PreLoopA4L4(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
874 {
875 return PE_OK;
876 }
877
PreLoopA8L8(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)878 TU_Error PreLoopA8L8(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
879 {
880 return PE_OK;
881 }
882
LoopA4L4(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)883 TU_Error LoopA4L4(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
884 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
885 {
886 MipLevel mipLevel;
887
888 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
889 {
890 return PE_Unknown;
891 }
892
893 u32 size = ((dwWidth * dwHeight) + 0x3) & ~0x3;
894 // Allocate the permanent buffer and unpack the bitmap data into it
895
896 if(fread(mipLevel.pData, size, 1, pFile) != 1)
897 {
898 return PE_Unknown;
899 }
900
901 return PE_OK;
902 }
903
LoopA8L8(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)904 TU_Error LoopA8L8(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
905 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
906 {
907 MipLevel mipLevel;
908
909 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
910 {
911 return PE_Unknown;
912 }
913
914 u32 size = (dwWidth * dwHeight) * 2;
915 // Allocate the permanent buffer and unpack the bitmap data into it
916
917 if(fread(mipLevel.pData, size, 1, pFile) != 1)
918 {
919 return PE_Unknown;
920 }
921
922 return PE_OK;
923 }
924
PostLoopA4L4(FILE * &,DDSD2 * &,GX2Surface * &,void * &)925 TU_Error PostLoopA4L4(FILE*&, DDSD2*&, GX2Surface*&, void*&)
926 {
927 return PE_OK;
928 }
929
PostLoopA8L8(FILE * &,DDSD2 * &,GX2Surface * &,void * &)930 TU_Error PostLoopA8L8(FILE*&, DDSD2*&, GX2Surface*&, void*&)
931 {
932 return PE_OK;
933 }
934
PreLoopAG8(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)935 TU_Error PreLoopAG8(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
936 {
937 return PE_OK;
938 }
939
LoopAG8(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)940 TU_Error LoopAG8(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
941 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
942 {
943 MipLevel mipLevel;
944
945 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
946 {
947 return PE_Unknown;
948 }
949
950 u32 size = (((dwWidth * dwHeight) + 0x3) & ~0x3) * 2;
951
952 if(fread(mipLevel.pData, size, 1, pFile) != 1)
953 {
954 return PE_Unknown;
955 }
956
957 return PE_OK;
958 }
959
PostLoopAG8(FILE * &,DDSD2 * &,GX2Surface * &,void * &)960 TU_Error PostLoopAG8(FILE*&, DDSD2*&, GX2Surface*&, void*&)
961 {
962 return PE_OK;
963 }
964
PreLoopG16(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)965 TU_Error PreLoopG16(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
966 {
967 return PE_OK;
968 }
969
LoopG16(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)970 TU_Error LoopG16(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
971 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
972 {
973 MipLevel mipLevel;
974
975 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
976 {
977 return PE_Unknown;
978 }
979
980 u32 size = (((dwWidth * dwHeight) + 0x3) & ~0x3) * 2;
981
982 if(fread(mipLevel.pData, size, 1, pFile) != 1)
983 return PE_Unknown;
984
985 return PE_OK;
986 }
987
PostLoopG16(FILE * &,DDSD2 * &,GX2Surface * &,void * &)988 TU_Error PostLoopG16(FILE*&, DDSD2*&, GX2Surface*&, void*&)
989 {
990 return PE_OK;
991 }
992
PreLoopA8(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)993 TU_Error PreLoopA8(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
994 {
995 return PE_OK;
996 }
997
LoopA8(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)998 TU_Error LoopA8(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
999 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1000 {
1001 MipLevel mipLevel;
1002
1003 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
1004 {
1005 return PE_Unknown;
1006 }
1007
1008 u32 size = ((dwWidth * dwHeight) + 0x3) & ~0x3;
1009
1010 if (fread(mipLevel.pData, size, 1, pFile) != 1)
1011 {
1012 return PE_Unknown;
1013 }
1014
1015 return PE_OK;
1016 }
1017
PostLoopA8(FILE * &,DDSD2 * &,GX2Surface * &,void * &)1018 TU_Error PostLoopA8(FILE*&, DDSD2*&, GX2Surface*&, void*&)
1019 {
1020 return PE_OK;
1021 }
1022
PreLoopABGR16(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)1023 TU_Error PreLoopABGR16(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
1024 {
1025 return PE_OK;
1026 }
1027
LoopABGR16(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1028 TU_Error LoopABGR16(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1029 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1030 {
1031 MipLevel mipLevel;
1032
1033 if (!GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel))
1034 {
1035 return PE_Unknown;
1036 }
1037
1038 u32 size = dwWidth * dwHeight * 8;
1039 if(fread((void*)mipLevel.pData, size, 1, pFile) != 1)
1040 {
1041 return PE_Unknown;
1042 }
1043
1044 return PE_OK;
1045 }
1046
PostLoopABGR16(FILE * &,DDSD2 * &,GX2Surface * &,void * &)1047 TU_Error PostLoopABGR16(FILE*&, DDSD2*&, GX2Surface*&, void*&)
1048 {
1049 return PE_OK;
1050 }
1051
PreLoopG16R16(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)1052 TU_Error PreLoopG16R16(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
1053 {
1054 return PE_OK;
1055 }
1056
PreLoopARGB1555(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)1057 TU_Error PreLoopARGB1555(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
1058 {
1059 return PE_OK;
1060 }
1061
PreLoopARGB4444(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)1062 TU_Error PreLoopARGB4444(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
1063 {
1064 return PE_OK;
1065 }
1066
LoopG16R16(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1067 TU_Error LoopG16R16(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1068 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1069 {
1070 MipLevel mipLevel;
1071 u32 size = dwWidth * dwHeight * 4;
1072 //u32 value, count;
1073 //u32* pData;
1074
1075 GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1076
1077 if(fread(mipLevel.pData, size, 1, pFile) != 1)
1078 {
1079 return PE_Unknown;
1080 }
1081
1082 /*pData = (u32*)mipLevel.pData;
1083
1084 for (count = 0; count < size / 4; count++)
1085 {
1086 value = *(pData + count);
1087 *(pData + count) = ((value & 0x0000ffff) << 16) | ((value & 0xffff0000) >> 16);
1088 }*/
1089
1090 return PE_OK;
1091 }
1092
LoopARGB1555(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1093 TU_Error LoopARGB1555(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1094 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1095 {
1096 MipLevel mipLevel;
1097 u32 size = dwWidth * dwHeight * 2;
1098 u16* pData = NULL;
1099 u32 count = 0;
1100 u16 value;
1101
1102 GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1103
1104 if(fread(mipLevel.pData, size, 1, pFile) != 1)
1105 {
1106 return PE_Unknown;
1107 }
1108
1109 pData = (u16*)mipLevel.pData;
1110
1111 for (count = 0; count < size/2; count++)
1112 {
1113 value = *(pData + count);
1114 // [MSB] ARGB [LSB] to ABGR
1115 *(pData + count) = ((value & 0x8000)) | ((value & 0x7c00) >> 10) | ((value & 0x001f) << 10) | (value & 0x03e0);
1116 }
1117
1118 return PE_OK;
1119 }
1120
LoopARGB4444(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1121 TU_Error LoopARGB4444(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1122 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1123 {
1124 MipLevel mipLevel;
1125 u32 count;
1126 u32 size = dwWidth * dwHeight * 2;
1127 u16* pData = NULL;
1128 u16 value;
1129
1130 GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1131
1132 if(fread(mipLevel.pData, size, 1, pFile) != 1)
1133 {
1134 return PE_Unknown;
1135 }
1136
1137 pData = (u16*)mipLevel.pData;
1138 for (count = 0; count < (size / 2); count++)
1139 {
1140 value = *(pData + count);
1141 //ARGB ABGR
1142 *(pData + count) = (value & 0xf000) | ((value & 0x0f00) >> 8) | (value & 0x00f0) | ((value & 0x000f) << 8);
1143 }
1144
1145 return PE_OK;
1146 }
1147
PostLoopG16R16(FILE * &,DDSD2 * &,GX2Surface * &,void * &)1148 TU_Error PostLoopG16R16(FILE*&, DDSD2*&, GX2Surface*&, void*&)
1149 {
1150 return PE_OK;
1151 }
1152
PostLoopARGB1555(FILE * &,DDSD2 * &,GX2Surface * &,void * &)1153 TU_Error PostLoopARGB1555(FILE*&, DDSD2*&, GX2Surface*&, void*&)
1154 {
1155 return PE_OK;
1156 }
1157
PostLoopARGB4444(FILE * &,DDSD2 * &,GX2Surface * &,void * &)1158 TU_Error PostLoopARGB4444(FILE*&, DDSD2*&, GX2Surface*&, void*&)
1159 {
1160 return PE_OK;
1161 }
1162
SetupDDSD(DDSD2 & ddsd2,const GX2Surface * pSurface,bool bCompressed)1163 bool SetupDDSD(DDSD2& ddsd2, const GX2Surface* pSurface, bool bCompressed)
1164 {
1165 memset(&ddsd2, 0, sizeof(DDSD2));
1166 ddsd2.dwSize = sizeof(DDSD2);
1167
1168 ASSERT(pSurface);
1169 if(pSurface == NULL)
1170 {
1171 return false;
1172 }
1173
1174 ddsd2.dwWidth = pSurface->width;
1175 ddsd2.dwHeight = pSurface->height;
1176 ddsd2.dwMipMapCount = pSurface->numMips;
1177 ddsd2.dwFlags = DDSD_CAPS|DDSD_WIDTH|DDSD_HEIGHT|DDSD_PIXELFORMAT|DDSD_MIPMAPCOUNT;
1178 if(bCompressed)
1179 {
1180 ddsd2.dwFlags |= DDSD_LINEARSIZE;
1181 ddsd2.dwLinearSize = pSurface->imageSize + pSurface->mipSize;
1182 }
1183 else
1184 ddsd2.dwFlags |= DDSD_PITCH;
1185
1186 ddsd2.ddpfPixelFormat.dwSize = sizeof(DDPIXELFORMAT);
1187 ddsd2.ddsCaps.dwCaps = DDSCAPS_TEXTURE|DDSCAPS_COMPLEX|DDSCAPS_MIPMAP;
1188
1189 if(pSurface->dim == GX2_SURFACE_DIM_CUBE)
1190 {
1191 ddsd2.ddsCaps.dwCaps2 |= DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_ALLFACES;
1192 }
1193 else if(pSurface->dim == GX2_SURFACE_DIM_3D)
1194 {
1195 ddsd2.dwFlags |= DDSD_DEPTH;
1196 ddsd2.dwDepth = pSurface->depth;
1197 ddsd2.ddsCaps.dwCaps2 |= DDSCAPS2_VOLUME;
1198 }
1199 else if(pSurface->dim == GX2_SURFACE_DIM_2D_ARRAY)
1200 {
1201 ddsd2.dwFlags |= DDSD_DEPTH;
1202 ddsd2.dwDepth = pSurface->depth;
1203 }
1204
1205 return true;
1206 }
1207
SetupDDSD_DDS10(DDSD2 & ddsd2,const GX2Surface * pSurface,bool bCompressed)1208 bool SetupDDSD_DDS10(DDSD2& ddsd2, const GX2Surface* pSurface, bool bCompressed)
1209 {
1210 memset(&ddsd2, 0, sizeof(DDSD2));
1211 ddsd2.dwSize = sizeof(DDSD2);
1212
1213 ASSERT(pSurface);
1214 if(pSurface == NULL)
1215 return false;
1216
1217 ddsd2.dwWidth = pSurface->width;
1218 ddsd2.dwHeight = pSurface->height;
1219 ddsd2.dwMipMapCount = pSurface->numMips;
1220 ddsd2.dwFlags = DDSD_WIDTH|DDSD_HEIGHT;
1221
1222 ddsd2.ddpfPixelFormat.dwSize = sizeof(DDPIXELFORMAT);
1223 ddsd2.ddsCaps.dwCaps = DDSCAPS_TEXTURE;
1224
1225 if(pSurface->dim == GX2_SURFACE_DIM_CUBE)
1226 {
1227 ddsd2.ddsCaps.dwCaps2 |= DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_ALLFACES;
1228 }
1229 else if(pSurface->dim == GX2_SURFACE_DIM_3D)
1230 {
1231 ddsd2.dwFlags |= DDSD_DEPTH;
1232 ddsd2.dwDepth = pSurface->depth;
1233 ddsd2.ddsCaps.dwCaps2 |= DDSCAPS2_VOLUME;
1234 }
1235 else if(pSurface->dim == GX2_SURFACE_DIM_2D_ARRAY)
1236 {
1237 ddsd2.dwFlags |= DDSD_DEPTH;
1238 ddsd2.dwDepth = pSurface->depth;
1239 }
1240
1241 if(pSurface->numMips > 1)
1242 {
1243 ddsd2.dwFlags |= DDSD_MIPMAPCOUNT;
1244 ddsd2.ddsCaps.dwCaps |= DDSCAPS_MIPMAP;
1245 }
1246
1247 return true;
1248 }
1249
PreLoopABGR32(FILE * &,DDSD2 * &,GX2Surface * & pSurface,void * &)1250 TU_Error PreLoopABGR32(FILE*&, DDSD2*&, GX2Surface*& pSurface, void*&)
1251 {
1252 return PE_OK;
1253 }
1254
LoopABGR32(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1255 TU_Error LoopABGR32(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1256 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1257 {
1258 MipLevel mipLevel;GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1259
1260 if(fread(mipLevel.pData, GetMipSize(pSurface, nMipLevel, nFaceOrSlice), 1, pFile) != 1)
1261 return PE_Unknown;
1262
1263 return PE_OK;
1264 }
1265
PostLoopABGR32(FILE * &,DDSD2 * &,GX2Surface * &,void * &)1266 TU_Error PostLoopABGR32(FILE*&, DDSD2*&, GX2Surface*&, void*&)
1267 {
1268 return PE_OK;
1269 }
1270
LoopR32(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1271 TU_Error LoopR32(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&, u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1272 {
1273 MipLevel mipLevel;GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1274 u32 dwSize = GetMipSize(pSurface, nMipLevel, nFaceOrSlice) / 4;
1275 s8* pTempData = (s8*) malloc(dwSize);
1276 assert(pTempData);
1277 if(!pTempData)
1278 return PE_Unknown;
1279
1280 u32 dws8sRead = (u32)fread(pTempData, 1, dwSize, pFile);
1281 if(dws8sRead != dwSize)
1282 {
1283 free(pTempData);
1284 return PE_Unknown;
1285 }
1286
1287 u32* pSrc = (u32*) pTempData;
1288 u32* pEnd = (u32*) (pTempData + dwSize);
1289 u32* pDest = (u32*) mipLevel.pData;
1290 while(pSrc < pEnd)
1291 {
1292 *pDest++ = *pSrc++;
1293 *pDest++ = 0;
1294 *pDest++ = 0;
1295 *pDest++ = _UI32_MAX;
1296 }
1297
1298 free(pTempData);
1299
1300 return PE_OK;
1301 }
1302
LoopR8G8(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1303 TU_Error LoopR8G8(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1304 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1305 {
1306 MipLevel mipLevel;GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1307
1308 u32 dwSize = GetMipSize(pSurface, nMipLevel, nFaceOrSlice) / 2;
1309 s8* pTempData = (s8*) malloc(dwSize);
1310 assert(pTempData);
1311 if(!pTempData)
1312 return PE_Unknown;
1313
1314 if(fread(pTempData, dwSize, 1, pFile) != 1)
1315 {
1316 free(pTempData);
1317 return PE_Unknown;
1318 }
1319
1320 u8* pSrc = (u8*)pTempData;
1321 u8* pEnd = (u8*)(pTempData + dwSize);
1322 u8* pDest = mipLevel.pData;
1323 while(pSrc < pEnd)
1324 {
1325 *pDest++ = 0;
1326 u8 bRed = *pSrc++;
1327 *pDest++ = *pSrc++;
1328 *pDest++ = bRed;
1329 *pDest++ = (u8)0xff;
1330 }
1331
1332 free(pTempData);
1333
1334 return PE_OK;
1335 }
1336
LoopR32G32(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1337 TU_Error LoopR32G32(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1338 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1339 {
1340 MipLevel mipLevel;GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1341 u32 dwSize = GetMipSize(pSurface, nMipLevel, nFaceOrSlice) / 2;
1342 u32* pTempData = (u32*) malloc(dwSize);
1343 assert(pTempData);
1344 if(!pTempData)
1345 return PE_Unknown;
1346
1347 if(fread(pTempData, dwSize, 1, pFile) != 1)
1348 {
1349 free(pTempData);
1350 return PE_Unknown;
1351 }
1352
1353 u32* pSrc = pTempData;
1354 u32* pEnd = (pTempData + (dwSize / sizeof(u32)));
1355 u32* pDest = (u32*)mipLevel.pData;
1356 while(pSrc < pEnd)
1357 {
1358 *pDest++ = *pSrc++;
1359 *pDest++ = *pSrc++;
1360 *pDest++ = 0;
1361 *pDest++ = 0;
1362 }
1363
1364 free(pTempData);
1365
1366 return PE_OK;
1367 }
1368
LoopA2R10G10B10(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1369 TU_Error LoopA2R10G10B10(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1370 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1371 {
1372 MipLevel mipLevel;GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1373 u32 dwSize = mipLevel.byteSize;
1374 u32* pTempData = (u32*) malloc(dwSize);
1375 assert(pTempData);
1376 if(!pTempData)
1377 return PE_Unknown;
1378
1379 if(fread(pTempData, dwSize, 1, pFile) != 1)
1380 {
1381 free(pTempData);
1382 return PE_Unknown;
1383 }
1384
1385 u32* pSrc = pTempData;
1386 u32* pEnd = (pTempData + (dwSize / sizeof(u32)));
1387 u32* pDest = (u32*)mipLevel.pData;
1388 while(pSrc < pEnd)
1389 {
1390 u32 dwSrc = *pSrc++;
1391 // ARGB to ABGR
1392 u32 dwDest = (dwSrc & 0xc0000000) | ((dwSrc & 0x3ff00000) >> 20) | (dwSrc & 0x000ffc00) | ((dwSrc & 0x000003ff) << 20);
1393 *pDest++ = dwDest;
1394 }
1395
1396 free(pTempData);
1397
1398 return PE_OK;
1399 }
1400
LoopR16G16(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1401 TU_Error LoopR16G16(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1402 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1403 {
1404 MipLevel mipLevel;GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1405 u32 dwSize = GetMipSize(pSurface, nMipLevel, nFaceOrSlice) / 2;
1406 WORD* pTempData = (WORD*) malloc(dwSize);
1407 assert(pTempData);
1408 if(!pTempData)
1409 return PE_Unknown;
1410
1411 if(fread(pTempData, dwSize, 1, pFile) != 1)
1412 {
1413 free(pTempData);
1414 return PE_Unknown;
1415 }
1416
1417 WORD* pSrc = pTempData;
1418 WORD* pEnd = (pTempData + (dwSize / sizeof(WORD)));
1419 WORD* pDest = (WORD*)mipLevel.pData;
1420 while(pSrc < pEnd)
1421 {
1422 *pDest++ = *pSrc++;
1423 *pDest++ = *pSrc++;
1424 *pDest++ = 0;
1425 *pDest++ = 0;
1426 }
1427
1428 free(pTempData);
1429
1430 return PE_OK;
1431 }
1432
LoopR16(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1433 TU_Error LoopR16(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1434 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1435 {
1436 MipLevel mipLevel;GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1437 u32 dwSize = GetMipSize(pSurface, nMipLevel, nFaceOrSlice) / 4;
1438 s8* pTempData = (s8*) malloc(dwSize);
1439 assert(pTempData);
1440 if(!pTempData)
1441 return PE_Unknown;
1442
1443 u32 dws8sRead = (u32)fread(pTempData, 1, dwSize, pFile);
1444 if(dws8sRead != dwSize)
1445 {
1446 free(pTempData);
1447 return PE_Unknown;
1448 }
1449
1450 WORD* pSrc = (WORD*) pTempData;
1451 WORD* pEnd = (WORD*) (pTempData + dwSize);
1452 WORD* pDest = (WORD*)mipLevel.pData;
1453 while(pSrc < pEnd)
1454 {
1455 *pDest++ = *pSrc++;
1456 *pDest++ = 0;
1457 *pDest++ = 0;
1458 *pDest++ = _UI16_MAX;
1459 }
1460
1461 free(pTempData);
1462
1463 return PE_OK;
1464 }
1465
LoopR8(FILE * & pFile,DDSD2 * &,GX2Surface * & pSurface,void * &,u32 nMipLevel,u32 nFaceOrSlice,u32 dwWidth,u32 dwHeight)1466 TU_Error LoopR8(FILE*& pFile, DDSD2*& , GX2Surface*& pSurface, void*&,
1467 u32 nMipLevel, u32 nFaceOrSlice, u32 dwWidth, u32 dwHeight)
1468 {
1469 MipLevel mipLevel;GetMipLevel(pSurface, nMipLevel, nFaceOrSlice, &mipLevel);
1470 u32 dwSize = GetMipSize(pSurface, nMipLevel, nFaceOrSlice) / 4;
1471 s8* pTempData = (s8*) malloc(dwSize);
1472 assert(pTempData);
1473 if(!pTempData)
1474 return PE_Unknown;
1475
1476 if(fread(pTempData, dwSize, 1, pFile) != 1)
1477 {
1478 free(pTempData);
1479 return PE_Unknown;
1480 }
1481
1482 u8* pSrc = (u8*)pTempData;
1483 u8* pEnd = (u8*)(pTempData + dwSize);
1484 u8* pDest = mipLevel.pData;
1485 while(pSrc < pEnd)
1486 {
1487 *pDest++ = 0;
1488 *pDest++ = 0;
1489 *pDest++ = *pSrc++;
1490 *pDest++ = (u8)0xff;
1491 }
1492
1493 free(pTempData);
1494
1495 return PE_OK;
1496 }
1497 } //namespace DDSReader
1498