1 #pragma warning(disable: 4018) //amckern - 64bit - '<' Singed/Unsigned Mismatch
2 
3 #include "qrad.h"
4 
5 #ifdef HLRAD_HULLU
6 #define HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
7 //#undef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
8 #endif
9 
10 funcCheckVisBit g_CheckVisBit = NULL;
11 
12 unsigned        g_total_transfer = 0;
13 unsigned        g_transfer_index_bytes = 0;
14 unsigned        g_transfer_data_bytes = 0;
15 
16 #define COMPRESSED_TRANSFERS
17 //#undef  COMPRESSED_TRANSFERS
18 
FindTransferOffsetPatchnum(transfer_index_t * tIndex,const patch_t * const patch,const unsigned patchnum)19 int             FindTransferOffsetPatchnum(transfer_index_t* tIndex, const patch_t* const patch, const unsigned patchnum)
20 {
21     //
22     // binary search for match
23     //
24     int             low = 0;
25     int             high = patch->iIndex - 1;
26     int             offset;
27 
28     while (1)
29     {
30         offset = (low + high) / 2;
31 
32         if ((tIndex[offset].index + tIndex[offset].size) < patchnum)
33         {
34             low = offset + 1;
35         }
36         else if (tIndex[offset].index > patchnum)
37         {
38             high = offset - 1;
39         }
40         else
41         {
42             unsigned        x;
43             unsigned int    rval = 0;
44             transfer_index_t* pIndex = tIndex;
45 
46             for (x = 0; x < offset; x++, pIndex++)
47             {
48                 rval += pIndex->size + 1;
49             }
50             rval += patchnum - tIndex[offset].index;
51             return rval;
52         }
53         if (low > high)
54         {
55             return -1;
56         }
57     }
58 }
59 
60 #ifdef COMPRESSED_TRANSFERS
61 
GetLengthOfRun(const transfer_raw_index_t * raw,const transfer_raw_index_t * const end)62 static unsigned GetLengthOfRun(const transfer_raw_index_t* raw, const transfer_raw_index_t* const end)
63 {
64     unsigned        run_size = 0;
65 
66     while (raw < end)
67     {
68         if (((*raw) + 1) == (*(raw + 1)))
69         {
70             raw++;
71             run_size++;
72 
73             if (run_size >= MAX_COMPRESSED_TRANSFER_INDEX_SIZE)
74             {
75                 return run_size;
76             }
77         }
78         else
79         {
80             return run_size;
81         }
82     }
83     return run_size;
84 }
85 
86 #ifdef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
CompressTransferIndicies(transfer_raw_index_t * tRaw,const unsigned rawSize,unsigned * iSize,transfer_index_t * CompressedArray)87 static transfer_index_t* CompressTransferIndicies(transfer_raw_index_t* tRaw, const unsigned rawSize, unsigned* iSize, transfer_index_t *CompressedArray)
88 #else
89 static transfer_index_t* CompressTransferIndicies(transfer_raw_index_t* tRaw, const unsigned rawSize, unsigned* iSize)
90 #endif
91 {
92     unsigned        x;
93     unsigned        size = rawSize;
94     unsigned        compressed_count = 0;
95 
96     transfer_raw_index_t* raw = tRaw;
97     transfer_raw_index_t* end = tRaw + rawSize - 1;        // -1 since we are comparing current with next and get errors when bumping into the 'end'
98 
99 #ifndef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
100     transfer_index_t CompressedArray[MAX_PATCHES];         // somewhat big stack object (1 Mb with 256k patches)
101 #endif
102     transfer_index_t* compressed = CompressedArray;
103 
104     for (x = 0; x < size; x++, raw++, compressed++)
105     {
106         compressed->index = (*raw);
107         compressed->size = GetLengthOfRun(raw, end);       // Zero based (count 0 still implies 1 item in the list, so 256 max entries result)
108         raw += compressed->size;
109         x += compressed->size;
110         compressed_count++;                                // number of entries in compressed table
111     }
112 
113     *iSize = compressed_count;
114 
115     if (compressed_count)
116     {
117         unsigned        compressed_array_size = sizeof(transfer_index_t) * compressed_count;
118         transfer_index_t* rval = (transfer_index_t*)AllocBlock(compressed_array_size);
119 
120         ThreadLock();
121         g_transfer_index_bytes += compressed_array_size;
122         ThreadUnlock();
123 
124         memcpy(rval, CompressedArray, compressed_array_size);
125         return rval;
126     }
127     else
128     {
129         return NULL;
130     }
131 }
132 
133 #else
134 
135 #ifdef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
CompressTransferIndicies(const transfer_raw_index_t * tRaw,const unsigned rawSize,unsigned * iSize,transfer_index_t * CompressedArray)136 static transfer_index_t* CompressTransferIndicies(const transfer_raw_index_t* tRaw, const unsigned rawSize, unsigned* iSize, transfer_index_t *CompressedArray)
137 #else
138 static transfer_index_t* CompressTransferIndicies(const transfer_raw_index_t* tRaw, const unsigned rawSize, unsigned* iSize)
139 #endif
140 {
141     unsigned        x;
142     unsigned        size = rawSize;
143     unsigned        compressed_count = 0;
144 
145     transfer_raw_index_t* raw = tRaw;
146     transfer_raw_index_t* end = tRaw + rawSize;
147 
148 #ifndef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
149     transfer_index_t CompressedArray[MAX_PATCHES];         // somewhat big stack object (1 Mb with 256k patches)
150 #endif
151     transfer_index_t* compressed = CompressedArray;
152 
153     for (x = 0; x < size; x++, raw++, compressed++)
154     {
155         compressed->index = (*raw);
156         compressed->size = 0;
157         compressed_count++;                                // number of entries in compressed table
158     }
159 
160     *iSize = compressed_count;
161 
162     if (compressed_count)
163     {
164         unsigned        compressed_array_size = sizeof(transfer_index_t) * compressed_count;
165         transfer_index_t* rval = AllocBlock(compressed_array_size);
166 
167         ThreadLock();
168         g_transfer_index_bytes += compressed_array_size;
169         ThreadUnlock();
170 
171         memcpy(rval, CompressedArray, compressed_array_size);
172         return rval;
173     }
174     else
175     {
176         return NULL;
177     }
178 }
179 #endif
180 
181 /*
182  * =============
183  * MakeScales
184  *
185  * This is the primary time sink.
186  * It can be run multi threaded.
187  * =============
188  */
189 #ifdef SYSTEM_WIN32
190 #pragma warning(push)
191 #pragma warning(disable: 4100)                             // unreferenced formal parameter
192 #endif
MakeScales(const intptr_t threadnum)193 void            MakeScales(const intptr_t threadnum)
194 {
195     int             i;
196     unsigned        j;
197     vec3_t          delta;
198     vec_t           dist;
199     int             count;
200     float           trans;
201     patch_t*        patch;
202     patch_t*        patch2;
203     float           send;
204     vec3_t          origin;
205     vec_t           area;
206     const vec_t*    normal1;
207     const vec_t*    normal2;
208 
209 #ifdef HLRAD_HULLU
210     unsigned int    fastfind_index;
211     vec3_t          transparency;
212 #endif
213 
214     vec_t           total;
215 
216     transfer_raw_index_t* tIndex;
217     transfer_data_t* tData;
218 
219     transfer_raw_index_t* tIndex_All = (transfer_raw_index_t*)AllocBlock(sizeof(transfer_index_t) * MAX_PATCHES);
220     transfer_data_t* tData_All = (transfer_data_t*)AllocBlock(sizeof(transfer_data_t) * MAX_PATCHES);
221 
222 #ifdef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
223     //Simple optimization.. CompressTransferIndicies stack allocs 1MB object on ever run .. that's slooow :)
224     //and some compilers cannot even make it work (Segfaults). Create array here and pass to CompressTransferIndicies
225     transfer_index_t *CompressedArray = (transfer_index_t *)AllocBlock(sizeof(transfer_index_t) * MAX_PATCHES);
226 #endif
227 
228     count = 0;
229 
230 #ifdef HLRAD_HULLU
231     fastfind_index = 0;
232 #endif
233 
234     while (1)
235     {
236         i = GetThreadWork();
237         if (i == -1)
238             break;
239 
240         patch = g_patches + i;
241         patch->iIndex = 0;
242         patch->iData = 0;
243 
244         total = 0.0;
245 
246         tIndex = tIndex_All;
247         tData = tData_All;
248 
249         VectorCopy(patch->origin, origin);
250         normal1 = getPlaneFromFaceNumber(patch->faceNumber)->normal;
251 
252         area = patch->area;
253 
254         // find out which patch2's will collect light
255         // from patch
256 
257         for (j = 0, patch2 = g_patches; j < g_num_patches; j++, patch2++)
258         {
259             vec_t           dot1;
260             vec_t           dot2;
261 
262 #ifdef HLRAD_HULLU
263             VectorFill(transparency,1.0);
264             if (!g_CheckVisBit(i, j, transparency, fastfind_index) || (i == j))
265 #else
266             if (!g_CheckVisBit(i, j) || (i == j))
267 #endif
268             {
269                 continue;
270             }
271 
272             normal2 = getPlaneFromFaceNumber(patch2->faceNumber)->normal;
273 
274             // calculate transferemnce
275             VectorSubtract(patch2->origin, origin, delta);
276 
277             dist = VectorNormalize(delta);
278             dot1 = DotProduct(delta, normal1);
279             dot2 = -DotProduct(delta, normal2);
280 
281             trans = (dot1 * dot2) / (dist * dist);         // Inverse square falloff factoring angle between patch normals
282 
283 #ifdef HLRAD_HULLU
284             trans = trans * VectorAvg(transparency); //hullu: add transparency effect
285 #endif
286 
287             if (trans >= 0)
288             {
289                 send = trans * patch2->area;
290 
291                 // Caps light from getting weird
292                 if (send > 0.4f)
293                 {
294                     trans = 0.4f / patch2->area;
295                     send = 0.4f;
296                 }
297 
298                 total += send;
299 
300                 // scale to 16 bit (black magic)
301                 trans = trans * area * INVERSE_TRANSFER_SCALE;
302                 if (trans >= TRANSFER_SCALE_MAX)
303                 {
304                     trans = TRANSFER_SCALE_MAX;
305                 }
306             }
307             else
308             {
309 #if 0
310                 Warning("transfer < 0 (%f): dist=(%f)\n"
311                         "   dot1=(%f) patch@(%4.3f %4.3f %4.3f) normal(%4.3f %4.3f %4.3f)\n"
312                         "   dot2=(%f) patch@(%4.3f %4.3f %4.3f) normal(%4.3f %4.3f %4.3f)\n",
313                         trans, dist,
314                         dot1, patch->origin[0], patch->origin[1], patch->origin[2], patch->normal[0], patch->normal[1],
315                         patch->normal[2], dot2, patch2->origin[0], patch2->origin[1], patch2->origin[2],
316                         patch2->normal[0], patch2->normal[1], patch2->normal[2]);
317 #endif
318                 trans = 0.0;
319             }
320 
321             *tData = trans;
322             *tIndex = j;
323             tData++;
324             tIndex++;
325             patch->iData++;
326             count++;
327         }
328 
329         // copy the transfers out
330         if (patch->iData)
331         {
332             unsigned        data_size = patch->iData * sizeof(transfer_data_t);
333 
334             patch->tData = (transfer_data_t*)AllocBlock(data_size);
335 
336 #ifdef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
337             patch->tIndex = CompressTransferIndicies(tIndex_All, patch->iData, &patch->iIndex, CompressedArray);
338 #else
339             patch->tIndex = CompressTransferIndicies(tIndex_All, patch->iData, &patch->iIndex);
340 #endif
341 
342             hlassume(patch->tData != NULL, assume_NoMemory);
343             hlassume(patch->tIndex != NULL, assume_NoMemory);
344 
345             ThreadLock();
346             g_transfer_data_bytes += data_size;
347             ThreadUnlock();
348 
349             //
350             // normalize all transfers so exactly 50% of the light
351             // is transfered to the surroundings
352             //
353 
354             total = 0.5 / total;
355             {
356                 unsigned        x;
357                 transfer_data_t* t1 = patch->tData;
358                 transfer_data_t* t2 = tData_All;
359 
360                 for (x = 0; x < patch->iData; x++, t1++, t2++)
361                 {
362                     (*t1) = (*t2) * total;
363                 }
364             }
365         }
366     }
367 
368     FreeBlock(tIndex_All);
369     FreeBlock(tData_All);
370 
371 #ifdef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
372     FreeBlock( CompressedArray );
373 #endif
374 
375     ThreadLock();
376     g_total_transfer += count;
377     ThreadUnlock();
378 }
379 
380 #ifdef SYSTEM_WIN32
381 #pragma warning(pop)
382 #endif
383 
384 /*
385  * =============
386  * SwapTransfersTask
387  *
388  * Change transfers from light sent out to light collected in.
389  * In an ideal world, they would be exactly symetrical, but
390  * because the form factors are only aproximated, then normalized,
391  * they will actually be rather different.
392  * =============
393  */
SwapTransfers(const intptr_t patchnum)394 void            SwapTransfers(const intptr_t patchnum)
395 {
396     patch_t*        patch = &g_patches[patchnum];
397     transfer_index_t* tIndex = patch->tIndex;
398     transfer_data_t* tData = patch->tData;
399     unsigned        x;
400 
401     for (x = 0; x < patch->iIndex; x++, tIndex++)
402     {
403         unsigned        size = (tIndex->size + 1);
404         unsigned        patchnum2 = tIndex->index;
405         unsigned        y;
406 
407         for (y = 0; y < size; y++, tData++, patchnum2++)
408         {
409             patch_t*        patch2 = &g_patches[patchnum2];
410 
411             if (patchnum2 > patchnum)
412             {                                              // done with this list
413                 return;
414             }
415             else if (!patch2->iData)
416             {                                              // Set to zero in this impossible case
417                 Log("patch2 has no iData\n");
418                 (*tData) = 0;
419                 continue;
420             }
421             else
422             {
423                 transfer_index_t* tIndex2 = patch2->tIndex;
424                 transfer_data_t* tData2 = patch2->tData;
425                 int             offset = FindTransferOffsetPatchnum(tIndex2, patch2, patchnum);
426 
427                 if (offset >= 0)
428                 {
429                     transfer_data_t tmp = *tData;
430 
431                     *tData = tData2[offset];
432                     tData2[offset] = tmp;
433                 }
434                 else
435                 {                                          // Set to zero in this impossible case
436                     Log("FindTransferOffsetPatchnum returned -1 looking for patch %d in patch %d's transfer lists\n",
437                         patchnum, patchnum2);
438                     (*tData) = 0;
439                     return;
440                 }
441             }
442         }
443     }
444 }
445 
446 #ifdef HLRAD_HULLU
447 /*
448  * =============
449  * MakeScales
450  *
451  * This is the primary time sink.
452  * It can be run multi threaded.
453  * =============
454  */
455 #ifdef SYSTEM_WIN32
456 #pragma warning(push)
457 #pragma warning(disable: 4100)                             // unreferenced formal parameter
458 #endif
MakeRGBScales(const intptr_t threadnum)459 void            MakeRGBScales(const intptr_t threadnum)
460 {
461     int             i;
462     unsigned        j;
463     vec3_t          delta;
464     vec_t           dist;
465     int             count;
466     float           trans[3];
467     float           trans_one;
468     patch_t*        patch;
469     patch_t*        patch2;
470     float           send;
471     vec3_t          origin;
472     vec_t           area;
473     const vec_t*    normal1;
474     const vec_t*    normal2;
475 
476     unsigned int    fastfind_index;
477     vec3_t          transparency;
478 
479     vec_t           total;
480 
481     transfer_raw_index_t* tIndex;
482     rgb_transfer_data_t* tRGBData;
483 
484     transfer_raw_index_t* tIndex_All = (transfer_raw_index_t*)AllocBlock(sizeof(transfer_index_t) * MAX_PATCHES);
485     rgb_transfer_data_t* tRGBData_All = (rgb_transfer_data_t*)AllocBlock(sizeof(rgb_transfer_data_t) * MAX_PATCHES);
486 
487 #ifdef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
488     //Simple optimization.. CompressTransferIndicies stack allocs 1MB object on ever run .. that's slooow :)
489     //and some compilers cannot even make it work (Segfaults). Create array here and pass to CompressTransferIndicies
490     transfer_index_t *CompressedArray = (transfer_index_t *)AllocBlock(sizeof(transfer_index_t) * MAX_PATCHES);
491 #endif
492 
493     count = 0;
494 
495 	fastfind_index = 0;
496 
497 
498     while (1)
499     {
500         i = GetThreadWork();
501         if (i == -1)
502             break;
503 
504         patch = g_patches + i;
505         patch->iIndex = 0;
506         patch->iData = 0;
507 
508         total = 0.0;
509 
510         tIndex = tIndex_All;
511         tRGBData = tRGBData_All;
512 
513         VectorCopy(patch->origin, origin);
514         normal1 = getPlaneFromFaceNumber(patch->faceNumber)->normal;
515 
516         area = patch->area;
517 
518         // find out which patch2's will collect light
519         // from patch
520 
521         for (j = 0, patch2 = g_patches; j < g_num_patches; j++, patch2++)
522         {
523             vec_t           dot1;
524             vec_t           dot2;
525             VectorFill( transparency, 1.0 );
526 
527             if (!g_CheckVisBit(i, j, transparency, fastfind_index) || (i == j))
528             {
529                 continue;
530             }
531 
532             normal2 = getPlaneFromFaceNumber(patch2->faceNumber)->normal;
533 
534             // calculate transferemnce
535             VectorSubtract(patch2->origin, origin, delta);
536 
537             dist = VectorNormalize(delta);
538             dot1 = DotProduct(delta, normal1);
539             dot2 = -DotProduct(delta, normal2);
540 
541             trans_one = (dot1 * dot2) / (dist * dist);         // Inverse square falloff factoring angle between patch normals
542 
543             VectorFill(trans, trans_one);
544             VectorMultiply(trans, transparency, trans); //hullu: add transparency effect
545 
546             if (VectorAvg(trans) >= 0)
547             {
548             	/////////////////////////////////////////RED
549                 send = trans[0] * patch2->area;
550                 // Caps light from getting weird
551                 if (send > 0.4f)
552                 {
553                     trans[0] = 0.4f / patch2->area;
554                     send = 0.4f;
555                 }
556                 total += send / 3.0f;
557 
558             	/////////////////////////////////////////GREEN
559                 send = trans[1] * patch2->area;
560                 // Caps light from getting weird
561                 if (send > 0.4f)
562                 {
563                     trans[1] = 0.4f / patch2->area;
564                     send = 0.4f;
565                 }
566                 total += send / 3.0f;
567 
568             	/////////////////////////////////////////BLUE
569                 send = trans[2] * patch2->area;
570                 // Caps light from getting weird
571                 if (send > 0.4f)
572                 {
573                     trans[2] = 0.4f / patch2->area;
574                     send = 0.4f;
575                 }
576                 total += send / 3.0f;
577 
578                 // scale to 16 bit (black magic)
579                 VectorScale(trans, area * INVERSE_TRANSFER_SCALE, trans);
580 
581                 if (trans[0] >= TRANSFER_SCALE_MAX)
582                 {
583                     trans[0] = TRANSFER_SCALE_MAX;
584                 }
585                 if (trans[1] >= TRANSFER_SCALE_MAX)
586                 {
587                     trans[1] = TRANSFER_SCALE_MAX;
588                 }
589                 if (trans[2] >= TRANSFER_SCALE_MAX)
590                 {
591                     trans[2] = TRANSFER_SCALE_MAX;
592                 }
593             }
594             else
595             {
596 #if 0
597                 Warning("transfer < 0 (%4.3f %4.3f %4.3f): dist=(%f)\n"
598                         "   dot1=(%f) patch@(%4.3f %4.3f %4.3f) normal(%4.3f %4.3f %4.3f)\n"
599                         "   dot2=(%f) patch@(%4.3f %4.3f %4.3f) normal(%4.3f %4.3f %4.3f)\n",
600                         trans[0], trans[1], trans[2], dist,
601                         dot1, patch->origin[0], patch->origin[1], patch->origin[2], patch->normal[0], patch->normal[1],
602                         patch->normal[2], dot2, patch2->origin[0], patch2->origin[1], patch2->origin[2],
603                         patch2->normal[0], patch2->normal[1], patch2->normal[2]);
604 #endif
605                 VectorFill(trans,0.0);
606             }
607 
608             VectorCopy(trans, *tRGBData);
609             *tIndex = j;
610             tRGBData++;
611             tIndex++;
612             patch->iData++;
613             count++;
614         }
615 
616         // copy the transfers out
617         if (patch->iData)
618         {
619             unsigned data_size = patch->iData * sizeof(rgb_transfer_data_t);
620 
621             patch->tRGBData = (rgb_transfer_data_t*)AllocBlock(data_size);
622 
623 #ifdef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
624             patch->tIndex = CompressTransferIndicies(tIndex_All, patch->iData, &patch->iIndex, CompressedArray);
625 #else
626             patch->tIndex = CompressTransferIndicies(tIndex_All, patch->iData, &patch->iIndex);
627 #endif
628 
629             hlassume(patch->tRGBData != NULL, assume_NoMemory);
630             hlassume(patch->tIndex != NULL, assume_NoMemory);
631 
632             ThreadLock();
633             g_transfer_data_bytes += data_size;
634             ThreadUnlock();
635 
636             //
637             // normalize all transfers so exactly 50% of the light
638             // is transfered to the surroundings
639             //
640 
641             total = 0.5 / total;
642             {
643                 unsigned        x;
644                 rgb_transfer_data_t* t1 = patch->tRGBData;
645                 rgb_transfer_data_t* t2 = tRGBData_All;
646 
647                 for (x = 0; x < patch->iData; x++, t1++, t2++)
648                 {
649                      VectorScale( *t2, total, *t1 );
650                 }
651             }
652         }
653     }
654 
655     FreeBlock(tIndex_All);
656     FreeBlock(tRGBData_All);
657 
658 #ifdef HLRAD_HULLU_COMPRESSEDARRAY_TWEAK
659     FreeBlock( CompressedArray );
660 #endif
661 
662     ThreadLock();
663     g_total_transfer += count;
664     ThreadUnlock();
665 }
666 
667 #ifdef SYSTEM_WIN32
668 #pragma warning(pop)
669 #endif
670 
671 /*
672  * =============
673  * SwapTransfersTask
674  *
675  * Change transfers from light sent out to light collected in.
676  * In an ideal world, they would be exactly symetrical, but
677  * because the form factors are only aproximated, then normalized,
678  * they will actually be rather different.
679  * =============
680  */
SwapRGBTransfers(const intptr_t patchnum)681 void            SwapRGBTransfers(const intptr_t patchnum)
682 {
683     patch_t*        		patch	= &g_patches[patchnum];
684     transfer_index_t*		tIndex	= patch->tIndex;
685     rgb_transfer_data_t* 	tRGBData= patch->tRGBData;
686     unsigned        x;
687 
688     for (x = 0; x < patch->iIndex; x++, tIndex++)
689     {
690         unsigned        size = (tIndex->size + 1);
691         unsigned        patchnum2 = tIndex->index;
692         unsigned        y;
693 
694         for (y = 0; y < size; y++, tRGBData++, patchnum2++)
695         {
696             patch_t*        patch2 = &g_patches[patchnum2];
697 
698             if (patchnum2 > patchnum)
699             {                                              // done with this list
700                 return;
701             }
702             else if (!patch2->iData)
703             {                                              // Set to zero in this impossible case
704                 Log("patch2 has no iData\n");
705                 VectorFill(*tRGBData, 0);
706                 continue;
707             }
708             else
709             {
710                 transfer_index_t* tIndex2 = patch2->tIndex;
711                 rgb_transfer_data_t* tRGBData2 = patch2->tRGBData;
712                 int             offset = FindTransferOffsetPatchnum(tIndex2, patch2, patchnum);
713 
714                 if (offset >= 0)
715                 {
716                     rgb_transfer_data_t tmp;
717                     VectorCopy(*tRGBData, tmp)
718 
719                     VectorCopy(tRGBData2[offset], *tRGBData);
720                     VectorCopy(tmp, tRGBData2[offset]);
721                 }
722                 else
723                 {                                          // Set to zero in this impossible case
724                     Log("FindTransferOffsetPatchnum returned -1 looking for patch %d in patch %d's transfer lists\n",
725                         patchnum, patchnum2);
726                     VectorFill(*tRGBData, 0);
727                     return;
728                 }
729             }
730         }
731     }
732 }
733 
734 #endif /*HLRAD_HULLU*/
735 
736 
737 #ifndef HLRAD_HULLU
738 
DumpTransfersMemoryUsage()739 void            DumpTransfersMemoryUsage()
740 {
741     Log("Transfer Lists : %u transfers\n       Indices : %u bytes\n          Data : %u bytes\n",
742         g_total_transfer, g_transfer_index_bytes, g_transfer_data_bytes);
743 }
744 
745 #else
746 
747 //More human readable numbers
DumpTransfersMemoryUsage()748 void            DumpTransfersMemoryUsage()
749 {
750 	if(g_total_transfer > 1000*1000)
751 		Log("Transfer Lists : %11u : %7.2fM transfers\n", g_total_transfer, g_total_transfer/(1000.0f*1000.0f));
752 	else if(g_total_transfer > 1000)
753 		Log("Transfer Lists : %11u : %7.2fk transfers\n", g_total_transfer, g_total_transfer/1000.0f);
754 	else
755 		Log("Transfer Lists : %11u transfers\n", g_total_transfer);
756 
757 	if(g_transfer_index_bytes > 1024*1024)
758 		Log("       Indices : %11u : %7.2fM bytes\n", g_transfer_index_bytes, g_transfer_index_bytes/(1024.0f * 1024.0f));
759 	else if(g_transfer_index_bytes > 1024)
760 		Log("       Indices : %11u : %7.2fk bytes\n", g_transfer_index_bytes, g_transfer_index_bytes/1024.0f);
761 	else
762 		Log("       Indices : %11u bytes\n", g_transfer_index_bytes);
763 
764 	if(g_transfer_data_bytes > 1024*1024)
765 		Log("          Data : %11u : %7.2fM bytes\n", g_transfer_data_bytes, g_transfer_data_bytes/(1024.0f * 1024.0f));
766 	else if(g_transfer_data_bytes > 1024)
767 		Log("          Data : %11u : %7.2fk bytes\n", g_transfer_data_bytes, g_transfer_data_bytes/1024.0f);
768 	else
769 		Log("       Indices : %11u bytes\n", g_transfer_data_bytes);
770 }
771 
772 #endif
773 
774